Skip to content

Commit b7ea479

Browse files
chore: track workspace resource monitors in telemetry (cherry-pick #16776) (#16779)
Cherry-picked chore: track workspace resource monitors in telemetry (#16776) Addresses https://github.com/coder/nexus/issues/195. Specifically, just the "tracking templates" requirement: > ## Tracking in templates > To enable resource alerts, a user must add the resource_monitoring block to a template's coder_agent resource. We'd like to track if customers have any resource monitoring enabled on a per-deployment basis. Even better, we could identify which templates are using resource monitoring. Co-authored-by: Hugo Dutka <hugo@coder.com>
1 parent 735dc5d commit b7ea479

File tree

10 files changed

+285
-22
lines changed

10 files changed

+285
-22
lines changed

coderd/database/dbauthz/dbauthz.go

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1426,6 +1426,17 @@ func (q *querier) FetchMemoryResourceMonitorsByAgentID(ctx context.Context, agen
14261426
return q.db.FetchMemoryResourceMonitorsByAgentID(ctx, agentID)
14271427
}
14281428

1429+
func (q *querier) FetchMemoryResourceMonitorsUpdatedAfter(ctx context.Context, updatedAt time.Time) ([]database.WorkspaceAgentMemoryResourceMonitor, error) {
1430+
// Ideally, we would return a list of monitors that the user has access to. However, that check would need to
1431+
// be implemented similarly to GetWorkspaces, which is more complex than what we're doing here. Since this query
1432+
// was introduced for telemetry, we perform a simpler check.
1433+
if err := q.authorizeContext(ctx, policy.ActionRead, rbac.ResourceWorkspaceAgentResourceMonitor); err != nil {
1434+
return nil, err
1435+
}
1436+
1437+
return q.db.FetchMemoryResourceMonitorsUpdatedAfter(ctx, updatedAt)
1438+
}
1439+
14291440
func (q *querier) FetchNewMessageMetadata(ctx context.Context, arg database.FetchNewMessageMetadataParams) (database.FetchNewMessageMetadataRow, error) {
14301441
if err := q.authorizeContext(ctx, policy.ActionRead, rbac.ResourceNotificationMessage); err != nil {
14311442
return database.FetchNewMessageMetadataRow{}, err
@@ -1447,6 +1458,17 @@ func (q *querier) FetchVolumesResourceMonitorsByAgentID(ctx context.Context, age
14471458
return q.db.FetchVolumesResourceMonitorsByAgentID(ctx, agentID)
14481459
}
14491460

1461+
func (q *querier) FetchVolumesResourceMonitorsUpdatedAfter(ctx context.Context, updatedAt time.Time) ([]database.WorkspaceAgentVolumeResourceMonitor, error) {
1462+
// Ideally, we would return a list of monitors that the user has access to. However, that check would need to
1463+
// be implemented similarly to GetWorkspaces, which is more complex than what we're doing here. Since this query
1464+
// was introduced for telemetry, we perform a simpler check.
1465+
if err := q.authorizeContext(ctx, policy.ActionRead, rbac.ResourceWorkspaceAgentResourceMonitor); err != nil {
1466+
return nil, err
1467+
}
1468+
1469+
return q.db.FetchVolumesResourceMonitorsUpdatedAfter(ctx, updatedAt)
1470+
}
1471+
14501472
func (q *querier) GetAPIKeyByID(ctx context.Context, id string) (database.APIKey, error) {
14511473
return fetch(q.log, q.auth, q.db.GetAPIKeyByID)(ctx, id)
14521474
}

coderd/database/dbauthz/dbauthz_test.go

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4802,6 +4802,14 @@ func (s *MethodTestSuite) TestResourcesMonitor() {
48024802
}).Asserts(rbac.ResourceWorkspaceAgentResourceMonitor, policy.ActionUpdate)
48034803
}))
48044804

