Skip to content

Commit dc182d5

Browse files
committed
Use formAction consistently to differentiate submissions
1 parent a738281 commit dc182d5

File tree

1 file changed

+72
-52
lines changed
  • apps/webapp/app/routes/_app.orgs.$organizationSlug.projects.$projectParam.env.$envParam.test.tasks.$taskParam

1 file changed

+72
-52
lines changed

apps/webapp/app/routes/_app.orgs.$organizationSlug.projects.$projectParam.env.$envParam.test.tasks.$taskParam/route.tsx

Lines changed: 72 additions & 52 deletions
Original file line numberDiff line numberDiff line change
@@ -74,8 +74,6 @@ import { DeleteTaskRunTemplateData, RunTemplateData } from "~/v3/taskRunTemplate
7474
import { Dialog, DialogContent, DialogHeader, DialogTrigger } from "~/components/primitives/Dialog";
7575
import { DialogClose, DialogDescription } from "@radix-ui/react-dialog";
7676
import { FormButtons } from "~/components/primitives/FormButtons";
77-
import { toast } from "sonner";
78-
import { ToastUI } from "~/components/primitives/Toast";
7977

8078
export const loader = async ({ request, params }: LoaderFunctionArgs) => {
8179
const userId = await requireUserId(request);
@@ -118,7 +116,7 @@ export const loader = async ({ request, params }: LoaderFunctionArgs) => {
118116

119117
export const action: ActionFunction = async ({ request, params }) => {
120118
const userId = await requireUserId(request);
121-
const { organizationSlug, projectParam, envParam, taskParam } = v3TaskParamsSchema.parse(params);
119+
const { organizationSlug, projectParam, envParam } = v3TaskParamsSchema.parse(params);
122120

123121
const project = await findProjectBySlug(organizationSlug, projectParam, userId);
124122
if (!project) {
@@ -136,19 +134,23 @@ export const action: ActionFunction = async ({ request, params }) => {
136134

137135
// Handle run template creation
138136
if (formAction === "create-template") {
139-
const runTemplateData = parse(formData, { schema: RunTemplateData });
140-
if (!runTemplateData.value) {
141-
return json(runTemplateData.error);
137+
const submission = parse(formData, { schema: RunTemplateData });
138+
if (!submission.value) {
139+
return json({
140+
...submission,
141+
formAction,
142+
});
142143
}
143144

144145
const templateService = new TaskRunTemplateService();
145146
try {
146-
await templateService.call(environment, runTemplateData.value);
147+
const template = await templateService.call(environment, submission.value);
147148

148149
return json({
150+
...submission,
149151
success: true,
152+
templateLabel: template.label,
150153
formAction,
151-
message: `Template "${runTemplateData.value.label}" created successfully`,
152154
});
153155
} catch (e) {
154156
logger.error("Failed to create template", { error: e instanceof Error ? e.message : e });
@@ -161,17 +163,20 @@ export const action: ActionFunction = async ({ request, params }) => {
161163
const submission = parse(formData, { schema: DeleteTaskRunTemplateData });
162164

163165
if (!submission.value) {
164-
return json(submission);
166+
return json({
167+
...submission,
168+
formAction,
169+
});
165170
}
166171

167172
const deleteService = new DeleteTaskRunTemplateService();
168173
try {
169174
await deleteService.call(environment, submission.value.templateId);
170175

171176
return json({
177+
...submission,
172178
success: true,
173179
formAction,
174-
message: `Template deleted successfully`,
175180
});
176181
} catch (e) {
177182
logger.error("Failed to delete template", { error: e instanceof Error ? e.message : e });
@@ -182,7 +187,10 @@ export const action: ActionFunction = async ({ request, params }) => {
182187
const submission = parse(formData, { schema: TestTaskData });
183188

184189
if (!submission.value) {
185-
return json(submission);
190+
return json({
191+
...submission,
192+
formAction,
193+
});
186194
}
187195

188196
if (environment.archivedAt) {
@@ -320,7 +328,16 @@ function StandardTaskForm({
320328
const { value, replace } = useSearchParams();
321329
const tab = value("tab");
322330

323-
const lastSubmission = useActionData();
331+
const submit = useSubmit();
332+
const actionData = useActionData<typeof action>();
333+
const lastSubmission =
334+
actionData &&
335+
typeof actionData === "object" &&
336+
"formAction" in actionData &&
337+
actionData.formAction === "run-standard"
338+
? actionData
339+
: undefined;
340+
324341
const lastRun = runs[0];
325342

326343
const [defaultPayloadJson, setDefaultPayloadJson] = useState<string>(
@@ -364,7 +381,6 @@ function StandardTaskForm({
364381

365382
const [showTemplateCreatedSuccessMessage, setShowTemplateCreatedSuccessMessage] = useState(false);
366383

367-
const fetcher = useFetcher();
368384
const [
369385
form,
370386
{
@@ -388,21 +404,14 @@ function StandardTaskForm({
388404
] = useForm({
389405
id: "test-task",
390406
// TODO: type this
391-
lastSubmission:
392-
lastSubmission &&
393-
typeof lastSubmission === "object" &&
394-
"formAction" in lastSubmission &&
395-
lastSubmission.formAction !== "create-template" &&
396-
lastSubmission.formAction !== "delete-template"
397-
? (lastSubmission as any)
398-
: undefined,
407+
lastSubmission: lastSubmission as any,
399408
onSubmit(event, { formData }) {
400409
event.preventDefault();
401410

402411
formData.set(payload.name, currentPayloadJson.current);
403412
formData.set(metadata.name, currentMetadataJson.current);
404413

405-
fetcher.submit(formData, { method: "POST" });
414+
submit(formData, { method: "POST" });
406415
},
407416
onValidate({ formData }) {
408417
return parse(formData, { schema: TestTaskData });
@@ -758,6 +767,8 @@ function StandardTaskForm({
758767
variant="primary/medium"
759768
LeadingIcon={BeakerIcon}
760769
shortcut={{ key: "enter", modifiers: ["mod"], enabledOnInputElements: true }}
770+
name="formAction"
771+
value="run-standard"
761772
>
762773
Run test
763774
</Button>
@@ -787,7 +798,6 @@ function ScheduledTaskForm({
787798
allowArbitraryQueues: boolean;
788799
}) {
789800
const environment = useEnvironment();
790-
const lastSubmission = useActionData();
791801

792802
const lastRun = runs[0];
793803

@@ -824,6 +834,15 @@ function ScheduledTaskForm({
824834
paused: q.paused,
825835
}));
826836

837+
const actionData = useActionData<typeof action>();
838+
const lastSubmission =
839+
actionData &&
840+
typeof actionData === "object" &&
841+
"formAction" in actionData &&
842+
actionData.formAction === "run-scheduled"
843+
? actionData
844+
: undefined;
845+
827846
const [
828847
form,
829848
{
@@ -848,14 +867,7 @@ function ScheduledTaskForm({
848867
] = useForm({
849868
id: "test-task-scheduled",
850869
// TODO: type this
851-
lastSubmission:
852-
lastSubmission &&
853-
typeof lastSubmission === "object" &&
854-
"formAction" in lastSubmission &&
855-
lastSubmission.formAction !== "create-template" &&
856-
lastSubmission.formAction !== "delete-template"
857-
? (lastSubmission as any)
858-
: undefined,
870+
lastSubmission: lastSubmission as any,
859871
onValidate({ formData }) {
860872
return parse(formData, { schema: TestTaskData });
861873
},
@@ -1264,6 +1276,8 @@ function ScheduledTaskForm({
12641276
variant="primary/medium"
12651277
LeadingIcon={BeakerIcon}
12661278
shortcut={{ key: "enter", modifiers: ["mod"], enabledOnInputElements: true }}
1279+
name="formAction"
1280+
value="run-scheduled"
12671281
>
12681282
Run test
12691283
</Button>
@@ -1340,17 +1354,17 @@ function RunTemplatesPopover({
13401354
const [isDeleteDialogOpen, setIsDeleteDialogOpen] = useState(false);
13411355
const [templateIdToDelete, setTemplateIdToDelete] = useState<string | undefined>();
13421356

1343-
const lastSubmission = useActionData<typeof action>();
1357+
const actionData = useActionData<typeof action>();
1358+
const lastSubmission =
1359+
actionData &&
1360+
typeof actionData === "object" &&
1361+
"formAction" in actionData &&
1362+
actionData.formAction === "delete-template"
1363+
? actionData
1364+
: undefined;
13441365

13451366
useEffect(() => {
1346-
if (
1347-
lastSubmission &&
1348-
typeof lastSubmission === "object" &&
1349-
"formAction" in lastSubmission &&
1350-
"success" in lastSubmission &&
1351-
lastSubmission.formAction === "delete-template" &&
1352-
lastSubmission.success === true
1353-
) {
1367+
if (lastSubmission && "success" in lastSubmission && lastSubmission.success === true) {
13541368
setIsDeleteDialogOpen(false);
13551369
}
13561370
}, [lastSubmission]);
@@ -1454,7 +1468,7 @@ function RunTemplatesPopover({
14541468
}}
14551469
className="absolute -left-1/2 top-full z-10 mt-1 flex min-w-max max-w-64 items-center gap-1 rounded border border-charcoal-700 bg-background-bright px-2 py-1 text-xs shadow-md outline-none before:absolute before:-top-2 before:left-1/2 before:-translate-x-1/2 before:border-4 before:border-transparent before:border-b-charcoal-700 before:content-[''] after:absolute after:-top-[7px] after:left-1/2 after:-translate-x-1/2 after:border-4 after:border-transparent after:border-b-background-bright after:content-['']"
14561470
>
1457-
<CheckCircleIcon className="h-4 w-4 shrink-0 text-success" /> Template created
1471+
<CheckCircleIcon className="h-4 w-4 shrink-0 text-success" /> Template saved
14581472
successfully
14591473
</motion.div>
14601474
)}
@@ -1475,12 +1489,17 @@ function RunTemplatesPopover({
14751489
Cancel
14761490
</Button>
14771491
<Form method="post" {...deleteForm.props}>
1478-
<input type="hidden" name="formAction" value="delete-template" />
14791492
<input
14801493
{...conform.input(templateId, { type: "hidden" })}
14811494
value={templateIdToDelete || ""}
14821495
/>
1483-
<Button type="submit" variant="danger/medium" LeadingIcon={TrashIcon}>
1496+
<Button
1497+
type="submit"
1498+
variant="danger/medium"
1499+
LeadingIcon={TrashIcon}
1500+
name="formAction"
1501+
value="delete-template"
1502+
>
14841503
Delete
14851504
</Button>
14861505
</Form>
@@ -1521,17 +1540,17 @@ function CreateTemplateModal({
15211540
const submit = useSubmit();
15221541
const [isModalOpen, setIsModalOpen] = useState(false);
15231542

1524-
const lastSubmission = useActionData<typeof action>();
1543+
const actionData = useActionData<typeof action>();
1544+
const lastSubmission =
1545+
actionData &&
1546+
typeof actionData === "object" &&
1547+
"formAction" in actionData &&
1548+
actionData.formAction === "create-template"
1549+
? actionData
1550+
: undefined;
15251551

15261552
useEffect(() => {
1527-
if (
1528-
lastSubmission &&
1529-
typeof lastSubmission === "object" &&
1530-
"formAction" in lastSubmission &&
1531-
"success" in lastSubmission &&
1532-
lastSubmission.formAction === "create-template" &&
1533-
lastSubmission.success === true
1534-
) {
1553+
if (lastSubmission && "success" in lastSubmission && lastSubmission.success === true) {
15351554
setIsModalOpen(false);
15361555
setShowCreatedSuccessMessage(true);
15371556
setTimeout(() => {
@@ -1564,6 +1583,7 @@ function CreateTemplateModal({
15641583
},
15651584
] = useForm({
15661585
id: "save-template",
1586+
lastSubmission: lastSubmission as any,
15671587
onSubmit(event, { formData }) {
15681588
event.preventDefault();
15691589

0 commit comments

Comments
 (0)