praetom 0.1.0 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cli/cli.js +11 -1
- package/dist/cli/cli.js.map +1 -1
- package/dist/cli/commands/connect.d.ts +13 -0
- package/dist/cli/commands/connect.d.ts.map +1 -0
- package/dist/cli/commands/connect.js +106 -0
- package/dist/cli/commands/connect.js.map +1 -0
- package/dist/cli/commands/discover.d.ts.map +1 -1
- package/dist/cli/commands/discover.js +4 -6
- package/dist/cli/commands/discover.js.map +1 -1
- package/dist/cli/commands/features.d.ts.map +1 -1
- package/dist/cli/commands/features.js +65 -49
- package/dist/cli/commands/features.js.map +1 -1
- package/dist/cli/commands/init.d.ts +16 -0
- package/dist/cli/commands/init.d.ts.map +1 -1
- package/dist/cli/commands/init.js +59 -40
- package/dist/cli/commands/init.js.map +1 -1
- package/dist/cli/commands/install.d.ts +20 -0
- package/dist/cli/commands/install.d.ts.map +1 -0
- package/dist/cli/commands/install.js +82 -0
- package/dist/cli/commands/install.js.map +1 -0
- package/dist/cli/commands/login.d.ts +1 -1
- package/dist/cli/commands/login.d.ts.map +1 -1
- package/dist/cli/commands/login.js +59 -45
- package/dist/cli/commands/login.js.map +1 -1
- package/dist/cli/commands/logout.d.ts.map +1 -1
- package/dist/cli/commands/logout.js +10 -10
- package/dist/cli/commands/logout.js.map +1 -1
- package/dist/cli/commands/rotate.d.ts.map +1 -1
- package/dist/cli/commands/rotate.js +29 -23
- package/dist/cli/commands/rotate.js.map +1 -1
- package/dist/cli/commands/status.d.ts.map +1 -1
- package/dist/cli/commands/status.js +38 -12
- package/dist/cli/commands/status.js.map +1 -1
- package/dist/cli/commands/uninstall.d.ts.map +1 -1
- package/dist/cli/commands/uninstall.js +63 -51
- package/dist/cli/commands/uninstall.js.map +1 -1
- package/dist/cli/commands/usage.d.ts.map +1 -1
- package/dist/cli/commands/usage.js +12 -12
- package/dist/cli/commands/usage.js.map +1 -1
- package/dist/cli/commands/whoami.d.ts.map +1 -1
- package/dist/cli/commands/whoami.js +22 -25
- package/dist/cli/commands/whoami.js.map +1 -1
- package/dist/cli/util/api.d.ts +9 -0
- package/dist/cli/util/api.d.ts.map +1 -1
- package/dist/cli/util/api.js +14 -1
- package/dist/cli/util/api.js.map +1 -1
- package/dist/cli/util/output.d.ts +55 -0
- package/dist/cli/util/output.d.ts.map +1 -0
- package/dist/cli/util/output.js +170 -0
- package/dist/cli/util/output.js.map +1 -0
- package/dist/server.d.ts +1 -1
- package/dist/server.d.ts.map +1 -1
- package/dist/server.js +1 -1
- package/dist/server.js.map +1 -1
- package/package.json +12 -4
package/dist/cli/cli.js
CHANGED
|
@@ -1,6 +1,8 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import { Command } from "commander";
|
|
3
3
|
import { initCommand } from "./commands/init.js";
|
|
4
|
+
import { installCommand } from "./commands/install.js";
|
|
5
|
+
import { connectCommand } from "./commands/connect.js";
|
|
4
6
|
import { loginCommand } from "./commands/login.js";
|
|
5
7
|
import { logoutCommand } from "./commands/logout.js";
|
|
6
8
|
import { whoamiCommand } from "./commands/whoami.js";
|
|
@@ -23,8 +25,16 @@ program
|
|
|
23
25
|
.option("--non-interactive", "fail instead of prompting; for automation");
|
|
24
26
|
program
|
|
25
27
|
.command("init")
|
|
26
|
-
.description("
|
|
28
|
+
.description("Set up praetom from zero in the current repository — runs login, connect, and install in one go.")
|
|
27
29
|
.action(() => runCommand(program, initCommand));
|
|
30
|
+
program
|
|
31
|
+
.command("install")
|
|
32
|
+
.description("Open the install pull request for this repository — wires praetom into your source.")
|
|
33
|
+
.action(() => runCommand(program, installCommand));
|
|
34
|
+
program
|
|
35
|
+
.command("connect")
|
|
36
|
+
.description("Grant praetom's GitHub App access to a repository (browser flow). Required before `install`.")
|
|
37
|
+
.action(() => runCommand(program, connectCommand));
|
|
28
38
|
program
|
|
29
39
|
.command("login")
|
|
30
40
|
.description("Open a browser to authenticate this terminal session.")
|
package/dist/cli/cli.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"cli.js","sourceRoot":"","sources":["../../src/cli/cli.ts"],"names":[],"mappings":";AACA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAEpC,OAAO,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AACjD,OAAO,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AACnD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AACnD,OAAO,EACL,kBAAkB,EAClB,mBAAmB,EACnB,mBAAmB,GACpB,MAAM,wBAAwB,CAAC;AAChC,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,gBAAgB,EAAE,MAAM,yBAAyB,CAAC;AAC3D,OAAO,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AAEzD,OAAO,EAAE,WAAW,EAAE,MAAM,qBAAqB,CAAC;AAClD,OAAO,EAAE,UAAU,EAAE,MAAM,eAAe,CAAC;AAE3C,MAAM,OAAO,GAAG,IAAI,OAAO,EAAE,CAAC;AAE9B,OAAO;KACJ,IAAI,CAAC,SAAS,CAAC;KACf,WAAW,CACV,2EAA2E,CAC5E;KACA,OAAO,CAAC,OAAO,EAAE,eAAe,CAAC;KACjC,MAAM,CAAC,oBAAoB,EAAE,wBAAwB,CAAC;KACtD,MAAM,CAAC,qBAAqB,EAAE,yBAAyB,CAAC;KACxD,MAAM,CACL,QAAQ,EACR,6EAA6E,CAC9E;KACA,MAAM,CAAC,mBAAmB,EAAE,2CAA2C,CAAC,CAAC;AAE5E,OAAO;KACJ,OAAO,CAAC,MAAM,CAAC;KACf,WAAW,CACV,
|
|
1
|
+
{"version":3,"file":"cli.js","sourceRoot":"","sources":["../../src/cli/cli.ts"],"names":[],"mappings":";AACA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAEpC,OAAO,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AACjD,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AACnD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AACnD,OAAO,EACL,kBAAkB,EAClB,mBAAmB,EACnB,mBAAmB,GACpB,MAAM,wBAAwB,CAAC;AAChC,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,gBAAgB,EAAE,MAAM,yBAAyB,CAAC;AAC3D,OAAO,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AAEzD,OAAO,EAAE,WAAW,EAAE,MAAM,qBAAqB,CAAC;AAClD,OAAO,EAAE,UAAU,EAAE,MAAM,eAAe,CAAC;AAE3C,MAAM,OAAO,GAAG,IAAI,OAAO,EAAE,CAAC;AAE9B,OAAO;KACJ,IAAI,CAAC,SAAS,CAAC;KACf,WAAW,CACV,2EAA2E,CAC5E;KACA,OAAO,CAAC,OAAO,EAAE,eAAe,CAAC;KACjC,MAAM,CAAC,oBAAoB,EAAE,wBAAwB,CAAC;KACtD,MAAM,CAAC,qBAAqB,EAAE,yBAAyB,CAAC;KACxD,MAAM,CACL,QAAQ,EACR,6EAA6E,CAC9E;KACA,MAAM,CAAC,mBAAmB,EAAE,2CAA2C,CAAC,CAAC;AAE5E,OAAO;KACJ,OAAO,CAAC,MAAM,CAAC;KACf,WAAW,CACV,kGAAkG,CACnG;KACA,MAAM,CAAC,GAAG,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,WAAW,CAAC,CAAC,CAAC;AAElD,OAAO;KACJ,OAAO,CAAC,SAAS,CAAC;KAClB,WAAW,CACV,qFAAqF,CACtF;KACA,MAAM,CAAC,GAAG,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,cAAc,CAAC,CAAC,CAAC;AAErD,OAAO;KACJ,OAAO,CAAC,SAAS,CAAC;KAClB,WAAW,CACV,8FAA8F,CAC/F;KACA,MAAM,CAAC,GAAG,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,cAAc,CAAC,CAAC,CAAC;AAErD,OAAO;KACJ,OAAO,CAAC,OAAO,CAAC;KAChB,WAAW,CAAC,uDAAuD,CAAC;KACpE,MAAM,CAAC,GAAG,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,YAAY,CAAC,CAAC,CAAC;AAEnD,OAAO;KACJ,OAAO,CAAC,QAAQ,CAAC;KACjB,WAAW,CAAC,0CAA0C,CAAC;KACvD,MAAM,CAAC,GAAG,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,aAAa,CAAC,CAAC,CAAC;AAEpD,OAAO;KACJ,OAAO,CAAC,QAAQ,CAAC;KACjB,WAAW,CAAC,yCAAyC,CAAC;KACtD,MAAM,CAAC,GAAG,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,aAAa,CAAC,CAAC,CAAC;AAEpD,OAAO;KACJ,OAAO,CAAC,QAAQ,CAAC;KACjB,WAAW,CAAC,wDAAwD,CAAC;KACrE,MAAM,CAAC,GAAG,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,aAAa,CAAC,CAAC,CAAC;AAEpD,OAAO;KACJ,OAAO,CAAC,OAAO,CAAC;KAChB,WAAW,CAAC,2DAA2D,CAAC;KACxE,MAAM,CAAC,GAAG,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,YAAY,CAAC,CAAC,CAAC;AAEnD,MAAM,QAAQ,GAAG,OAAO;KACrB,OAAO,CAAC,UAAU,CAAC;KACnB,WAAW,CAAC,oCAAoC,CAAC,CAAC;AAErD,QAAQ;KACL,OAAO,CAAC,MAAM,CAAC;KACf,WAAW,CAAC,yCAAyC,CAAC;KACtD,MAAM,CAAC,GAAG,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,mBAAmB,CAAC,CAAC,CAAC;AAE1D,QAAQ;KACL,OAAO,CAAC,YAAY,CAAC;KACrB,WAAW,CAAC,wDAAwD,CAAC;KACrE,MAAM,CAAC,CAAC,IAAY,EAAE,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,CAAC,GAAG,EAAE,EAAE,CAAC,kBAAkB,CAAC,GAAG,EAAE,IAAI,CAAC,CAAC,CAAC,CAAC;AAEzF,QAAQ;KACL,OAAO,CAAC,aAAa,CAAC;KACtB,WAAW,CAAC,4BAA4B,CAAC;KACzC,MAAM,CAAC,CAAC,IAAY,EAAE,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,CAAC,GAAG,EAAE,EAAE,CAAC,mBAAmB,CAAC,GAAG,EAAE,IAAI,CAAC,CAAC,CAAC,CAAC;AAE1F,OAAO;KACJ,OAAO,CAAC,QAAQ,CAAC;KACjB,WAAW,CACV,8EAA8E,CAC/E;KACA,MAAM,CAAC,GAAG,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,aAAa,CAAC,CAAC,CAAC;AAEpD,OAAO;KACJ,OAAO,CAAC,WAAW,CAAC;KACpB,WAAW,CACV,+EAA+E,CAChF;KACA,MAAM,CAAC,GAAG,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,gBAAgB,CAAC,CAAC,CAAC;AAEvD,OAAO;KACJ,OAAO,CAAC,UAAU,CAAC;KACnB,WAAW,CAAC,kDAAkD,CAAC;KAC/D,MAAM,CAAC,GAAG,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,eAAe,CAAC,CAAC,CAAC;AAEtD,6EAA6E;AAC7E,6EAA6E;AAC7E,gCAAgC;AAChC,MAAM,KAAK,GAAG,WAAW,EAAE,CAAC;AAC5B,IAAI,KAAK,EAAE,CAAC;IACV,MAAM,IAAI,GAAG,OAAO,CAAC,IAAI,EAAE,CAAC;IAC5B,IAAI,IAAI,CAAC,MAAM,CAAC,KAAK,SAAS;QAAE,IAAI,CAAC,MAAM,CAAC,GAAG,IAAI,CAAC;IACpD,IAAI,IAAI,CAAC,gBAAgB,CAAC,KAAK,SAAS;QAAE,IAAI,CAAC,gBAAgB,CAAC,GAAG,IAAI,CAAC;AAC1E,CAAC;AAED,OAAO,CAAC,UAAU,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,KAAK,CAAC,CAAC,GAAY,EAAE,EAAE;IACtD,MAAM,GAAG,GAAG,GAAG,YAAY,KAAK,CAAC,CAAC,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC;IAC7D,MAAM,IAAI,GAAG,OAAO,CAAC,IAAI,EAAsB,CAAC;IAChD,IAAI,IAAI,CAAC,IAAI,EAAE,CAAC;QACd,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,SAAS,CAAC,EAAE,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,GAAG,EAAE,CAAC,GAAG,IAAI,CAAC,CAAC;IACzE,CAAC;SAAM,CAAC;QACN,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,YAAY,GAAG,IAAI,CAAC,CAAC;IAC5C,CAAC;IACD,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC,CAAC,CAAC"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import type { RunContext } from "../util/run.js";
|
|
2
|
+
/**
|
|
3
|
+
* `praetom connect` — grant praetom's GitHub App access to a
|
|
4
|
+
* repository. Opens GitHub's App-install screen in the browser, lets
|
|
5
|
+
* the user pick org + repos, and waits for the install callback to
|
|
6
|
+
* fire. Bridges via cli_install_codes — the same shape as `login`'s
|
|
7
|
+
* device-authorization flow but for the GitHub App.
|
|
8
|
+
*
|
|
9
|
+
* Required before `praetom install` can open a pull request — the
|
|
10
|
+
* installer needs a GitHub App installation to authenticate as.
|
|
11
|
+
*/
|
|
12
|
+
export declare function connectCommand(ctx: RunContext): Promise<void>;
|
|
13
|
+
//# sourceMappingURL=connect.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"connect.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/connect.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;AAsBjD;;;;;;;;;GASG;AACH,wBAAsB,cAAc,CAAC,GAAG,EAAE,UAAU,GAAG,OAAO,CAAC,IAAI,CAAC,CAiEnE"}
|
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
import { spawn } from "node:child_process";
|
|
2
|
+
import { apiRequest, NotAuthenticatedError, workspaceQuery, } from "../util/api.js";
|
|
3
|
+
import { colors, logError, result, runTasks } from "../util/output.js";
|
|
4
|
+
/**
|
|
5
|
+
* `praetom connect` — grant praetom's GitHub App access to a
|
|
6
|
+
* repository. Opens GitHub's App-install screen in the browser, lets
|
|
7
|
+
* the user pick org + repos, and waits for the install callback to
|
|
8
|
+
* fire. Bridges via cli_install_codes — the same shape as `login`'s
|
|
9
|
+
* device-authorization flow but for the GitHub App.
|
|
10
|
+
*
|
|
11
|
+
* Required before `praetom install` can open a pull request — the
|
|
12
|
+
* installer needs a GitHub App installation to authenticate as.
|
|
13
|
+
*/
|
|
14
|
+
export async function connectCommand(ctx) {
|
|
15
|
+
if (ctx.nonInteractive) {
|
|
16
|
+
logError(ctx, "praetom connect: --non-interactive set; can't open a browser. Configure the GitHub App via the dashboard for now.");
|
|
17
|
+
process.exit(2);
|
|
18
|
+
}
|
|
19
|
+
let session = null;
|
|
20
|
+
let installationId = null;
|
|
21
|
+
try {
|
|
22
|
+
await runTasks(ctx, [
|
|
23
|
+
{
|
|
24
|
+
title: "Requesting GitHub App install handshake",
|
|
25
|
+
task: async (t) => {
|
|
26
|
+
try {
|
|
27
|
+
session = await apiRequest("/api/cli/repos/connect-start", { method: "POST", query: workspaceQuery(ctx) });
|
|
28
|
+
t.setTitle(`Got install code ${colors.dim(session.install_code.slice(0, 16) + "…")}`);
|
|
29
|
+
}
|
|
30
|
+
catch (e) {
|
|
31
|
+
if (e instanceof NotAuthenticatedError) {
|
|
32
|
+
throw new Error(`${e.message} Run \`praetom login\` first.`);
|
|
33
|
+
}
|
|
34
|
+
throw e;
|
|
35
|
+
}
|
|
36
|
+
},
|
|
37
|
+
},
|
|
38
|
+
{
|
|
39
|
+
title: "Opening GitHub App install in your browser",
|
|
40
|
+
task: (t) => {
|
|
41
|
+
openBrowser(session.install_url);
|
|
42
|
+
t.setTitle(`Opened ${colors.dim("github.com/apps/praetom/installations/new")}`);
|
|
43
|
+
},
|
|
44
|
+
},
|
|
45
|
+
{
|
|
46
|
+
title: "Waiting for you to authorize the install",
|
|
47
|
+
task: async (t) => {
|
|
48
|
+
installationId = await pollUntilConnected(session, ctx, t);
|
|
49
|
+
t.setTitle(`Install complete ${colors.dim(`installation ${installationId}`)}`);
|
|
50
|
+
},
|
|
51
|
+
},
|
|
52
|
+
]);
|
|
53
|
+
}
|
|
54
|
+
catch {
|
|
55
|
+
process.exit(1);
|
|
56
|
+
}
|
|
57
|
+
result(ctx, { ok: true, installationId }, () => {
|
|
58
|
+
process.stdout.write(`\n${colors.green("✓")} GitHub App connected. Run ${colors.bold("praetom install")} next to open the install pull request.\n`);
|
|
59
|
+
});
|
|
60
|
+
}
|
|
61
|
+
async function pollUntilConnected(session, ctx, t) {
|
|
62
|
+
const intervalMs = Math.max(1, session.interval) * 1000;
|
|
63
|
+
const deadline = Date.now() + session.expires_in * 1000;
|
|
64
|
+
while (Date.now() < deadline) {
|
|
65
|
+
await sleep(intervalMs);
|
|
66
|
+
const poll = await apiRequest("/api/cli/repos/connect-poll", {
|
|
67
|
+
method: "POST",
|
|
68
|
+
body: { install_code: session.install_code },
|
|
69
|
+
query: workspaceQuery(ctx),
|
|
70
|
+
});
|
|
71
|
+
if (poll.status === "connected")
|
|
72
|
+
return poll.installation_id;
|
|
73
|
+
if (poll.status === "expired") {
|
|
74
|
+
throw new Error("Install code expired before authorization.");
|
|
75
|
+
}
|
|
76
|
+
if (poll.status === "consumed") {
|
|
77
|
+
throw new Error("Install code already consumed by another `praetom connect`.");
|
|
78
|
+
}
|
|
79
|
+
if (poll.status === "error") {
|
|
80
|
+
throw new Error(poll.error);
|
|
81
|
+
}
|
|
82
|
+
t.setTitle(`Waiting for you to authorize the install ${colors.dim(`(${secondsLeft(deadline)}s left)`)}`);
|
|
83
|
+
}
|
|
84
|
+
throw new Error("Timed out waiting for the install to complete.");
|
|
85
|
+
}
|
|
86
|
+
function openBrowser(url) {
|
|
87
|
+
const platform = process.platform;
|
|
88
|
+
const cmd = platform === "darwin"
|
|
89
|
+
? "open"
|
|
90
|
+
: platform === "win32"
|
|
91
|
+
? "start"
|
|
92
|
+
: "xdg-open";
|
|
93
|
+
try {
|
|
94
|
+
spawn(cmd, [url], { stdio: "ignore", detached: true }).unref();
|
|
95
|
+
}
|
|
96
|
+
catch {
|
|
97
|
+
// ignore — the URL has already been logged for manual paste
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
function sleep(ms) {
|
|
101
|
+
return new Promise((r) => setTimeout(r, ms));
|
|
102
|
+
}
|
|
103
|
+
function secondsLeft(deadline) {
|
|
104
|
+
return Math.max(0, Math.round((deadline - Date.now()) / 1000));
|
|
105
|
+
}
|
|
106
|
+
//# sourceMappingURL=connect.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"connect.js","sourceRoot":"","sources":["../../../src/cli/commands/connect.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,EAAE,MAAM,oBAAoB,CAAC;AAG3C,OAAO,EACL,UAAU,EACV,qBAAqB,EACrB,cAAc,GACf,MAAM,gBAAgB,CAAC;AACxB,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAgBvE;;;;;;;;;GASG;AACH,MAAM,CAAC,KAAK,UAAU,cAAc,CAAC,GAAe;IAClD,IAAI,GAAG,CAAC,cAAc,EAAE,CAAC;QACvB,QAAQ,CACN,GAAG,EACH,mHAAmH,CACpH,CAAC;QACF,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,IAAI,OAAO,GAAgC,IAAI,CAAC;IAChD,IAAI,cAAc,GAAkB,IAAI,CAAC;IAEzC,IAAI,CAAC;QACH,MAAM,QAAQ,CAAC,GAAG,EAAE;YAClB;gBACE,KAAK,EAAE,yCAAyC;gBAChD,IAAI,EAAE,KAAK,EAAE,CAAC,EAAE,EAAE;oBAChB,IAAI,CAAC;wBACH,OAAO,GAAG,MAAM,UAAU,CACxB,8BAA8B,EAC9B,EAAE,MAAM,EAAE,MAAM,EAAE,KAAK,EAAE,cAAc,CAAC,GAAG,CAAC,EAAE,CAC/C,CAAC;wBACF,CAAC,CAAC,QAAQ,CACR,qBAAqB,MAAM,CAAC,GAAG,CAAC,OAAO,CAAC,YAAY,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,GAAG,GAAG,CAAC,EAAE,CAC3E,CAAC;oBACJ,CAAC;oBAAC,OAAO,CAAC,EAAE,CAAC;wBACX,IAAI,CAAC,YAAY,qBAAqB,EAAE,CAAC;4BACvC,MAAM,IAAI,KAAK,CAAC,GAAG,CAAC,CAAC,OAAO,+BAA+B,CAAC,CAAC;wBAC/D,CAAC;wBACD,MAAM,CAAC,CAAC;oBACV,CAAC;gBACH,CAAC;aACF;YACD;gBACE,KAAK,EAAE,4CAA4C;gBACnD,IAAI,EAAE,CAAC,CAAC,EAAE,EAAE;oBACV,WAAW,CAAC,OAAQ,CAAC,WAAW,CAAC,CAAC;oBAClC,CAAC,CAAC,QAAQ,CACR,UAAU,MAAM,CAAC,GAAG,CAAC,2CAA2C,CAAC,EAAE,CACpE,CAAC;gBACJ,CAAC;aACF;YACD;gBACE,KAAK,EAAE,0CAA0C;gBACjD,IAAI,EAAE,KAAK,EAAE,CAAC,EAAE,EAAE;oBAChB,cAAc,GAAG,MAAM,kBAAkB,CAAC,OAAQ,EAAE,GAAG,EAAE,CAAC,CAAC,CAAC;oBAC5D,CAAC,CAAC,QAAQ,CACR,qBAAqB,MAAM,CAAC,GAAG,CAAC,gBAAgB,cAAc,EAAE,CAAC,EAAE,CACpE,CAAC;gBACJ,CAAC;aACF;SACF,CAAC,CAAC;IACL,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,MAAM,CACJ,GAAG,EACH,EAAE,EAAE,EAAE,IAAI,EAAE,cAAc,EAAE,EAC5B,GAAG,EAAE;QACH,OAAO,CAAC,MAAM,CAAC,KAAK,CAClB,KAAK,MAAM,CAAC,KAAK,CAAC,GAAG,CAAC,8BAA8B,MAAM,CAAC,IAAI,CAAC,iBAAiB,CAAC,2CAA2C,CAC9H,CAAC;IACJ,CAAC,CACF,CAAC;AACJ,CAAC;AAED,KAAK,UAAU,kBAAkB,CAC/B,OAA6B,EAC7B,GAAe,EACf,CAAoC;IAEpC,MAAM,UAAU,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,OAAO,CAAC,QAAQ,CAAC,GAAG,IAAI,CAAC;IACxD,MAAM,QAAQ,GAAG,IAAI,CAAC,GAAG,EAAE,GAAG,OAAO,CAAC,UAAU,GAAG,IAAI,CAAC;IACxD,OAAO,IAAI,CAAC,GAAG,EAAE,GAAG,QAAQ,EAAE,CAAC;QAC7B,MAAM,KAAK,CAAC,UAAU,CAAC,CAAC;QACxB,MAAM,IAAI,GAAG,MAAM,UAAU,CAC3B,6BAA6B,EAC7B;YACE,MAAM,EAAE,MAAM;YACd,IAAI,EAAE,EAAE,YAAY,EAAE,OAAO,CAAC,YAAY,EAAE;YAC5C,KAAK,EAAE,cAAc,CAAC,GAAG,CAAC;SAC3B,CACF,CAAC;QACF,IAAI,IAAI,CAAC,MAAM,KAAK,WAAW;YAAE,OAAO,IAAI,CAAC,eAAe,CAAC;QAC7D,IAAI,IAAI,CAAC,MAAM,KAAK,SAAS,EAAE,CAAC;YAC9B,MAAM,IAAI,KAAK,CAAC,4CAA4C,CAAC,CAAC;QAChE,CAAC;QACD,IAAI,IAAI,CAAC,MAAM,KAAK,UAAU,EAAE,CAAC;YAC/B,MAAM,IAAI,KAAK,CAAC,6DAA6D,CAAC,CAAC;QACjF,CAAC;QACD,IAAI,IAAI,CAAC,MAAM,KAAK,OAAO,EAAE,CAAC;YAC5B,MAAM,IAAI,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QAC9B,CAAC;QACD,CAAC,CAAC,QAAQ,CACR,6CAA6C,MAAM,CAAC,GAAG,CAAC,IAAI,WAAW,CAAC,QAAQ,CAAC,SAAS,CAAC,EAAE,CAC9F,CAAC;IACJ,CAAC;IACD,MAAM,IAAI,KAAK,CAAC,gDAAgD,CAAC,CAAC;AACpE,CAAC;AAED,SAAS,WAAW,CAAC,GAAW;IAC9B,MAAM,QAAQ,GAAG,OAAO,CAAC,QAAQ,CAAC;IAClC,MAAM,GAAG,GACP,QAAQ,KAAK,QAAQ;QACnB,CAAC,CAAC,MAAM;QACR,CAAC,CAAC,QAAQ,KAAK,OAAO;YACpB,CAAC,CAAC,OAAO;YACT,CAAC,CAAC,UAAU,CAAC;IACnB,IAAI,CAAC;QACH,KAAK,CAAC,GAAG,EAAE,CAAC,GAAG,CAAC,EAAE,EAAE,KAAK,EAAE,QAAQ,EAAE,QAAQ,EAAE,IAAI,EAAE,CAAC,CAAC,KAAK,EAAE,CAAC;IACjE,CAAC;IAAC,MAAM,CAAC;QACP,4DAA4D;IAC9D,CAAC;AACH,CAAC;AAED,SAAS,KAAK,CAAC,EAAU;IACvB,OAAO,IAAI,OAAO,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,UAAU,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;AAC/C,CAAC;AAED,SAAS,WAAW,CAAC,QAAgB;IACnC,OAAO,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,IAAI,CAAC,KAAK,CAAC,CAAC,QAAQ,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC;AACjE,CAAC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"discover.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/discover.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;
|
|
1
|
+
{"version":3,"file":"discover.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/discover.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;AAGjD,wBAAgB,eAAe,CAAC,GAAG,EAAE,UAAU,GAAG,IAAI,CAerD"}
|
|
@@ -1,15 +1,13 @@
|
|
|
1
|
+
import { logError, result } from "../util/output.js";
|
|
1
2
|
export function discoverCommand(ctx) {
|
|
2
3
|
const message = "praetom discover isn't implemented yet (v0.1). " +
|
|
3
4
|
"Run discovery via your AI coding agent today: praetom's MCP plugin exposes " +
|
|
4
5
|
"`start_discovery` and `accept_discovery_candidates`. From Claude Code, that " +
|
|
5
6
|
"looks like: `@praetom map this repository` then `accept all` once the " +
|
|
6
7
|
"candidates list streams in.";
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
}
|
|
10
|
-
else {
|
|
11
|
-
process.stderr.write(`${message}\n`);
|
|
12
|
-
}
|
|
8
|
+
result(ctx, { ok: false, error: "not_implemented", command: "discover" }, () => {
|
|
9
|
+
logError(ctx, message);
|
|
10
|
+
});
|
|
13
11
|
process.exit(2);
|
|
14
12
|
}
|
|
15
13
|
//# sourceMappingURL=discover.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"discover.js","sourceRoot":"","sources":["../../../src/cli/commands/discover.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"discover.js","sourceRoot":"","sources":["../../../src/cli/commands/discover.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,QAAQ,EAAE,MAAM,EAAE,MAAM,mBAAmB,CAAC;AAErD,MAAM,UAAU,eAAe,CAAC,GAAe;IAC7C,MAAM,OAAO,GACX,iDAAiD;QACjD,6EAA6E;QAC7E,8EAA8E;QAC9E,wEAAwE;QACxE,6BAA6B,CAAC;IAChC,MAAM,CACJ,GAAG,EACH,EAAE,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,iBAAiB,EAAE,OAAO,EAAE,UAAU,EAAE,EAC5D,GAAG,EAAE;QACH,QAAQ,CAAC,GAAG,EAAE,OAAO,CAAC,CAAC;IACzB,CAAC,CACF,CAAC;IACF,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"features.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/features.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;
|
|
1
|
+
{"version":3,"file":"features.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/features.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;AAmCjD,wBAAsB,mBAAmB,CAAC,GAAG,EAAE,UAAU,GAAG,OAAO,CAAC,IAAI,CAAC,CAoCxE;AAED,wBAAsB,mBAAmB,CACvC,GAAG,EAAE,UAAU,EACf,IAAI,EAAE,MAAM,GACX,OAAO,CAAC,IAAI,CAAC,CA4Bf;AAED,wBAAsB,kBAAkB,CACtC,GAAG,EAAE,UAAU,EACf,IAAI,EAAE,MAAM,GACX,OAAO,CAAC,IAAI,CAAC,CAuDf"}
|
|
@@ -1,45 +1,48 @@
|
|
|
1
1
|
import { createInterface } from "node:readline/promises";
|
|
2
2
|
import { apiRequest, workspaceQuery } from "../util/api.js";
|
|
3
|
+
import { colors, logError, logInfo, logSuccess, result } from "../util/output.js";
|
|
3
4
|
export async function featuresListCommand(ctx) {
|
|
4
5
|
const res = await apiRequest("/api/cli/features", {
|
|
5
6
|
query: workspaceQuery(ctx),
|
|
6
7
|
});
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
process.stdout.write(`
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
process.stdout.write(` ${" ".repeat(28)} ${tags.join(" · ")}\n`);
|
|
27
|
-
}
|
|
8
|
+
result(ctx, res, () => {
|
|
9
|
+
if (res.count === 0) {
|
|
10
|
+
logInfo(ctx, `No features in ${colors.dim(res.workspaceSlug)} yet.`);
|
|
11
|
+
return;
|
|
12
|
+
}
|
|
13
|
+
process.stdout.write(`${colors.bold(String(res.count))} ${colors.dim(`feature(s) in ${res.workspaceSlug}:`)}\n\n`);
|
|
14
|
+
for (const f of res.features) {
|
|
15
|
+
const tags = [];
|
|
16
|
+
if (f.instrumentationScore)
|
|
17
|
+
tags.push(`${Math.round(f.instrumentationScore.score * 100)}% instrumented`);
|
|
18
|
+
if (f.activitySignal?.commits_30d != null)
|
|
19
|
+
tags.push(`${f.activitySignal.commits_30d} commits/30d`);
|
|
20
|
+
if (f.criticVerdict)
|
|
21
|
+
tags.push(verdictColor(f.criticVerdict));
|
|
22
|
+
process.stdout.write(` ${colors.bold(f.slug.padEnd(28))} ${colors.cyan(f.event)}\n`);
|
|
23
|
+
if (tags.length > 0)
|
|
24
|
+
process.stdout.write(` ${" ".repeat(28)} ${colors.dim(tags.join(" · "))}\n`);
|
|
25
|
+
}
|
|
26
|
+
});
|
|
28
27
|
}
|
|
29
28
|
export async function featuresShowCommand(ctx, slug) {
|
|
30
29
|
const res = await apiRequest(`/api/cli/features/${encodeURIComponent(slug)}`, { query: workspaceQuery(ctx) });
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
30
|
+
result(ctx, res, () => {
|
|
31
|
+
const f = res.feature;
|
|
32
|
+
process.stdout.write(`${colors.bold(f.slug)} ${colors.dim(`(workspace: ${res.workspaceSlug})`)}\n` +
|
|
33
|
+
`${colors.dim("─".repeat(60))}\n\n` +
|
|
34
|
+
`${f.plainEnglish}\n\n` +
|
|
35
|
+
`${colors.dim(`created ${f.createdAt}`)}\n` +
|
|
36
|
+
(f.signalsRefreshedAt
|
|
37
|
+
? `${colors.dim(`signals ${f.signalsRefreshedAt}`)}\n`
|
|
38
|
+
: "") +
|
|
39
|
+
(f.criticVerdict
|
|
40
|
+
? `${colors.dim("verdict ")}${verdictColor(f.criticVerdict)}\n`
|
|
41
|
+
: "") +
|
|
42
|
+
(f.criticCritique
|
|
43
|
+
? `\n${colors.dim("critique:")}\n ${f.criticCritique}\n`
|
|
44
|
+
: ""));
|
|
45
|
+
});
|
|
43
46
|
}
|
|
44
47
|
export async function featuresAddCommand(ctx, name) {
|
|
45
48
|
const slug = name.trim().toLowerCase();
|
|
@@ -49,8 +52,10 @@ export async function featuresAddCommand(ctx, name) {
|
|
|
49
52
|
if (ctx.nonInteractive) {
|
|
50
53
|
fail(ctx, "praetom features add: --non-interactive set; cannot prompt for description. Use the dashboard for now.");
|
|
51
54
|
}
|
|
55
|
+
// Interactive prompts go through readline directly — they're stdin
|
|
56
|
+
// questions, not status output, so the wrapper doesn't apply.
|
|
52
57
|
const rl = createInterface({ input: process.stdin, output: process.stdout });
|
|
53
|
-
process.stdout.write(`Creating feature \`${slug}\`. Press enter to skip optional fields
|
|
58
|
+
process.stdout.write(`Creating feature \`${colors.bold(slug)}\`. ${colors.dim("Press enter to skip optional fields.")}\n\n`);
|
|
54
59
|
const event = (await rl.question("Event (one sentence — what happens): ")).trim();
|
|
55
60
|
if (!event) {
|
|
56
61
|
rl.close();
|
|
@@ -60,24 +65,35 @@ export async function featuresAddCommand(ctx, name) {
|
|
|
60
65
|
const healthy = (await rl.question("Healthy (optional): ")).trim();
|
|
61
66
|
const incident = (await rl.question("Incident (optional): ")).trim();
|
|
62
67
|
rl.close();
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
68
|
+
let created;
|
|
69
|
+
try {
|
|
70
|
+
created = await apiRequest("/api/cli/features", {
|
|
71
|
+
method: "POST",
|
|
72
|
+
body: { slug, event, description, healthy, incident },
|
|
73
|
+
query: workspaceQuery(ctx),
|
|
74
|
+
});
|
|
75
|
+
}
|
|
76
|
+
catch (e) {
|
|
77
|
+
fail(ctx, e.message);
|
|
71
78
|
}
|
|
72
|
-
|
|
79
|
+
result(ctx, created, () => {
|
|
80
|
+
logSuccess(ctx, `Created feature \`${colors.bold(created.slug)}\`.`);
|
|
81
|
+
});
|
|
82
|
+
}
|
|
83
|
+
function verdictColor(verdict) {
|
|
84
|
+
const v = verdict.toLowerCase();
|
|
85
|
+
if (v.includes("good") || v.includes("pass") || v.includes("ok"))
|
|
86
|
+
return colors.green(verdict);
|
|
87
|
+
if (v.includes("warn") || v.includes("partial"))
|
|
88
|
+
return colors.yellow(verdict);
|
|
89
|
+
if (v.includes("fail") || v.includes("bad"))
|
|
90
|
+
return colors.red(verdict);
|
|
91
|
+
return colors.dim(verdict);
|
|
73
92
|
}
|
|
74
93
|
function fail(ctx, message) {
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
}
|
|
78
|
-
else {
|
|
79
|
-
process.stderr.write(`${message}\n`);
|
|
80
|
-
}
|
|
94
|
+
result(ctx, { ok: false, error: message }, () => {
|
|
95
|
+
logError(ctx, message);
|
|
96
|
+
});
|
|
81
97
|
process.exit(1);
|
|
82
98
|
}
|
|
83
99
|
//# sourceMappingURL=features.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"features.js","sourceRoot":"","sources":["../../../src/cli/commands/features.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AAGzD,OAAO,EAAE,UAAU,EAAE,cAAc,EAAE,MAAM,gBAAgB,CAAC;
|
|
1
|
+
{"version":3,"file":"features.js","sourceRoot":"","sources":["../../../src/cli/commands/features.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,3 +1,19 @@
|
|
|
1
1
|
import type { RunContext } from "../util/run.js";
|
|
2
|
+
/**
|
|
3
|
+
* `praetom init` — the umbrella command. Walks the customer through
|
|
4
|
+
* the four steps that turn a fresh repository into a praetom-
|
|
5
|
+
* instrumented service:
|
|
6
|
+
*
|
|
7
|
+
* 1. Authenticate the terminal (login if needed)
|
|
8
|
+
* 2. Connect the GitHub App to the current repository (if not already)
|
|
9
|
+
* 3. Install the runtime (open the install PR)
|
|
10
|
+
* 4. (Defer feature definition; the install PR landing is the
|
|
11
|
+
* meaningful state change. Customers run `praetom features add`
|
|
12
|
+
* or use the MCP plugin's discovery flow afterwards.)
|
|
13
|
+
*
|
|
14
|
+
* Each step is its own task in the listr2 list, so the user sees
|
|
15
|
+
* progress streaming. Steps that are already done are marked
|
|
16
|
+
* "skipped" inline.
|
|
17
|
+
*/
|
|
2
18
|
export declare function initCommand(ctx: RunContext): Promise<void>;
|
|
3
19
|
//# sourceMappingURL=init.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"init.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/init.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"init.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/init.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;AAsBjD;;;;;;;;;;;;;;;GAeG;AACH,wBAAsB,WAAW,CAAC,GAAG,EAAE,UAAU,GAAG,OAAO,CAAC,IAAI,CAAC,CA2DhE"}
|
|
@@ -1,52 +1,71 @@
|
|
|
1
|
-
import { apiRequest, NotAuthenticatedError, workspaceQuery } from "../util/api.js";
|
|
1
|
+
import { apiRequest, NotAuthenticatedError, workspaceQuery, } from "../util/api.js";
|
|
2
|
+
import { readAuth } from "../util/auth-file.js";
|
|
2
3
|
import { resolveRepo } from "../util/git.js";
|
|
4
|
+
import { logError, result } from "../util/output.js";
|
|
5
|
+
import { loginCommand } from "./login.js";
|
|
6
|
+
import { connectCommand } from "./connect.js";
|
|
7
|
+
import { installCommand } from "./install.js";
|
|
8
|
+
/**
|
|
9
|
+
* `praetom init` — the umbrella command. Walks the customer through
|
|
10
|
+
* the four steps that turn a fresh repository into a praetom-
|
|
11
|
+
* instrumented service:
|
|
12
|
+
*
|
|
13
|
+
* 1. Authenticate the terminal (login if needed)
|
|
14
|
+
* 2. Connect the GitHub App to the current repository (if not already)
|
|
15
|
+
* 3. Install the runtime (open the install PR)
|
|
16
|
+
* 4. (Defer feature definition; the install PR landing is the
|
|
17
|
+
* meaningful state change. Customers run `praetom features add`
|
|
18
|
+
* or use the MCP plugin's discovery flow afterwards.)
|
|
19
|
+
*
|
|
20
|
+
* Each step is its own task in the listr2 list, so the user sees
|
|
21
|
+
* progress streaming. Steps that are already done are marked
|
|
22
|
+
* "skipped" inline.
|
|
23
|
+
*/
|
|
3
24
|
export async function initCommand(ctx) {
|
|
4
25
|
const repo = await resolveRepo(ctx.repo);
|
|
5
26
|
if (!repo) {
|
|
6
|
-
|
|
27
|
+
logError(ctx, "Couldn't determine the repository. Pass --repo owner/name, or run this from inside a git checkout with a GitHub remote.");
|
|
28
|
+
process.exit(1);
|
|
7
29
|
}
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
let
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
fail(ctx, e.message);
|
|
30
|
+
const slug = `${repo.owner}/${repo.name}`;
|
|
31
|
+
// Step 1: auth. If a token is already on disk + works, skip the login flow.
|
|
32
|
+
const existing = await readAuth();
|
|
33
|
+
let needsLogin = !existing;
|
|
34
|
+
if (existing) {
|
|
35
|
+
try {
|
|
36
|
+
await apiRequest("/api/cli/me");
|
|
37
|
+
}
|
|
38
|
+
catch (e) {
|
|
39
|
+
if (e instanceof NotAuthenticatedError)
|
|
40
|
+
needsLogin = true;
|
|
41
|
+
else
|
|
42
|
+
throw e;
|
|
22
43
|
}
|
|
23
|
-
throw e;
|
|
24
44
|
}
|
|
25
|
-
if (
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
repo: `${repo.owner}/${repo.name}`,
|
|
29
|
-
prUrl: result.prUrl,
|
|
30
|
-
prNumber: result.prNumber,
|
|
31
|
-
branch: result.branch,
|
|
32
|
-
framework: result.framework,
|
|
33
|
-
}) + "\n");
|
|
34
|
-
return;
|
|
45
|
+
if (needsLogin) {
|
|
46
|
+
// Defer to the login command's own listr presentation.
|
|
47
|
+
await loginCommand(ctx);
|
|
35
48
|
}
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
49
|
+
// Step 2: GitHub App connection. Check before triggering the browser.
|
|
50
|
+
let connected = false;
|
|
51
|
+
try {
|
|
52
|
+
const r = await apiRequest(`/api/cli/repos/check?owner=${encodeURIComponent(repo.owner)}&name=${encodeURIComponent(repo.name)}`, { query: workspaceQuery(ctx) });
|
|
53
|
+
connected = r.connected;
|
|
54
|
+
}
|
|
55
|
+
catch {
|
|
56
|
+
// Endpoint may not exist yet; assume not connected and let
|
|
57
|
+
// connect handle the rest. Worst case we open the browser
|
|
58
|
+
// unnecessarily.
|
|
59
|
+
connected = false;
|
|
46
60
|
}
|
|
47
|
-
|
|
48
|
-
|
|
61
|
+
if (!connected) {
|
|
62
|
+
await connectCommand(ctx);
|
|
49
63
|
}
|
|
50
|
-
|
|
64
|
+
// Step 3: install. Hands off to installCommand which has its own
|
|
65
|
+
// listr presentation.
|
|
66
|
+
await installCommand(ctx);
|
|
67
|
+
result(ctx, { ok: true, repo: slug }, () => {
|
|
68
|
+
// installCommand already printed its success box; nothing more.
|
|
69
|
+
});
|
|
51
70
|
}
|
|
52
71
|
//# sourceMappingURL=init.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"init.js","sourceRoot":"","sources":["../../../src/cli/commands/init.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"init.js","sourceRoot":"","sources":["../../../src/cli/commands/init.ts"],"names":[],"mappings":"AAGA,OAAO,EACL,UAAU,EACV,qBAAqB,EACrB,cAAc,GACf,MAAM,gBAAgB,CAAC;AACxB,OAAO,EAAE,QAAQ,EAAE,MAAM,sBAAsB,CAAC;AAChD,OAAO,EAAE,WAAW,EAAE,MAAM,gBAAgB,CAAC;AAC7C,OAAO,EAAU,QAAQ,EAAE,MAAM,EAAY,MAAM,mBAAmB,CAAC;AACvE,OAAO,EAAE,YAAY,EAAE,MAAM,YAAY,CAAC;AAC1C,OAAO,EAAE,cAAc,EAAE,MAAM,cAAc,CAAC;AAC9C,OAAO,EAAE,cAAc,EAAwB,MAAM,cAAc,CAAC;AAWpE;;;;;;;;;;;;;;;GAeG;AACH,MAAM,CAAC,KAAK,UAAU,WAAW,CAAC,GAAe;IAC/C,MAAM,IAAI,GAAG,MAAM,WAAW,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;IACzC,IAAI,CAAC,IAAI,EAAE,CAAC;QACV,QAAQ,CACN,GAAG,EACH,yHAAyH,CAC1H,CAAC;QACF,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,MAAM,IAAI,GAAG,GAAG,IAAI,CAAC,KAAK,IAAI,IAAI,CAAC,IAAI,EAAE,CAAC;IAE1C,4EAA4E;IAC5E,MAAM,QAAQ,GAAG,MAAM,QAAQ,EAAE,CAAC;IAClC,IAAI,UAAU,GAAG,CAAC,QAAQ,CAAC;IAC3B,IAAI,QAAQ,EAAE,CAAC;QACb,IAAI,CAAC;YACH,MAAM,UAAU,CAAa,aAAa,CAAC,CAAC;QAC9C,CAAC;QAAC,OAAO,CAAC,EAAE,CAAC;YACX,IAAI,CAAC,YAAY,qBAAqB;gBAAE,UAAU,GAAG,IAAI,CAAC;;gBACrD,MAAM,CAAC,CAAC;QACf,CAAC;IACH,CAAC;IAED,IAAI,UAAU,EAAE,CAAC;QACf,uDAAuD;QACvD,MAAM,YAAY,CAAC,GAAG,CAAC,CAAC;IAC1B,CAAC;IAED,sEAAsE;IACtE,IAAI,SAAS,GAAG,KAAK,CAAC;IACtB,IAAI,CAAC;QACH,MAAM,CAAC,GAAG,MAAM,UAAU,CACxB,8BAA8B,kBAAkB,CAAC,IAAI,CAAC,KAAK,CAAC,SAAS,kBAAkB,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,EACpG,EAAE,KAAK,EAAE,cAAc,CAAC,GAAG,CAAC,EAAE,CAC/B,CAAC;QACF,SAAS,GAAG,CAAC,CAAC,SAAS,CAAC;IAC1B,CAAC;IAAC,MAAM,CAAC;QACP,2DAA2D;QAC3D,0DAA0D;QAC1D,iBAAiB;QACjB,SAAS,GAAG,KAAK,CAAC;IACpB,CAAC;IAED,IAAI,CAAC,SAAS,EAAE,CAAC;QACf,MAAM,cAAc,CAAC,GAAG,CAAC,CAAC;IAC5B,CAAC;IAED,iEAAiE;IACjE,sBAAsB;IACtB,MAAM,cAAc,CAAC,GAAG,CAAC,CAAC;IAE1B,MAAM,CACJ,GAAG,EACH,EAAE,EAAE,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,EACxB,GAAG,EAAE;QACH,gEAAgE;IAClE,CAAC,CACF,CAAC;AACJ,CAAC"}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import type { RunContext } from "../util/run.js";
|
|
2
|
+
export interface InstallResponse {
|
|
3
|
+
ok: true;
|
|
4
|
+
prUrl: string;
|
|
5
|
+
prNumber: number;
|
|
6
|
+
branch: string;
|
|
7
|
+
framework: string;
|
|
8
|
+
}
|
|
9
|
+
/**
|
|
10
|
+
* `praetom install` — open the install pull request for the current
|
|
11
|
+
* repository. Wires `praetom` into the customer's source: adds the
|
|
12
|
+
* dependency to package.json and creates the framework-specific boot
|
|
13
|
+
* wrapper (instrumentation.ts for Next.js, server-entry edits for
|
|
14
|
+
* Express/Fastify, etc.).
|
|
15
|
+
*
|
|
16
|
+
* Was named `praetom init` until we split that verb out as the
|
|
17
|
+
* orchestrator command. The server endpoint is still /api/cli/install.
|
|
18
|
+
*/
|
|
19
|
+
export declare function installCommand(ctx: RunContext): Promise<void>;
|
|
20
|
+
//# sourceMappingURL=install.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"install.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/install.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;AASjD,MAAM,WAAW,eAAe;IAC9B,EAAE,EAAE,IAAI,CAAC;IACT,KAAK,EAAE,MAAM,CAAC;IACd,QAAQ,EAAE,MAAM,CAAC;IACjB,MAAM,EAAE,MAAM,CAAC;IACf,SAAS,EAAE,MAAM,CAAC;CACnB;AAED;;;;;;;;;GASG;AACH,wBAAsB,cAAc,CAAC,GAAG,EAAE,UAAU,GAAG,OAAO,CAAC,IAAI,CAAC,CAiFnE"}
|