Skip to content

Commit 7a1ae15

Browse files
committed
Add RBAC tests
1 parent d3b9ab5 commit 7a1ae15

File tree

7 files changed

+27
-8
lines changed

7 files changed

+27
-8
lines changed

.vscode/settings.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -80,6 +80,7 @@
8080
"weblinks",
8181
"webrtc",
8282
"workspaceagent",
83+
"workspaceapp",
8384
"workspaceapps",
8485
"wsconncache",
8586
"xerrors",

coderd/coderd.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -107,8 +107,8 @@ func New(options *Options) *API {
107107
// %40 is the encoded character of the @ symbol. VS Code Web does
108108
// not handle character encoding properly, so it's safe to assume
109109
// other applications might not as well.
110-
r.Route("/%40{user}/{workspaceagent}/apps/{application}", apps)
111-
r.Route("/@{user}/{workspaceagent}/apps/{application}", apps)
110+
r.Route("/%40{user}/{workspacename}/apps/{workspaceapp}", apps)
111+
r.Route("/@{user}/{workspacename}/apps/{workspaceapp}", apps)
112112

113113
r.Route("/api/v2", func(r chi.Router) {
114114
r.NotFound(func(rw http.ResponseWriter, r *http.Request) {

coderd/coderd_test.go

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,10 @@ func TestAuthorizeAllEndpoints(t *testing.T) {
8282
Agents: []*proto.Agent{{
8383
Id: "something",
8484
Auth: &proto.Agent_Token{},
85+
Apps: []*proto.App{{
86+
Name: "app",
87+
Url: "http://localhost:3000",
88+
}},
8589
}},
8690
}},
8791
},
@@ -128,6 +132,15 @@ func TestAuthorizeAllEndpoints(t *testing.T) {
128132
"GET:/api/v2/users/authmethods": {NoAuthorize: true},
129133
"POST:/api/v2/csp/reports": {NoAuthorize: true},
130134

135+
"GET:/%40{user}/{workspacename}/apps/{application}/*": {
136+
AssertAction: rbac.ActionRead,
137+
AssertObject: workspaceRBACObj,
138+
},
139+
"GET:/@{user}/{workspacename}/apps/{application}/*": {
140+
AssertAction: rbac.ActionRead,
141+
AssertObject: workspaceRBACObj,
142+
},
143+
131144
// Has it's own auth
132145
"GET:/api/v2/users/oauth2/github/callback": {NoAuthorize: true},
133146

@@ -374,6 +387,7 @@ func TestAuthorizeAllEndpoints(t *testing.T) {
374387
route = strings.ReplaceAll(route, "{template}", template.ID.String())
375388
route = strings.ReplaceAll(route, "{hash}", file.Hash)
376389
route = strings.ReplaceAll(route, "{workspaceresource}", workspaceResources[0].ID.String())
390+
route = strings.ReplaceAll(route, "{workspaceapp}", workspaceResources[0].Agents[0].Apps[0].Name)
377391
route = strings.ReplaceAll(route, "{templateversion}", version.ID.String())
378392
route = strings.ReplaceAll(route, "{templateversiondryrun}", templateVersionDryRun.ID.String())
379393
route = strings.ReplaceAll(route, "{templatename}", template.Name)

coderd/workspaceagents.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -403,7 +403,7 @@ func (api *API) workspaceAgentPTY(rw http.ResponseWriter, r *http.Request) {
403403
return
404404
}
405405
defer release()
406-
ptNetConn, err := agentConn.ReconnectingPTY(reconnect.String(), uint16(height), uint16(width), "")
406+
ptNetConn, err := agentConn.ReconnectingPTY(reconnect.String(), uint16(height), uint16(width), r.URL.Query().Get("command"))
407407
if err != nil {
408408
_ = conn.Close(websocket.StatusInternalError, httpapi.WebsocketCloseSprintf("dial: %s", err))
409409
return

coderd/workspaceagents_test.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -297,7 +297,7 @@ func TestWorkspaceAgentPTY(t *testing.T) {
297297
})
298298
resources := coderdtest.AwaitWorkspaceAgents(t, client, workspace.LatestBuild.ID)
299299

300-
conn, err := client.WorkspaceAgentReconnectingPTY(context.Background(), resources[0].Agents[0].ID, uuid.New(), 80, 80)
300+
conn, err := client.WorkspaceAgentReconnectingPTY(context.Background(), resources[0].Agents[0].ID, uuid.New(), 80, 80, "/bin/bash")
301301
require.NoError(t, err)
302302
defer conn.Close()
303303

coderd/workspaceapps.go

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ import (
1515
"github.com/coder/coder/coderd/database"
1616
"github.com/coder/coder/coderd/httpapi"
1717
"github.com/coder/coder/coderd/httpmw"
18+
"github.com/coder/coder/coderd/rbac"
1819
"github.com/coder/coder/site"
1920
)
2021

@@ -23,7 +24,7 @@ import (
2324
func (api *API) workspaceAppsProxyPath(rw http.ResponseWriter, r *http.Request) {
2425
user := httpmw.UserParam(r)
2526
// This can be in the form of: "<workspace-name>.[workspace-agent]" or "<workspace-name>"
26-
workspaceWithAgent := chi.URLParam(r, "workspaceagent")
27+
workspaceWithAgent := chi.URLParam(r, "workspacename")
2728
workspaceParts := strings.Split(workspaceWithAgent, ".")
2829

2930
workspace, err := api.Database.GetWorkspaceByOwnerIDAndName(r.Context(), database.GetWorkspaceByOwnerIDAndNameParams{
@@ -42,6 +43,9 @@ func (api *API) workspaceAppsProxyPath(rw http.ResponseWriter, r *http.Request)
4243
})
4344
return
4445
}
46+
if !api.Authorize(rw, r, rbac.ActionRead, workspace) {
47+
return
48+
}
4549

4650
build, err := api.Database.GetLatestWorkspaceBuildByWorkspaceID(r.Context(), workspace.ID)
4751
if err != nil {
@@ -87,7 +91,7 @@ func (api *API) workspaceAppsProxyPath(rw http.ResponseWriter, r *http.Request)
8791

8892
app, err := api.Database.GetWorkspaceAppByAgentIDAndName(r.Context(), database.GetWorkspaceAppByAgentIDAndNameParams{
8993
AgentID: agent.ID,
90-
Name: chi.URLParam(r, "application"),
94+
Name: chi.URLParam(r, "workspaceapp"),
9195
})
9296
if errors.Is(err, sql.ErrNoRows) {
9397
httpapi.Write(rw, http.StatusNotFound, httpapi.Response{

codersdk/workspaceagents.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -341,8 +341,8 @@ func (c *Client) WorkspaceAgent(ctx context.Context, id uuid.UUID) (WorkspaceAge
341341
// WorkspaceAgentReconnectingPTY spawns a PTY that reconnects using the token provided.
342342
// It communicates using `agent.ReconnectingPTYRequest` marshaled as JSON.
343343
// Responses are PTY output that can be rendered.
344-
func (c *Client) WorkspaceAgentReconnectingPTY(ctx context.Context, agentID, reconnect uuid.UUID, height, width int) (net.Conn, error) {
345-
serverURL, err := c.URL.Parse(fmt.Sprintf("/api/v2/workspaceagents/%s/pty?reconnect=%s&height=%d&width=%d", agentID, reconnect, height, width))
344+
func (c *Client) WorkspaceAgentReconnectingPTY(ctx context.Context, agentID, reconnect uuid.UUID, height, width int, command string) (net.Conn, error) {
345+
serverURL, err := c.URL.Parse(fmt.Sprintf("/api/v2/workspaceagents/%s/pty?reconnect=%s&height=%d&width=%d&command=%s", agentID, reconnect, height, width, command))
346346
if err != nil {
347347
return nil, xerrors.Errorf("parse url: %w", err)
348348
}

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy