Skip to content

g1t/apps/web/app/lib/milestones.server.ts

35 lines1,708 bytesCodeBlame

Pick any line to see why it is the way it is: the commit, the pull request and issue it came from, and what the agent was thinking.

Teams and CODEOWNERS, labels and milestones, dependency updates, the security suite, and a clearer top bar1// The forms of the milestones pages: create, edit, close or reopen, delete.
2// Each needs the Triage role, which work checks again.
3
4import type { MilestoneResult } from "../components/milestones";
5import { refusal } from "./access.server";
6import { work } from "./services.server";
7import { assertSameOrigin, requireUser } from "./session.server";
8
9type Context = Parameters<typeof refusal>[0];
10type RepoParams = Parameters<typeof refusal>[1];
11
12export async function milestoneAction(request: Request, params: RepoParams, context: Context): Promise<MilestoneResult> {
13 assertSameOrigin(request);
14 const user = requireUser(context, request);
15 const form = await request.formData();
16 const intent = String(form.get("intent") ?? "");
17 const number = Number(form.get("number")) || undefined;
Merge membership: owners, org roles, GitHub's repo roles, privileges, 2FA18 const refused = await refusal(context, params, "manage_labels");
Teams and CODEOWNERS, labels and milestones, dependency updates, the security suite, and a clearer top bar19 if (refused) return { intent, number, error: refused };
20 const path = { namespace: params.owner ?? "", name: params.repo ?? "" };
21 const text = (key: string) => (form.has(key) ? String(form.get(key) ?? "") : undefined);
22 if (intent === "delete") {
23 const deleted = await work.deleteMilestone(user, path, number ?? 0);
24 return deleted.ok ? { intent, number } : { intent, number, error: deleted.error.message };
25 }
26 const state = form.get("state");
27 const saved = await work.saveMilestone(user, path, {
28 number: intent === "create" ? undefined : number,
29 title: text("title"),
30 description: text("description"),
31 dueOn: text("dueOn"),
32 state: state === "open" || state === "closed" ? state : undefined,
33 });
34 return saved.ok ? { intent, number: saved.value.number } : { intent, number, error: saved.error.message };
35}

This file's history is long; its oldest lines are credited to the oldest commit read.