Skip to content

Commit db117b4

Browse files
committed
Add batch.retrieve and allow filtering by batch in runs.list
1 parent d91ba05 commit db117b4

File tree

8 files changed

+149
-0
lines changed

8 files changed

+149
-0
lines changed
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
import { RetrieveBatchResponse } from "@trigger.dev/core/v3";
2+
import { AuthenticatedEnvironment } from "~/services/apiAuth.server";
3+
import { BasePresenter } from "./basePresenter.server";
4+
5+
export class ApiRetrieveBatchPresenter extends BasePresenter {
6+
public async call(
7+
friendlyId: string,
8+
env: AuthenticatedEnvironment
9+
): Promise<RetrieveBatchResponse | undefined> {
10+
return this.traceWithEnv<RetrieveBatchResponse | undefined>("call", env, async (span) => {
11+
const batch = await this._replica.batchTaskRun.findFirst({
12+
where: {
13+
friendlyId,
14+
runtimeEnvironmentId: env.id,
15+
},
16+
});
17+
18+
if (!batch) {
19+
return;
20+
}
21+
22+
return {
23+
id: batch.friendlyId,
24+
status: batch.status,
25+
idempotencyKey: batch.idempotencyKey ?? undefined,
26+
createdAt: batch.createdAt,
27+
updatedAt: batch.updatedAt,
28+
runCount: batch.runCount,
29+
};
30+
});
31+
}
32+
}

apps/webapp/app/presenters/v3/ApiRunListPresenter.server.ts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -119,6 +119,7 @@ export const ApiRunListSearchParams = z.object({
119119
"filter[createdAt][from]": CoercedDate,
120120
"filter[createdAt][to]": CoercedDate,
121121
"filter[createdAt][period]": z.string().optional(),
122+
"filter[batch]": z.string().optional(),
122123
});
123124

124125
type ApiRunListSearchParams = z.infer<typeof ApiRunListSearchParams>;
@@ -209,6 +210,10 @@ export class ApiRunListPresenter extends BasePresenter {
209210
options.isTest = searchParams["filter[isTest]"];
210211
}
211212

213+
if (searchParams["filter[batch]"]) {
214+
options.batchId = searchParams["filter[batch]"];
215+
}
216+
212217
const presenter = new RunListPresenter();
213218

214219
logger.debug("Calling RunListPresenter", { options });
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
import { json } from "@remix-run/server-runtime";
2+
import { z } from "zod";
3+
import { ApiRetrieveBatchPresenter } from "~/presenters/v3/ApiRetrieveBatchPresenter.server";
4+
import { createLoaderApiRoute } from "~/services/routeBuilders/apiBuilder.server";
5+
6+
const ParamsSchema = z.object({
7+
batchId: z.string(),
8+
});
9+
10+
export const loader = createLoaderApiRoute(
11+
{
12+
params: ParamsSchema,
13+
allowJWT: true,
14+
corsStrategy: "all",
15+
authorization: {
16+
action: "read",
17+
resource: (params) => ({ batch: params.batchId }),
18+
superScopes: ["read:runs", "read:all", "admin"],
19+
},
20+
},
21+
async ({ params, authentication }) => {
22+
const presenter = new ApiRetrieveBatchPresenter();
23+
const result = await presenter.call(params.batchId, authentication.environment);
24+
25+
if (!result) {
26+
return json({ error: "Batch not found" }, { status: 404 });
27+
}
28+
29+
return json(result);
30+
}
31+
);

packages/core/src/v3/apiClient/index.ts

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ import {
1818
ListScheduleOptions,
1919
ReplayRunResponse,
2020
RescheduleRunRequestBody,
21+
RetrieveBatchResponse,
2122
RetrieveRunResponse,
2223
ScheduleObject,
2324
TaskRunExecutionResult,
@@ -670,6 +671,18 @@ export class ApiClient {
670671
);
671672
}
672673

