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/web/app/lib/add-ci.server.ts

43 lines2,124 bytesCodeBlame
1/**
2 * "Add CI": a starter workflow for a repository that has no checks, worked
3 * out from what is at its root (lib/starter-workflow.ts), committed on a
4 * new branch as the person asking and opened as their pull request. Its
5 * runs then become the repository's checks, and it can be required.
6 */
7import type { RepoPath, User } from "@g1t/contracts";
8
9import { repos, work } from "./services.server";
10import { STARTER_PATH, freeBranch, starterDescription, starterWorkflow } from "./starter-workflow";
11
12export type AddedCi = { number: number };
13
14export async function addCi(user: User, path: RepoPath): Promise<{ ok: true; value: AddedCi } | { ok: false; message: string }> {
15 const repo = await repos.get(path, user);
16 if (!repo.ok) return { ok: false, message: repo.error.message };
17 const defaultBranch = repo.value.defaultBranch;
18 const [root, branches] = await Promise.all([repos.tree(path, user, null, ""), repos.branches(path, user)]);
19 if (!root.ok) return { ok: false, message: root.error.message };
20 if (!root.value.head) return { ok: false, message: `${defaultBranch} has no commits yet. Push a first commit, then add CI.` };
21 const names = root.value.entries.map((entry) => entry.name);
22 const packageJson = names.includes("package.json")
23 ? await repos.blob(path, user, defaultBranch, "package.json").then((found) => (found.ok ? found.value.text : null))
24 : null;
25 const { yaml, stacks } = starterWorkflow({ names, packageJson }, defaultBranch);
26 const branch = freeBranch(branches.ok ? branches.value.map((known) => known.name) : []);
27 const committed = await repos.commitFile(path, user, {
28 branch,
29 path: STARTER_PATH,
30 content: yaml,
31 message: "Add CI workflow",
32 });
33 if (!committed.ok) return { ok: false, message: committed.error.message };
34 const opened = await work.openPull(user, path, {
35 branch,
36 title: "Add CI",
37 body: starterDescription(stacks, defaultBranch),
38 agent: user.username,
39 runtime: "external",
40 });
41 if (!opened.ok) return { ok: false, message: opened.error.message };
42 return { ok: true, value: { number: opened.value.number } };
43}