flagon-io/g1t

public

Where people and agents ship software together. The open-source git platform for the whole job: issues, agents, checks and deploys to the edge.

g1t/apps/sudo/app/lib/sales-actions.server.ts

55 lines2,100 bytesCodeBlame
1/**
2 * Changes to a workspace's sales record: its stage, owner and next step,
3 * and notes. Not money, so no confirmation step; still POSTs from sudo's
4 * own pages only (the worker checks), each recorded with who made it.
5 */
6import { data, redirect } from "react-router";
7
8import { fields, parseSales, parseSalesNote, text } from "./forms";
9import type { ActionData } from "./review";
10import { admin } from "./services.server";
11import type { Staff } from "./staff";
12
13export const SALES_INTENTS = new Set(["sales", "note"]);
14
15function failed(section: string, error: string, values?: Record<string, string>) {
16 return data<ActionData>({ error, section, values }, { status: 422 });
17}
18
19/** Unexpected trouble from billing, as a message for the form. */
20function reason(error: unknown): string {
21 return error instanceof Error ? error.message : "Billing did not answer.";
22}
23
24export async function salesAction(form: FormData, staff: Staff, workspace: string, path: string) {
25 const intent = text(form, "intent");
26 const back = (done: string, anchor: string) => redirect(`${path}?done=${done}#${anchor}`);
27
28 if (intent === "sales") {
29 const values = fields(form, "stage", "owner", "nextStep", "nextAt");
30 const parsed = parseSales(form);
31 if (!parsed.ok) return failed("sales", parsed.error, values);
32 try {
33 const result = await admin.setSales(workspace, parsed.value, staff.email);
34 if (!result.ok) return failed("sales", result.error.message, values);
35 } catch (error) {
36 return failed("sales", reason(error), values);
37 }
38 return back("sales", "sales");
39 }
40
41 if (intent === "note") {
42 const values = fields(form, "text");
43 const note = parseSalesNote(values.text);
44 if (!note.ok) return failed("note", note.error, values);
45 try {
46 const result = await admin.addNote(workspace, note.value, staff.email);
47 if (!result.ok) return failed("note", result.error.message, values);
48 } catch (error) {
49 return failed("note", reason(error), values);
50 }
51 return back("note", "notes");
52 }
53
54 return failed("top", "Unknown action.");
55}