@@ -5,13 +5,15 @@ import (
55"fmt"
66"net/http"
77
8+ "cdr.dev/slog"
89"github.com/google/uuid"
910"golang.org/x/xerrors"
1011
1112"github.com/coder/coder/v2/coderd/audit"
1213"github.com/coder/coder/v2/coderd/database"
1314"github.com/coder/coder/v2/coderd/database/db2sdk"
1415"github.com/coder/coder/v2/coderd/database/dbauthz"
16+ "github.com/coder/coder/v2/coderd/database/dbtime"
1517"github.com/coder/coder/v2/coderd/httpapi"
1618"github.com/coder/coder/v2/coderd/httpmw"
1719"github.com/coder/coder/v2/coderd/rbac/acl"
@@ -338,3 +340,45 @@ func (api *API) RequireFeatureMW(feat codersdk.FeatureName) func(http.Handler) h
338340})
339341}
340342}
343+
344+ // @Summary Invalidate prebuilt workspaces for template
345+ // @ID invalidate-prebuilt-workspaces-for-template
346+ // @Security CoderSessionToken
347+ // @Produce json
348+ // @Tags Enterprise
349+ // @Param template path string true "Template ID" format(uuid)
350+ // @Success 200 {object} codersdk.InvalidatePrebuildsResponse
351+ // @Router /templates/{template}/prebuilds/invalidate [post]
352+ func (api * API )postInvalidateTemplatePrebuilds (rw http.ResponseWriter ,r * http.Request ) {
353+ ctx := r .Context ()
354+ template := httpmw .TemplateParam (r )
355+
356+ // Authorization: user must be able to update the template
357+ if ! api .Authorize (r ,policy .ActionUpdate ,template ) {
358+ httpapi .ResourceNotFound (rw )
359+ return
360+ }
361+
362+ // Update last_invalidated_at for all presets of the active template version
363+ invalidatedPresets ,err := api .Database .UpdatePresetsLastInvalidatedAt (ctx , database.UpdatePresetsLastInvalidatedAtParams {
364+ TemplateID :template .ID ,
365+ LastInvalidatedAt : sql.NullTime {Time :dbtime .Now (),Valid :true },
366+ })
367+ if err != nil {
368+ httpapi .Write (ctx ,rw ,http .StatusInternalServerError , codersdk.Response {
369+ Message :"Failed to invalidate prebuilds." ,
370+ Detail :err .Error (),
371+ })
372+ return
373+ }
374+
375+ api .Logger .Info (ctx ,"invalidated prebuilds" ,
376+ slog .F ("template_id" ,template .ID ),
377+ slog .F ("template_name" ,template .Name ),
378+ slog .F ("preset_count" ,len (invalidatedPresets )),
379+ )
380+
381+ httpapi .Write (ctx ,rw ,http .StatusOK , codersdk.InvalidatePrebuildsResponse {
382+ InvalidatedPresets :invalidatedPresets ,
383+ })
384+ }