mirror of
https://github.com/coder/coder.git
synced 2026-09-24 15:04:27 +08:00
chore: support signed token query param for web terminal (#7197)
* chore: add endpoint to get token for web terminal * chore: support signed token query param for web terminal
This commit is contained in:
+11
-2
@@ -47,6 +47,15 @@ const (
|
||||
// token.
|
||||
//nolint:gosec
|
||||
DevURLSignedAppTokenCookie = "coder_devurl_signed_app_token"
|
||||
// SignedAppTokenQueryParameter is the name of the query parameter that
|
||||
// stores a temporary JWT that can be used to authenticate instead of the
|
||||
// session token. This is only acceptable on reconnecting-pty requests, not
|
||||
// apps.
|
||||
//
|
||||
// It has a random suffix to avoid conflict with user query parameters on
|
||||
// apps.
|
||||
//nolint:gosec
|
||||
SignedAppTokenQueryParameter = "coder_signed_app_token_23db1dde"
|
||||
|
||||
// BypassRatelimitHeader is the custom header to use to bypass ratelimits.
|
||||
// Only owners can bypass rate limits. This is typically used for scale testing.
|
||||
@@ -289,8 +298,8 @@ func ReadBodyAsError(res *http.Response) error {
|
||||
|
||||
mimeType := parseMimeType(contentType)
|
||||
if mimeType != "application/json" {
|
||||
if len(resp) > 1024 {
|
||||
resp = append(resp[:1024], []byte("...")...)
|
||||
if len(resp) > 2048 {
|
||||
resp = append(resp[:2048], []byte("...")...)
|
||||
}
|
||||
if len(resp) == 0 {
|
||||
resp = []byte("no response body")
|
||||
|
||||
@@ -174,7 +174,7 @@ func Test_readBodyAsError(t *testing.T) {
|
||||
}
|
||||
|
||||
longResponse := ""
|
||||
for i := 0; i < 2000; i++ {
|
||||
for i := 0; i < 4000; i++ {
|
||||
longResponse += "a"
|
||||
}
|
||||
|
||||
@@ -258,7 +258,7 @@ func Test_readBodyAsError(t *testing.T) {
|
||||
|
||||
assert.Contains(t, sdkErr.Response.Message, "unexpected non-JSON response")
|
||||
|
||||
expected := longResponse[0:1024] + "..."
|
||||
expected := longResponse[0:2048] + "..."
|
||||
assert.Equal(t, expected, sdkErr.Response.Detail)
|
||||
},
|
||||
},
|
||||
|
||||
@@ -362,6 +362,29 @@ func (c *Client) WorkspaceAgent(ctx context.Context, id uuid.UUID) (WorkspaceAge
|
||||
return workspaceAgent, json.NewDecoder(res.Body).Decode(&workspaceAgent)
|
||||
}
|
||||
|
||||
type IssueReconnectingPTYSignedTokenRequest struct {
|
||||
// URL is the URL of the reconnecting-pty endpoint you are connecting to.
|
||||
URL string `json:"url" validate:"required"`
|
||||
AgentID uuid.UUID `json:"agentID" format:"uuid" validate:"required"`
|
||||
}
|
||||
|
||||
type IssueReconnectingPTYSignedTokenResponse struct {
|
||||
SignedToken string `json:"signed_token"`
|
||||
}
|
||||
|
||||
func (c *Client) IssueReconnectingPTYSignedToken(ctx context.Context, req IssueReconnectingPTYSignedTokenRequest) (IssueReconnectingPTYSignedTokenResponse, error) {
|
||||
res, err := c.Request(ctx, http.MethodPost, "/api/v2/applications/reconnecting-pty-signed-token", req)
|
||||
if err != nil {
|
||||
return IssueReconnectingPTYSignedTokenResponse{}, err
|
||||
}
|
||||
defer res.Body.Close()
|
||||
if res.StatusCode != http.StatusOK {
|
||||
return IssueReconnectingPTYSignedTokenResponse{}, ReadBodyAsError(res)
|
||||
}
|
||||
var resp IssueReconnectingPTYSignedTokenResponse
|
||||
return resp, json.NewDecoder(res.Body).Decode(&resp)
|
||||
}
|
||||
|
||||
// WorkspaceAgentReconnectingPTY spawns a PTY that reconnects using the token provided.
|
||||
// It communicates using `agent.ReconnectingPTYRequest` marshaled as JSON.
|
||||
// Responses are PTY output that can be rendered.
|
||||
|
||||
Reference in New Issue
Block a user