674+
retrieveBatch(batchId: string, requestOptions?: ZodFetchOptions) {
675+
return zodfetch(
676+
RetrieveBatchResponse,
677+
`${this.baseUrl}/api/v1/batches/${batchId}`,
678+
{
679+
method: "GET",
680+
headers: this.#getHeaders(false),
681+
},
682+
mergeRequestOptions(this.defaultRequestOptions, requestOptions)
683+
);
684+
}
685+
673686
#getHeaders(spanParentAsLink: boolean, additionalHeaders?: Record<string, string | undefined>) {
674687
const headers: Record<string, string> = {
675688
"Content-Type": "application/json",
@@ -793,6 +806,10 @@ function createSearchQueryForListRuns(query?: ListRunsQueryParams): URLSearchPar
793806
if (query.period) {
794807
searchParams.append("filter[createdAt][period]", query.period);
795808
}
809+
810+
if (query.batch) {
811+
searchParams.append("filter[batch]", query.batch);
812+
}
796813
}
797814

798815
return searchParams;

packages/core/src/v3/apiClient/types.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@ export interface ListRunsQueryParams extends CursorPageParams {
3131
tag?: Array<string> | string;
3232
schedule?: string;
3333
isTest?: boolean;
34+
batch?: string;
3435
}
3536

3637
export interface ListProjectRunsQueryParams extends CursorPageParams, ListRunsQueryParams {

packages/core/src/v3/schemas/api.ts

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -712,3 +712,18 @@ export const SubscribeRunRawShape = z.object({
712712
});
713713

714714
export type SubscribeRunRawShape = z.infer<typeof SubscribeRunRawShape>;
715+
716+
export const BatchStatus = z.enum(["PENDING", "COMPLETED"]);
717+
718+
export type BatchStatus = z.infer<typeof BatchStatus>;
719+
720+
export const RetrieveBatchResponse = z.object({
721+
id: z.string(),
722+
status: BatchStatus,
723+
idempotencyKey: z.string().optional(),
724+
createdAt: z.coerce.date(),
725+
updatedAt: z.coerce.date(),
726+
runCount: z.number(),
727+
});
728+
729+
export type RetrieveBatchResponse = z.infer<typeof RetrieveBatchResponse>;

packages/trigger-sdk/src/v3/batch.ts

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,53 @@
1+
import {
2+
accessoryAttributes,
3+
apiClientManager,
4+
ApiPromise,
5+
ApiRequestOptions,
6+
mergeRequestOptions,
7+
RetrieveBatchResponse,
8+
} from "@trigger.dev/core/v3";
19
import {
210
batchTriggerById,
311
batchTriggerByIdAndWait,
412
batchTriggerTasks,
513
batchTriggerAndWaitTasks,
614
} from "./shared.js";
15+
import { tracer } from "./tracer.js";
716

817
export const batch = {
918
trigger: batchTriggerById,
1019
triggerAndWait: batchTriggerByIdAndWait,
1120
triggerByTask: batchTriggerTasks,
1221
triggerByTaskAndWait: batchTriggerAndWaitTasks,
22+
retrieve: retrieveBatch,
1323
};
24+
25+
function retrieveBatch(
26+
batchId: string,
27+
requestOptions?: ApiRequestOptions
28+
): ApiPromise<RetrieveBatchResponse> {
29+
const apiClient = apiClientManager.clientOrThrow();
30+
31+
const $requestOptions = mergeRequestOptions(
32+
{
33+
tracer,
34+
name: "batch.retrieve()",
35+
icon: "batch",
36+
attributes: {
37+
batchId: batchId,
38+
...accessoryAttributes({
39+
items: [
40+
{
41+
text: batchId,
42+
variant: "normal",
43+
},
44+
],
45+
style: "codepath",
46+
}),
47+
},
48+
},
49+
requestOptions
50+
);
51+
52+
return apiClient.retrieveBatch(batchId, $requestOptions);
53+
}

references/v3-catalog/src/management.ts

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -261,6 +261,14 @@ async function doBatchTrigger() {
261261
]);
262262

263263
console.log("batch trigger response", response);
264+
265+
const $batch = await batch.retrieve(response.batchId);
266+
267+
console.log("batch", $batch);
268+
269+
const $runs = await runs.list({ batch: response.batchId });
270+
271+
console.log("batch runs", $runs.data);
264272
}
265273

266274
// doRuns().catch(console.error);

0 commit comments

Comments
 (0)