Skip to content

Commit a4a8507

Browse files
authored
feat: Surface Flow task report on Task API (#2288)
## Description - Adds the structured execution `report` (already produced by Flow) to the rack Task endpoints. - Single-task `GET /rack/task/{id}` and `POST /rack/task/{id}/cancel` always include the report. The two list endpoints (`/rack/{id}/task`, `/tray/{id}/task`) take a new `withReport=true` opt-in. - `IncludeReport` is plumbed all the way down to `flow.ListTasksRequest`, so Flow drops the multi-KB blob server-side when the caller hasn't asked for it; the savings cover the full Temporal workflow / activity payload chain, not just the wire response. ## Type of Change <!-- Check one that best describes this PR --> - [x] **Add** - New feature or capability - [ ] **Change** - Changes in existing functionality - [ ] **Fix** - Bug fixes - [ ] **Remove** - Removed features or deprecated functionality - [ ] **Internal** - Internal changes (refactoring, tests, docs, etc.) ## Related Issues (Optional) <!-- If applicable, provide GitHub Issue. --> ## Breaking Changes - [ ] This PR contains breaking changes <!-- If checked above, describe the breaking changes and migration steps --> ## Testing <!-- How was this tested? Check all that apply --> - [x] Unit tests added/updated - [ ] Integration tests added/updated - [ ] Manual testing performed - [ ] No testing required (docs, internal refactor, etc.) ## Additional Notes <!-- Any additional context, deployment notes, or reviewer guidance --> --------- Signed-off-by: Kun Zhao <kunzhao@nvidia.com>
1 parent e867f98 commit a4a8507

22 files changed

Lines changed: 11481 additions & 8967 deletions

rest-api/api/pkg/api/handler/task.go

Lines changed: 16 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,7 @@ func NewGetTaskHandler(dbSession *cdb.Session, tc tClient.Client, scp *sc.Client
6262
// @Param org path string true "Name of NGC organization"
6363
// @Param id path string true "UUID of the Task"
6464
// @Param siteId query string true "ID of the Site"
65-
// @Success 200 {object} model.APIRackTask
65+
// @Success 200 {object} model.APITask
6666
// @Router /v2/org/{org}/nico/rack/task/{id} [get]
6767
func (gth GetTaskHandler) Handle(c echo.Context) error {
6868
org, dbUser, ctx, logger, handlerSpan := common.SetupHandler("Task", "Get", c, gth.tracerSpan)
@@ -183,7 +183,7 @@ func (gth GetTaskHandler) Handle(c echo.Context) error {
183183
return cutil.NewAPIErrorResponse(c, http.StatusNotFound, "Task not found", nil)
184184
}
185185

186-
apiTask := model.NewAPIRackTask(tasks[0])
186+
apiTask := model.NewAPITask(tasks[0], model.WithTaskReport())
187187

188188
logger.Info().Msg("finishing API handler")
189189

@@ -229,7 +229,7 @@ func NewCancelTaskHandler(dbSession *cdb.Session, tc tClient.Client, scp *sc.Cli
229229
// @Param org path string true "Name of NGC organization"
230230
// @Param id path string true "UUID of the Task"
231231
// @Param body body model.APICancelTaskRequest true "Cancel task request"
232-
// @Success 202 {object} model.APIRackTask
232+
// @Success 202 {object} model.APITask
233233
// @Router /v2/org/{org}/nico/rack/task/{id}/cancel [post]
234234
func (cth CancelTaskHandler) Handle(c echo.Context) error {
235235
org, dbUser, ctx, logger, handlerSpan := common.SetupHandler("Task", "Cancel", c, cth.tracerSpan)
@@ -354,7 +354,7 @@ func (cth CancelTaskHandler) Handle(c echo.Context) error {
354354
return cutil.NewAPIErrorResponse(c, code, fmt.Sprintf("Failed to execute Task cancellation workflow on Site: %s", unwrapErr), nil)
355355
}
356356

357-
apiTask := model.NewAPIRackTask(flowResponse.GetTask())
357+
apiTask := model.NewAPITask(flowResponse.GetTask(), model.WithTaskReport())
358358

359359
logger.Info().Msg("finishing API handler")
360360
return c.JSON(http.StatusAccepted, apiTask)
@@ -393,9 +393,10 @@ func NewGetRackTasksHandler(dbSession *cdb.Session, tc tClient.Client, scp *sc.C
393393
// @Param id path string true "UUID of the Rack"
394394
// @Param siteId query string true "ID of the Site"
395395
// @Param activeOnly query boolean false "Restrict to non-terminal Tasks"
396+
// @Param includeReport query boolean false "Include the per-task execution report in each response (default false)"
396397
// @Param pageNumber query integer false "Page number of results returned"
397398
// @Param pageSize query integer false "Number of results per page"
398-
// @Success 200 {array} model.APIRackTask
399+
// @Success 200 {array} model.APITask
399400
// @Router /v2/org/{org}/nico/rack/{id}/task [get]
400401
func (h GetRackTasksHandler) Handle(c echo.Context) error {
401402
org, dbUser, ctx, logger, handlerSpan := common.SetupHandler("RackTasks", "List", c, h.tracerSpan)
@@ -490,6 +491,7 @@ func (h GetRackTasksHandler) Handle(c echo.Context) error {
490491
flowRequest := &flowv1.ListTasksRequest{
491492
RackId: &flowv1.UUID{Id: rackID},
492493
ActiveOnly: apiRequest.ActiveOnly,
494+
WithReport: apiRequest.IncludeReport,
493495
}
494496
if pageRequest.Offset != nil && pageRequest.Limit != nil {
495497
flowRequest.Pagination = &flowv1.Pagination{
@@ -527,9 +529,10 @@ func (h GetRackTasksHandler) Handle(c echo.Context) error {
527529
return cutil.NewAPIErrorResponse(c, code, fmt.Sprintf("Failed to execute workflow to retrieve all Rack Tasks: %s", unwrapErr), nil)
528530
}
529531

530-
apiTasks := make([]*model.APIRackTask, 0, len(flowResponse.GetTasks()))
532+
taskOpts := apiRequest.TaskOptions()
533+
apiTasks := make([]*model.APITask, 0, len(flowResponse.GetTasks()))
531534
for _, t := range flowResponse.GetTasks() {
532-
apiTasks = append(apiTasks, model.NewAPIRackTask(t))
535+
apiTasks = append(apiTasks, model.NewAPITask(t, taskOpts...))
533536
}
534537

535538
total := int(flowResponse.GetTotal())
@@ -576,9 +579,10 @@ func NewGetTrayTasksHandler(dbSession *cdb.Session, tc tClient.Client, scp *sc.C
576579
// @Param id path string true "UUID of the Tray"
577580
// @Param siteId query string true "ID of the Site"
578581
// @Param activeOnly query boolean false "Restrict to non-terminal Tasks"
582+
// @Param includeReport query boolean false "Include the per-task execution report in each response (default false)"
579583
// @Param pageNumber query integer false "Page number of results returned"
580584
// @Param pageSize query integer false "Number of results per page"
581-
// @Success 200 {array} model.APIRackTask
585+
// @Success 200 {array} model.APITask
582586
// @Router /v2/org/{org}/nico/tray/{id}/task [get]
583587
func (h GetTrayTasksHandler) Handle(c echo.Context) error {
584588
org, dbUser, ctx, logger, handlerSpan := common.SetupHandler("TrayTasks", "List", c, h.tracerSpan)
@@ -673,6 +677,7 @@ func (h GetTrayTasksHandler) Handle(c echo.Context) error {
673677
flowRequest := &flowv1.ListTasksRequest{
674678
ComponentId: &flowv1.UUID{Id: trayID},
675679
ActiveOnly: apiRequest.ActiveOnly,
680+
WithReport: apiRequest.IncludeReport,
676681
}
677682
if pageRequest.Offset != nil && pageRequest.Limit != nil {
678683
flowRequest.Pagination = &flowv1.Pagination{
@@ -710,9 +715,10 @@ func (h GetTrayTasksHandler) Handle(c echo.Context) error {
710715
return cutil.NewAPIErrorResponse(c, code, fmt.Sprintf("Failed to execute workflow to retrieve all Tray Tasks: %s", unwrapErr), nil)
711716
}
712717

713-
apiTasks := make([]*model.APIRackTask, 0, len(flowResponse.GetTasks()))
718+
taskOpts := apiRequest.TaskOptions()
719+
apiTasks := make([]*model.APITask, 0, len(flowResponse.GetTasks()))
714720
for _, t := range flowResponse.GetTasks() {
715-
apiTasks = append(apiTasks, model.NewAPIRackTask(t))
721+
apiTasks = append(apiTasks, model.NewAPITask(t, taskOpts...))
716722
}
717723

718724
total := int(flowResponse.GetTotal())

rest-api/api/pkg/api/handler/task_test.go

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -189,7 +189,7 @@ func TestGetTaskHandler_Handle(t *testing.T) {
189189
return
190190
}
191191

192-
var apiTask model.APIRackTask
192+
var apiTask model.APITask
193193
err = json.Unmarshal(rec.Body.Bytes(), &apiTask)
194194
assert.NoError(t, err)
195195
assert.Equal(t, taskUUID, apiTask.ID)
@@ -264,7 +264,7 @@ func ExecuteGetTasksHandlerTestCases(t *testing.T, pathFmt string, handle func(e
264264
if tt.expectedStatus != http.StatusOK {
265265
return
266266
}
267-
var tasks []model.APIRackTask
267+
var tasks []model.APITask
268268
require.NoError(t, json.Unmarshal(rec.Body.Bytes(), &tasks))
269269
require.Len(t, tasks, len(tt.mockTasks))
270270
require.NotEmpty(t, rec.Header().Get("X-Pagination"), "X-Pagination")
@@ -580,7 +580,7 @@ func TestCancelTaskHandler_Handle(t *testing.T) {
580580
return
581581
}
582582

583-
var apiTask model.APIRackTask
583+
var apiTask model.APITask
584584
err = json.Unmarshal(rec.Body.Bytes(), &apiTask)
585585
assert.NoError(t, err)
586586
assert.Equal(t, taskUUID, apiTask.ID)

0 commit comments

Comments
 (0)