4805+
s.Run("FetchMemoryResourceMonitorsUpdatedAfter", s.Subtest(func(db database.Store, check *expects) {
4806+
check.Args(dbtime.Now()).Asserts(rbac.ResourceWorkspaceAgentResourceMonitor, policy.ActionRead)
4807+
}))
4808+
4809+
s.Run("FetchVolumesResourceMonitorsUpdatedAfter", s.Subtest(func(db database.Store, check *expects) {
4810+
check.Args(dbtime.Now()).Asserts(rbac.ResourceWorkspaceAgentResourceMonitor, policy.ActionRead)
4811+
}))
4812+
48054813
s.Run("FetchMemoryResourceMonitorsByAgentID", s.Subtest(func(db database.Store, check *expects) {
48064814
agt, w := createAgent(s.T(), db)
48074815

coderd/database/dbmem/dbmem.go

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2361,6 +2361,19 @@ func (q *FakeQuerier) FetchMemoryResourceMonitorsByAgentID(_ context.Context, ag
23612361
return database.WorkspaceAgentMemoryResourceMonitor{}, sql.ErrNoRows
23622362
}
23632363

2364+
func (q *FakeQuerier) FetchMemoryResourceMonitorsUpdatedAfter(_ context.Context, updatedAt time.Time) ([]database.WorkspaceAgentMemoryResourceMonitor, error) {
2365+
q.mutex.RLock()
2366+
defer q.mutex.RUnlock()
2367+
2368+
monitors := []database.WorkspaceAgentMemoryResourceMonitor{}
2369+
for _, monitor := range q.workspaceAgentMemoryResourceMonitors {
2370+
if monitor.UpdatedAt.After(updatedAt) {
2371+
monitors = append(monitors, monitor)
2372+
}
2373+
}
2374+
return monitors, nil
2375+
}
2376+
23642377
func (q *FakeQuerier) FetchNewMessageMetadata(_ context.Context, arg database.FetchNewMessageMetadataParams) (database.FetchNewMessageMetadataRow, error) {
23652378
err := validateDatabaseType(arg)
23662379
if err != nil {
@@ -2405,6 +2418,19 @@ func (q *FakeQuerier) FetchVolumesResourceMonitorsByAgentID(_ context.Context, a
24052418
return monitors, nil
24062419
}
24072420

2421+
func (q *FakeQuerier) FetchVolumesResourceMonitorsUpdatedAfter(_ context.Context, updatedAt time.Time) ([]database.WorkspaceAgentVolumeResourceMonitor, error) {
2422+
q.mutex.RLock()
2423+
defer q.mutex.RUnlock()
2424+
2425+
monitors := []database.WorkspaceAgentVolumeResourceMonitor{}
2426+
for _, monitor := range q.workspaceAgentVolumeResourceMonitors {
2427+
if monitor.UpdatedAt.After(updatedAt) {
2428+
monitors = append(monitors, monitor)
2429+
}
2430+
}
2431+
return monitors, nil
2432+
}
2433+
24082434
func (q *FakeQuerier) GetAPIKeyByID(_ context.Context, id string) (database.APIKey, error) {
24092435
q.mutex.RLock()
24102436
defer q.mutex.RUnlock()

coderd/database/dbmetrics/querymetrics.go

Lines changed: 14 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

coderd/database/dbmock/dbmock.go

Lines changed: 30 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

coderd/database/querier.go

Lines changed: 2 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

coderd/database/queries.sql.go

Lines changed: 81 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

coderd/database/queries/workspaceagentresourcemonitors.sql

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,19 @@
1+
-- name: FetchVolumesResourceMonitorsUpdatedAfter :many
2+
SELECT
3+
*
4+
FROM
5+
workspace_agent_volume_resource_monitors
6+
WHERE
7+
updated_at > $1;
8+
9+
-- name: FetchMemoryResourceMonitorsUpdatedAfter :many
10+
SELECT
11+
*
12+
FROM
13+
workspace_agent_memory_resource_monitors
14+
WHERE
15+
updated_at > $1;
16+
117
-- name: FetchMemoryResourceMonitorsByAgentID :one
218
SELECT
319
*

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