From acf1ad3bfd513b389a4e519cdd47d951aa22501d Mon Sep 17 00:00:00 2001 From: Kira Pilot Date: Mon, 24 Oct 2022 22:58:06 +0000 Subject: [PATCH 1/8] added test for stopping a workspace build --- coderd/workspacebuilds_test.go | 4 ++++ docs/admin/audit-logs.md | 1 + 2 files changed, 5 insertions(+) diff --git a/coderd/workspacebuilds_test.go b/coderd/workspacebuilds_test.go index 983063a1907bc..1c7f2abf1f141 100644 --- a/coderd/workspacebuilds_test.go +++ b/coderd/workspacebuilds_test.go @@ -561,6 +561,10 @@ func TestWorkspaceBuildStatus(t *testing.T) { require.NoError(t, err) require.EqualValues(t, codersdk.WorkspaceStatusStopped, workspace.LatestBuild.Status) + // assert an audit log has been created for workspace stopping + require.Len(t, auditor.AuditLogs, 5) + assert.Equal(t, database.AuditActionStop, auditor.AuditLogs[4].Action) + _ = closeDaemon.Close() // after successful cancel is "canceled" build = coderdtest.CreateWorkspaceBuild(t, client, workspace, database.WorkspaceTransitionStart) diff --git a/docs/admin/audit-logs.md b/docs/admin/audit-logs.md index d7179c7ee590c..7ecd5142cb660 100644 --- a/docs/admin/audit-logs.md +++ b/docs/admin/audit-logs.md @@ -11,6 +11,7 @@ We track **create, update and delete** events for the following resources: - Template - TemplateVersion - Workspace +- Workspace start/stop - User - Group From c50db185f03253ab43d78c242e3fecf67da42f1d Mon Sep 17 00:00:00 2001 From: Kira Pilot Date: Wed, 26 Oct 2022 15:26:43 +0000 Subject: [PATCH 2/8] formatted sfriendly string; added tests --- coderd/audit.go | 4 +++- coderd/audit/request.go | 2 +- coderd/workspacebuilds_test.go | 23 +++++++++++++++---- .../AuditLogRow/AuditLogRow.stories.tsx | 11 ++++++++- .../components/AuditLogRow/AuditLogRow.tsx | 8 +++++++ site/src/testHelpers/entities.ts | 9 ++++++++ 6 files changed, 50 insertions(+), 7 deletions(-) diff --git a/coderd/audit.go b/coderd/audit.go index ba845c8b048b0..4f2c28aff4912 100644 --- a/coderd/audit.go +++ b/coderd/audit.go @@ -241,7 +241,9 @@ func auditLogDescription(alog database.GetAuditLogsOffsetRow) string { // We don't display the name for git ssh keys. It's fairly long and doesn't // make too much sense to display. - if alog.ResourceType != database.ResourceTypeGitSshKey { + + // The UI-visible target for workspace builds is workspace (see above block) so we don't add it to the friendly string + if alog.ResourceType != database.ResourceTypeGitSshKey && alog.ResourceType != database.ResourceTypeWorkspaceBuild { str += " {target}" } diff --git a/coderd/audit/request.go b/coderd/audit/request.go index efba7ebb4304b..ef15611fa8de2 100644 --- a/coderd/audit/request.go +++ b/coderd/audit/request.go @@ -46,7 +46,7 @@ func ResourceTarget[T Auditable](tgt T) string { return typed.Name case database.WorkspaceBuild: // this isn't used - return string(typed.BuildNumber) + return "" case database.GitSSHKey: return typed.PublicKey case database.Group: diff --git a/coderd/workspacebuilds_test.go b/coderd/workspacebuilds_test.go index a758bb712ce24..3d152932bf866 100644 --- a/coderd/workspacebuilds_test.go +++ b/coderd/workspacebuilds_test.go @@ -536,13 +536,20 @@ func TestWorkspaceBuildStatus(t *testing.T) { ctx, cancel := context.WithTimeout(context.Background(), testutil.WaitLong) defer cancel() auditor := audit.NewMock() + numLogs := len(auditor.AuditLogs) client, closeDaemon, api := coderdtest.NewWithAPI(t, &coderdtest.Options{IncludeProvisionerDaemon: true, Auditor: auditor}) user := coderdtest.CreateFirstUser(t, client) + numLogs++ // add an audit log for user version := coderdtest.CreateTemplateVersion(t, client, user.OrganizationID, nil) + numLogs++ // add an audit log for template version + coderdtest.AwaitTemplateVersionJob(t, client, version.ID) closeDaemon.Close() template := coderdtest.CreateTemplate(t, client, user.OrganizationID, version.ID) + numLogs++ // add an audit log for template creation + workspace := coderdtest.CreateWorkspace(t, client, user.OrganizationID, template.ID) + numLogs++ // add an audit log for workspace creation // initial returned state is "pending" require.EqualValues(t, codersdk.WorkspaceStatusPending, workspace.LatestBuild.Status) @@ -562,14 +569,21 @@ func TestWorkspaceBuildStatus(t *testing.T) { require.EqualValues(t, codersdk.WorkspaceStatusStopped, workspace.LatestBuild.Status) // assert an audit log has been created for workspace stopping - require.Len(t, auditor.AuditLogs, 5) - assert.Equal(t, database.AuditActionStop, auditor.AuditLogs[4].Action) + numLogs++ // add an audit log for workspace_build stop + require.Len(t, auditor.AuditLogs, numLogs) + require.Equal(t, database.AuditActionStop, auditor.AuditLogs[numLogs-1].Action) _ = closeDaemon.Close() // after successful cancel is "canceled" build = coderdtest.CreateWorkspaceBuild(t, client, workspace, database.WorkspaceTransitionStart) err = client.CancelWorkspaceBuild(ctx, build.ID) require.NoError(t, err) + + numLogs++ // add an audit log for workspace build start + // assert an audit log has been created workspace starting + require.Len(t, auditor.AuditLogs, numLogs) + require.Equal(t, database.AuditActionStart, auditor.AuditLogs[numLogs-1].Action) + workspace, err = client.Workspace(ctx, workspace.ID) require.NoError(t, err) require.EqualValues(t, codersdk.WorkspaceStatusCanceled, workspace.LatestBuild.Status) @@ -581,8 +595,9 @@ func TestWorkspaceBuildStatus(t *testing.T) { workspace, err = client.DeletedWorkspace(ctx, workspace.ID) require.NoError(t, err) require.EqualValues(t, codersdk.WorkspaceStatusDeleted, workspace.LatestBuild.Status) + numLogs++ // add an audit log for workspace build deletion // assert an audit log has been created for deletion - require.Len(t, auditor.AuditLogs, 7) - assert.Equal(t, database.AuditActionDelete, auditor.AuditLogs[6].Action) + require.Len(t, auditor.AuditLogs, numLogs) + require.Equal(t, database.AuditActionDelete, auditor.AuditLogs[numLogs-1].Action) } diff --git a/site/src/components/AuditLogRow/AuditLogRow.stories.tsx b/site/src/components/AuditLogRow/AuditLogRow.stories.tsx index b552b868ac240..9b1239ebe7b82 100644 --- a/site/src/components/AuditLogRow/AuditLogRow.stories.tsx +++ b/site/src/components/AuditLogRow/AuditLogRow.stories.tsx @@ -5,7 +5,11 @@ import TableContainer from "@material-ui/core/TableContainer" import TableHead from "@material-ui/core/TableHead" import TableRow from "@material-ui/core/TableRow" import { ComponentMeta, Story } from "@storybook/react" -import { MockAuditLog, MockAuditLog2 } from "testHelpers/entities" +import { + MockAuditLog, + MockAuditLog2, + MockAuditLogWithWorkspaceBuild, +} from "testHelpers/entities" import { AuditLogRow, AuditLogRowProps } from "./AuditLogRow" export default { @@ -38,3 +42,8 @@ WithDiff.args = { auditLog: MockAuditLog2, defaultIsDiffOpen: true, } + +export const WithWorkspaceBuild = Template.bind({}) +WithWorkspaceBuild.args = { + auditLog: MockAuditLogWithWorkspaceBuild, +} diff --git a/site/src/components/AuditLogRow/AuditLogRow.tsx b/site/src/components/AuditLogRow/AuditLogRow.tsx index 478c01e05aa19..e330ecfc8da8a 100644 --- a/site/src/components/AuditLogRow/AuditLogRow.tsx +++ b/site/src/components/AuditLogRow/AuditLogRow.tsx @@ -31,6 +31,14 @@ const pillTypeByHttpStatus = ( } const readableActionMessage = (auditLog: AuditLog) => { + // workspace builds audit logs don't have targets; therefore format them differently + if (auditLog.resource_type === "workspace_build") { + const substr = auditLog.description.trim().split(" ").pop() ?? "" + return auditLog.description + .replace("{user}", `${auditLog.user?.username}`) + .replace(substr, `${substr}`) + } + return auditLog.description .replace("{user}", `${auditLog.user?.username}`) .replace("{target}", `${auditLog.resource_target}`) diff --git a/site/src/testHelpers/entities.ts b/site/src/testHelpers/entities.ts index d02f8bfd5b60f..a910f7b51c916 100644 --- a/site/src/testHelpers/entities.ts +++ b/site/src/testHelpers/entities.ts @@ -949,6 +949,15 @@ export const MockAuditLog2: TypesGen.AuditLog = { }, } +export const MockAuditLogWithWorkspaceBuild: TypesGen.AuditLog = { + ...MockAuditLog, + id: "f90995bf-4a2b-4089-b597-e66e025e523e", + request_id: "61555889-2875-475c-8494-f7693dd5d75b", + action: "stop", + resource_type: "workspace_build", + description: "{user} stopped workspace build for workspace test2", +} + export const MockWorkspaceQuota: TypesGen.WorkspaceQuota = { user_workspace_count: 0, user_workspace_limit: 100, From fdc94d8295d0f6786f286c6a972be525c0170434 Mon Sep 17 00:00:00 2001 From: Kira Pilot Date: Wed, 26 Oct 2022 15:50:51 +0000 Subject: [PATCH 3/8] logging unmarshal error in auditLogDescription --- coderd/audit.go | 19 ++++++++++++------- 1 file changed, 12 insertions(+), 7 deletions(-) diff --git a/coderd/audit.go b/coderd/audit.go index 4f2c28aff4912..b1e399f6a9149 100644 --- a/coderd/audit.go +++ b/coderd/audit.go @@ -1,6 +1,7 @@ package coderd import ( + "context" "encoding/json" "fmt" "net" @@ -13,6 +14,7 @@ import ( "github.com/google/uuid" "github.com/tabbed/pqtype" + "cdr.dev/slog" "github.com/coder/coder/coderd/database" "github.com/coder/coder/coderd/httpapi" "github.com/coder/coder/coderd/httpmw" @@ -57,7 +59,7 @@ func (api *API) auditLogs(rw http.ResponseWriter, r *http.Request) { } httpapi.Write(ctx, rw, http.StatusOK, codersdk.AuditLogResponse{ - AuditLogs: convertAuditLogs(dblogs), + AuditLogs: api.convertAuditLogs(ctx, dblogs), }) } @@ -165,17 +167,17 @@ func (api *API) generateFakeAuditLog(rw http.ResponseWriter, r *http.Request) { rw.WriteHeader(http.StatusNoContent) } -func convertAuditLogs(dblogs []database.GetAuditLogsOffsetRow) []codersdk.AuditLog { +func (api *API) convertAuditLogs(ctx context.Context, dblogs []database.GetAuditLogsOffsetRow) []codersdk.AuditLog { alogs := make([]codersdk.AuditLog, 0, len(dblogs)) for _, dblog := range dblogs { - alogs = append(alogs, convertAuditLog(dblog)) + alogs = append(alogs, api.convertAuditLog(ctx, dblog)) } return alogs } -func convertAuditLog(dblog database.GetAuditLogsOffsetRow) codersdk.AuditLog { +func (api *API) convertAuditLog(ctx context.Context, dblog database.GetAuditLogsOffsetRow) codersdk.AuditLog { ip, _ := netip.AddrFromSlice(dblog.Ip.IPNet.IP) diff := codersdk.AuditDiff{} @@ -214,7 +216,7 @@ func convertAuditLog(dblog database.GetAuditLogsOffsetRow) codersdk.AuditLog { Diff: diff, StatusCode: dblog.StatusCode, AdditionalFields: dblog.AdditionalFields, - Description: auditLogDescription(dblog), + Description: api.auditLogDescription(ctx, dblog), User: user, } } @@ -223,7 +225,7 @@ type WorkspaceResourceInfo struct { WorkspaceName string } -func auditLogDescription(alog database.GetAuditLogsOffsetRow) string { +func (api *API) auditLogDescription(ctx context.Context, alog database.GetAuditLogsOffsetRow) string { str := fmt.Sprintf("{user} %s %s", codersdk.AuditAction(alog.Action).FriendlyString(), codersdk.ResourceType(alog.ResourceType).FriendlyString(), @@ -235,7 +237,10 @@ func auditLogDescription(alog database.GetAuditLogsOffsetRow) string { if alog.ResourceType == database.ResourceTypeWorkspaceBuild { workspaceBytes := []byte(alog.AdditionalFields) var workspaceResourceInfo WorkspaceResourceInfo - _ = json.Unmarshal(workspaceBytes, &workspaceResourceInfo) + err := json.Unmarshal(workspaceBytes, &workspaceResourceInfo) + if err != nil { + api.Logger.Error(ctx, "could not unmarshal workspace name for friendly string", slog.Error(err)) + } str += " for workspace " + workspaceResourceInfo.WorkspaceName } From 93aedaff54805ed761e0293419270644ce15d2af Mon Sep 17 00:00:00 2001 From: Kira Pilot Date: Wed, 26 Oct 2022 15:57:50 +0000 Subject: [PATCH 4/8] prettier --- site/src/testHelpers/entities.ts | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/site/src/testHelpers/entities.ts b/site/src/testHelpers/entities.ts index a910f7b51c916..62e9c7804313f 100644 --- a/site/src/testHelpers/entities.ts +++ b/site/src/testHelpers/entities.ts @@ -950,12 +950,12 @@ export const MockAuditLog2: TypesGen.AuditLog = { } export const MockAuditLogWithWorkspaceBuild: TypesGen.AuditLog = { - ...MockAuditLog, - id: "f90995bf-4a2b-4089-b597-e66e025e523e", - request_id: "61555889-2875-475c-8494-f7693dd5d75b", - action: "stop", - resource_type: "workspace_build", - description: "{user} stopped workspace build for workspace test2", + ...MockAuditLog, + id: "f90995bf-4a2b-4089-b597-e66e025e523e", + request_id: "61555889-2875-475c-8494-f7693dd5d75b", + action: "stop", + resource_type: "workspace_build", + description: "{user} stopped workspace build for workspace test2", } export const MockWorkspaceQuota: TypesGen.WorkspaceQuota = { From 1a9936f03717c6a97b65c0aa87682b458335ef5e Mon Sep 17 00:00:00 2001 From: Kira Pilot Date: Wed, 26 Oct 2022 16:35:17 +0000 Subject: [PATCH 5/8] got rid of extra workspace word --- coderd/audit.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/coderd/audit.go b/coderd/audit.go index b1e399f6a9149..e90d78f6e27a3 100644 --- a/coderd/audit.go +++ b/coderd/audit.go @@ -232,7 +232,7 @@ func (api *API) auditLogDescription(ctx context.Context, alog database.GetAuditL ) // Strings for build updates follow the below format: - // "{user} started workspace build for workspace {target}" + // "{user} started workspace build for {target}" // where target is a workspace instead of the workspace build if alog.ResourceType == database.ResourceTypeWorkspaceBuild { workspaceBytes := []byte(alog.AdditionalFields) @@ -241,7 +241,7 @@ func (api *API) auditLogDescription(ctx context.Context, alog database.GetAuditL if err != nil { api.Logger.Error(ctx, "could not unmarshal workspace name for friendly string", slog.Error(err)) } - str += " for workspace " + workspaceResourceInfo.WorkspaceName + str += " for " + workspaceResourceInfo.WorkspaceName } // We don't display the name for git ssh keys. It's fairly long and doesn't From 3e4cb891fd0ee99293dd676fb71c0ab86435f075 Mon Sep 17 00:00:00 2001 From: Kira Pilot Date: Thu, 27 Oct 2022 15:13:59 +0000 Subject: [PATCH 6/8] PR feedback --- coderd/audit.go | 3 ++- .../components/AuditLogRow/AuditLogRow.tsx | 25 +++++++++++++++---- 2 files changed, 22 insertions(+), 6 deletions(-) diff --git a/coderd/audit.go b/coderd/audit.go index e90d78f6e27a3..3e011dc6616ae 100644 --- a/coderd/audit.go +++ b/coderd/audit.go @@ -233,7 +233,8 @@ func (api *API) auditLogDescription(ctx context.Context, alog database.GetAuditL // Strings for build updates follow the below format: // "{user} started workspace build for {target}" - // where target is a workspace instead of the workspace build + // where target is a workspace instead of the workspace build. + // Note the workspace name will be bolded on the FE. if alog.ResourceType == database.ResourceTypeWorkspaceBuild { workspaceBytes := []byte(alog.AdditionalFields) var workspaceResourceInfo WorkspaceResourceInfo diff --git a/site/src/components/AuditLogRow/AuditLogRow.tsx b/site/src/components/AuditLogRow/AuditLogRow.tsx index e330ecfc8da8a..3452222cf969b 100644 --- a/site/src/components/AuditLogRow/AuditLogRow.tsx +++ b/site/src/components/AuditLogRow/AuditLogRow.tsx @@ -30,13 +30,26 @@ const pillTypeByHttpStatus = ( return "success" } -const readableActionMessage = (auditLog: AuditLog) => { +// the BE returns additional_field as a string, since it's stored as JSON but +// technically, it's a map, so we adjust the type here. +type ExtendedAuditLog = Omit & { + additional_fields: Record +} + +const readableActionMessage = (auditLog: ExtendedAuditLog) => { // workspace builds audit logs don't have targets; therefore format them differently if (auditLog.resource_type === "workspace_build") { - const substr = auditLog.description.trim().split(" ").pop() ?? "" - return auditLog.description + // remove the "{target}" identifier in the string description as we don't use it + const amendedDescription = auditLog.description.substring( + 0, + auditLog.description.lastIndexOf(" "), + ) + return amendedDescription .replace("{user}", `${auditLog.user?.username}`) - .replace(substr, `${substr}`) + .replace( + auditLog.additional_fields.workspaceName, + `${auditLog.additional_fields.workspaceName}`, + ) } return auditLog.description @@ -101,7 +114,9 @@ export const AuditLogRow: React.FC = ({ From dc7e4a969395fecfc0ab8e3f560d4dcf465d7ea1 Mon Sep 17 00:00:00 2001 From: Kira Pilot Date: Thu, 27 Oct 2022 18:46:01 +0000 Subject: [PATCH 7/8] fixed mistake; wrote tests in penance --- site/src/api/typesGenerated.ts | 3 +- .../AuditLogRow/AuditLogRow.test.tsx | 41 +++++++++++++++++++ .../components/AuditLogRow/AuditLogRow.tsx | 28 +++---------- site/src/testHelpers/entities.ts | 7 +++- 4 files changed, 53 insertions(+), 26 deletions(-) create mode 100644 site/src/components/AuditLogRow/AuditLogRow.test.tsx diff --git a/site/src/api/typesGenerated.ts b/site/src/api/typesGenerated.ts index c006c13928eef..7a3bf62d1c6af 100644 --- a/site/src/api/typesGenerated.ts +++ b/site/src/api/typesGenerated.ts @@ -65,8 +65,7 @@ export interface AuditLog { readonly action: AuditAction readonly diff: AuditDiff readonly status_code: number - // This is likely an enum in an external package ("encoding/json.RawMessage") - readonly additional_fields: string + readonly additional_fields: Record readonly description: string readonly user?: User } diff --git a/site/src/components/AuditLogRow/AuditLogRow.test.tsx b/site/src/components/AuditLogRow/AuditLogRow.test.tsx new file mode 100644 index 0000000000000..3ee13f46e4bc0 --- /dev/null +++ b/site/src/components/AuditLogRow/AuditLogRow.test.tsx @@ -0,0 +1,41 @@ +import { readableActionMessage } from "./AuditLogRow" +import { + MockAuditLog, + MockAuditLogWithWorkspaceBuild, +} from "testHelpers/entities" + +describe("readableActionMessage()", () => { + it("renders the correct string for a workspaceBuild audit log", async () => { + // When + const friendlyString = readableActionMessage(MockAuditLogWithWorkspaceBuild) + + // Then + expect(friendlyString).toBe( + "TestUser stopped workspace build for test2", + ) + }) + it("renders the correct string for a workspaceBuild audit log with a duplicate word", async () => { + // When + const AuditLogWithRepeat = { + ...MockAuditLogWithWorkspaceBuild, + additional_fields: { + workspaceName: "workspace", + }, + } + const friendlyString = readableActionMessage(AuditLogWithRepeat) + + // Then + expect(friendlyString).toBe( + "TestUser stopped workspace build for workspace", + ) + }) + it("renders the correct string for a workspace audit log", async () => { + // When + const friendlyString = readableActionMessage(MockAuditLog) + + // Then + expect(friendlyString).toBe( + "TestUser updated workspace bruno-dev", + ) + }) +}) diff --git a/site/src/components/AuditLogRow/AuditLogRow.tsx b/site/src/components/AuditLogRow/AuditLogRow.tsx index 8bd27fa4bbeb5..c00d1564d5c95 100644 --- a/site/src/components/AuditLogRow/AuditLogRow.tsx +++ b/site/src/components/AuditLogRow/AuditLogRow.tsx @@ -16,31 +16,17 @@ import userAgentParser from "ua-parser-js" import { combineClasses } from "util/combineClasses" import { AuditLogDiff } from "./AuditLogDiff" -// the BE returns additional_field as a string, since it's stored as JSON but -// technically, it's a map, so we adjust the type here. -type ExtendedAuditLog = Omit & { - additional_fields: Record -} +export const readableActionMessage = (auditLog: AuditLog): string => { + let target = auditLog.resource_target.trim() -const readableActionMessage = (auditLog: ExtendedAuditLog) => { - // workspace builds audit logs don't have targets; therefore format them differently + // audit logs with a resource_type of workspace build use workspace name as a target if (auditLog.resource_type === "workspace_build") { - // remove the "{target}" identifier in the string description as we don't use it - const amendedDescription = auditLog.description.substring( - 0, - auditLog.description.lastIndexOf(" "), - ) - return amendedDescription - .replace("{user}", `${auditLog.user?.username}`) - .replace( - auditLog.additional_fields.workspaceName, - `${auditLog.additional_fields.workspaceName}`, - ) + target = auditLog.additional_fields.workspaceName.trim() } return auditLog.description .replace("{user}", `${auditLog.user?.username.trim()}`) - .replace("{target}", `${auditLog.resource_target.trim()}`) + .replace("{target}", `${target}`) } const httpStatusColor = (httpStatus: number): PaletteIndex => { @@ -132,9 +118,7 @@ export const AuditLogRow: React.FC = ({ > diff --git a/site/src/testHelpers/entities.ts b/site/src/testHelpers/entities.ts index 62e9c7804313f..704871496c79c 100644 --- a/site/src/testHelpers/entities.ts +++ b/site/src/testHelpers/entities.ts @@ -916,7 +916,7 @@ export const MockAuditLog: TypesGen.AuditLog = { }, }, status_code: 200, - additional_fields: "", + additional_fields: {}, description: "{user} updated workspace {target}", user: MockUser, } @@ -955,7 +955,10 @@ export const MockAuditLogWithWorkspaceBuild: TypesGen.AuditLog = { request_id: "61555889-2875-475c-8494-f7693dd5d75b", action: "stop", resource_type: "workspace_build", - description: "{user} stopped workspace build for workspace test2", + description: "{user} stopped workspace build for {target}", + additional_fields: { + "workspaceName": "test2" + }, } export const MockWorkspaceQuota: TypesGen.WorkspaceQuota = { From ac68b3cb150dc2424ef5129965070bce8d247f6d Mon Sep 17 00:00:00 2001 From: Kira Pilot Date: Thu, 27 Oct 2022 18:50:00 +0000 Subject: [PATCH 8/8] fix be --- coderd/audit.go | 36 ++++++++++---------------------- scripts/apitypings/main.go | 2 ++ site/src/testHelpers/entities.ts | 2 +- 3 files changed, 14 insertions(+), 26 deletions(-) diff --git a/coderd/audit.go b/coderd/audit.go index 3e011dc6616ae..1a8f0e79b8b8e 100644 --- a/coderd/audit.go +++ b/coderd/audit.go @@ -1,7 +1,6 @@ package coderd import ( - "context" "encoding/json" "fmt" "net" @@ -14,7 +13,6 @@ import ( "github.com/google/uuid" "github.com/tabbed/pqtype" - "cdr.dev/slog" "github.com/coder/coder/coderd/database" "github.com/coder/coder/coderd/httpapi" "github.com/coder/coder/coderd/httpmw" @@ -59,7 +57,7 @@ func (api *API) auditLogs(rw http.ResponseWriter, r *http.Request) { } httpapi.Write(ctx, rw, http.StatusOK, codersdk.AuditLogResponse{ - AuditLogs: api.convertAuditLogs(ctx, dblogs), + AuditLogs: convertAuditLogs(dblogs), }) } @@ -167,17 +165,17 @@ func (api *API) generateFakeAuditLog(rw http.ResponseWriter, r *http.Request) { rw.WriteHeader(http.StatusNoContent) } -func (api *API) convertAuditLogs(ctx context.Context, dblogs []database.GetAuditLogsOffsetRow) []codersdk.AuditLog { +func convertAuditLogs(dblogs []database.GetAuditLogsOffsetRow) []codersdk.AuditLog { alogs := make([]codersdk.AuditLog, 0, len(dblogs)) for _, dblog := range dblogs { - alogs = append(alogs, api.convertAuditLog(ctx, dblog)) + alogs = append(alogs, convertAuditLog(dblog)) } return alogs } -func (api *API) convertAuditLog(ctx context.Context, dblog database.GetAuditLogsOffsetRow) codersdk.AuditLog { +func convertAuditLog(dblog database.GetAuditLogsOffsetRow) codersdk.AuditLog { ip, _ := netip.AddrFromSlice(dblog.Ip.IPNet.IP) diff := codersdk.AuditDiff{} @@ -216,40 +214,28 @@ func (api *API) convertAuditLog(ctx context.Context, dblog database.GetAuditLogs Diff: diff, StatusCode: dblog.StatusCode, AdditionalFields: dblog.AdditionalFields, - Description: api.auditLogDescription(ctx, dblog), + Description: auditLogDescription(dblog), User: user, } } -type WorkspaceResourceInfo struct { - WorkspaceName string -} - -func (api *API) auditLogDescription(ctx context.Context, alog database.GetAuditLogsOffsetRow) string { +func auditLogDescription(alog database.GetAuditLogsOffsetRow) string { str := fmt.Sprintf("{user} %s %s", codersdk.AuditAction(alog.Action).FriendlyString(), codersdk.ResourceType(alog.ResourceType).FriendlyString(), ) - // Strings for build updates follow the below format: + // Strings for workspace_builds follow the below format: // "{user} started workspace build for {target}" - // where target is a workspace instead of the workspace build. - // Note the workspace name will be bolded on the FE. + // where target is a workspace instead of the workspace build, + // passed in on the FE via AuditLog.AdditionalFields rather than derived in request.go:35 if alog.ResourceType == database.ResourceTypeWorkspaceBuild { - workspaceBytes := []byte(alog.AdditionalFields) - var workspaceResourceInfo WorkspaceResourceInfo - err := json.Unmarshal(workspaceBytes, &workspaceResourceInfo) - if err != nil { - api.Logger.Error(ctx, "could not unmarshal workspace name for friendly string", slog.Error(err)) - } - str += " for " + workspaceResourceInfo.WorkspaceName + str += " for" } // We don't display the name for git ssh keys. It's fairly long and doesn't // make too much sense to display. - - // The UI-visible target for workspace builds is workspace (see above block) so we don't add it to the friendly string - if alog.ResourceType != database.ResourceTypeGitSshKey && alog.ResourceType != database.ResourceTypeWorkspaceBuild { + if alog.ResourceType != database.ResourceTypeGitSshKey { str += " {target}" } diff --git a/scripts/apitypings/main.go b/scripts/apitypings/main.go index 20ff1ba1f8250..5d27695fc6d43 100644 --- a/scripts/apitypings/main.go +++ b/scripts/apitypings/main.go @@ -688,6 +688,8 @@ func (g *Generator) typescriptType(ty types.Type) (TypescriptType, error) { return TypescriptType{ValueType: "string", Optional: true}, nil case "github.com/google/uuid.UUID": return TypescriptType{ValueType: "string"}, nil + case "encoding/json.RawMessage": + return TypescriptType{ValueType: "Record"}, nil } // Then see if the type is defined elsewhere. If it is, we can just diff --git a/site/src/testHelpers/entities.ts b/site/src/testHelpers/entities.ts index 704871496c79c..d4670f66baead 100644 --- a/site/src/testHelpers/entities.ts +++ b/site/src/testHelpers/entities.ts @@ -957,7 +957,7 @@ export const MockAuditLogWithWorkspaceBuild: TypesGen.AuditLog = { resource_type: "workspace_build", description: "{user} stopped workspace build for {target}", additional_fields: { - "workspaceName": "test2" + workspaceName: "test2", }, } 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