inflight-cli 1.1.4 → 2.0.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/commands/login.js +10 -9
- package/dist/commands/logout.js +0 -1
- package/dist/commands/preview.js +2 -3
- package/dist/commands/reset.d.ts +1 -0
- package/dist/commands/reset.js +17 -0
- package/dist/commands/setup.d.ts +1 -0
- package/dist/commands/setup.js +168 -0
- package/dist/commands/share.d.ts +6 -1
- package/dist/commands/share.js +44 -13
- package/dist/commands/vercel.d.ts +2 -0
- package/dist/commands/vercel.js +169 -0
- package/dist/commands/workspace.js +2 -4
- package/dist/commands/workspaces.d.ts +4 -0
- package/dist/commands/workspaces.js +81 -0
- package/dist/index.js +20 -3
- package/dist/lib/api.d.ts +12 -0
- package/dist/lib/api.js +17 -0
- package/dist/lib/config.d.ts +12 -2
- package/dist/lib/config.js +29 -19
- package/dist/lib/framework.d.ts +17 -0
- package/dist/lib/framework.js +154 -0
- package/dist/lib/skill.d.ts +5 -0
- package/dist/lib/skill.js +22 -0
- package/dist/lib/vercel.d.ts +21 -11
- package/dist/lib/vercel.js +107 -83
- package/dist/providers/vercel.d.ts +6 -0
- package/dist/providers/vercel.js +67 -55
- package/package.json +3 -2
package/dist/index.js
CHANGED
|
@@ -3,15 +3,25 @@ import { Command } from "commander";
|
|
|
3
3
|
import updateNotifier from "update-notifier";
|
|
4
4
|
import { loginCommand } from "./commands/login.js";
|
|
5
5
|
import { shareCommand } from "./commands/share.js";
|
|
6
|
-
import { workspaceCommand } from "./commands/workspace.js";
|
|
7
6
|
import { logoutCommand } from "./commands/logout.js";
|
|
7
|
+
import { resetCommand } from "./commands/reset.js";
|
|
8
|
+
import { workspacesCommand } from "./commands/workspaces.js";
|
|
9
|
+
import { registerVercelCommand } from "./commands/vercel.js";
|
|
10
|
+
import { setupCommand } from "./commands/setup.js";
|
|
8
11
|
import pkg from "../package.json" with { type: "json" };
|
|
9
12
|
const { version } = pkg;
|
|
10
13
|
updateNotifier({ pkg }).notify();
|
|
11
14
|
const program = new Command();
|
|
12
15
|
program.name("inflight").description("Get feedback directly on your staging URL").version(version);
|
|
16
|
+
program.command("setup").description("Set up Inflight in your project").action(setupCommand);
|
|
13
17
|
program.command("login").description("Authenticate with your Inflight account").action(loginCommand);
|
|
14
|
-
program
|
|
18
|
+
program
|
|
19
|
+
.command("share")
|
|
20
|
+
.description("Get feedback on your staging URL")
|
|
21
|
+
.option("--url <url>", "Staging URL (skips provider selection)")
|
|
22
|
+
.option("--workspace <id>", "Workspace ID (skips workspace selection)")
|
|
23
|
+
.option("--json", "Output result as JSON")
|
|
24
|
+
.action((opts) => shareCommand(opts));
|
|
15
25
|
// program
|
|
16
26
|
// .command("preview")
|
|
17
27
|
// .description("Preview a live component from your code")
|
|
@@ -19,6 +29,13 @@ program.command("share").description("Get feedback on your staging URL").action(
|
|
|
19
29
|
// .option("--scope <mode>", "Skip scope prompt: branch, uncommitted, staged")
|
|
20
30
|
// .option("--no-open", "Don't open result in browser")
|
|
21
31
|
// .action((opts) => previewCommand(opts));
|
|
22
|
-
program
|
|
32
|
+
program
|
|
33
|
+
.command("workspaces")
|
|
34
|
+
.description("List, select, or set your workspaces")
|
|
35
|
+
.option("--json", "Output as JSON")
|
|
36
|
+
.option("--set <id>", "Set the active workspace")
|
|
37
|
+
.action((opts) => workspacesCommand(opts));
|
|
38
|
+
registerVercelCommand(program);
|
|
23
39
|
program.command("logout").description("Disconnect your Inflight account").action(logoutCommand);
|
|
40
|
+
program.command("reset").description("Clear all Inflight auth and config").action(resetCommand);
|
|
24
41
|
program.parse();
|
package/dist/lib/api.d.ts
CHANGED
|
@@ -2,6 +2,7 @@ import type { GitInfo } from "./git.js";
|
|
|
2
2
|
export interface Workspace {
|
|
3
3
|
id: string;
|
|
4
4
|
name: string;
|
|
5
|
+
widgetId: string;
|
|
5
6
|
}
|
|
6
7
|
export interface CreateVersionResult {
|
|
7
8
|
projectId: string;
|
|
@@ -19,3 +20,14 @@ export declare function apiCreateVersion(opts: {
|
|
|
19
20
|
stagingUrl: string;
|
|
20
21
|
gitInfo: GitInfo;
|
|
21
22
|
}): Promise<CreateVersionResult>;
|
|
23
|
+
export interface WidgetLocationResult {
|
|
24
|
+
file: string | null;
|
|
25
|
+
insertAfter: string | null;
|
|
26
|
+
framework: string | null;
|
|
27
|
+
confidence: "high" | "low";
|
|
28
|
+
}
|
|
29
|
+
export declare function apiDetectWidgetLocation(opts: {
|
|
30
|
+
apiKey: string;
|
|
31
|
+
fileTree: string[];
|
|
32
|
+
fileContents: Record<string, string>;
|
|
33
|
+
}): Promise<WidgetLocationResult>;
|
package/dist/lib/api.js
CHANGED
|
@@ -26,3 +26,20 @@ export async function apiCreateVersion(opts) {
|
|
|
26
26
|
}
|
|
27
27
|
return res.json();
|
|
28
28
|
}
|
|
29
|
+
export async function apiDetectWidgetLocation(opts) {
|
|
30
|
+
const res = await fetch(`${API_URL}/api/cli/detect-widget-location`, {
|
|
31
|
+
method: "POST",
|
|
32
|
+
headers: {
|
|
33
|
+
"Content-Type": "application/json",
|
|
34
|
+
Authorization: `Bearer ${opts.apiKey}`,
|
|
35
|
+
},
|
|
36
|
+
body: JSON.stringify({
|
|
37
|
+
fileTree: opts.fileTree,
|
|
38
|
+
fileContents: opts.fileContents,
|
|
39
|
+
}),
|
|
40
|
+
});
|
|
41
|
+
if (!res.ok) {
|
|
42
|
+
return { file: null, insertAfter: null, framework: null, confidence: "low" };
|
|
43
|
+
}
|
|
44
|
+
return res.json();
|
|
45
|
+
}
|
package/dist/lib/config.d.ts
CHANGED
|
@@ -7,5 +7,15 @@ export declare function clearGlobalAuth(): void;
|
|
|
7
7
|
export interface WorkspaceConfig {
|
|
8
8
|
workspaceId: string;
|
|
9
9
|
}
|
|
10
|
-
export declare function readWorkspaceConfig(
|
|
11
|
-
export declare function
|
|
10
|
+
export declare function readWorkspaceConfig(): WorkspaceConfig | null;
|
|
11
|
+
export declare function clearWorkspaceConfig(): void;
|
|
12
|
+
export declare function writeWorkspaceConfig(config: WorkspaceConfig): void;
|
|
13
|
+
export interface VercelConfig {
|
|
14
|
+
teamId: string;
|
|
15
|
+
teamName: string;
|
|
16
|
+
projectId: string;
|
|
17
|
+
projectName: string;
|
|
18
|
+
}
|
|
19
|
+
export declare function readVercelConfig(): VercelConfig | null;
|
|
20
|
+
export declare function writeVercelConfig(config: VercelConfig): void;
|
|
21
|
+
export declare function clearVercelConfig(): void;
|
package/dist/lib/config.js
CHANGED
|
@@ -30,35 +30,45 @@ export function clearGlobalAuth() {
|
|
|
30
30
|
unlinkSync(AUTH_FILE);
|
|
31
31
|
}
|
|
32
32
|
}
|
|
33
|
-
// ---
|
|
34
|
-
const WORKSPACE_FILE = "
|
|
35
|
-
export function readWorkspaceConfig(
|
|
36
|
-
|
|
37
|
-
if (!existsSync(file))
|
|
33
|
+
// --- Workspace config (global, persists across directories) ---
|
|
34
|
+
const WORKSPACE_FILE = join(getGlobalConfigDir(), "workspace.json");
|
|
35
|
+
export function readWorkspaceConfig() {
|
|
36
|
+
if (!existsSync(WORKSPACE_FILE))
|
|
38
37
|
return null;
|
|
39
38
|
try {
|
|
40
|
-
return JSON.parse(readFileSync(
|
|
39
|
+
return JSON.parse(readFileSync(WORKSPACE_FILE, "utf-8"));
|
|
41
40
|
}
|
|
42
41
|
catch {
|
|
43
42
|
return null;
|
|
44
43
|
}
|
|
45
44
|
}
|
|
46
|
-
export function
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
45
|
+
export function clearWorkspaceConfig() {
|
|
46
|
+
if (existsSync(WORKSPACE_FILE)) {
|
|
47
|
+
unlinkSync(WORKSPACE_FILE);
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
export function writeWorkspaceConfig(config) {
|
|
51
|
+
mkdirSync(getGlobalConfigDir(), { recursive: true });
|
|
52
|
+
writeFileSync(WORKSPACE_FILE, JSON.stringify(config, null, 2), { mode: 0o600 });
|
|
51
53
|
}
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
54
|
+
// --- Vercel config (global, persists across directories) ---
|
|
55
|
+
const VERCEL_FILE = join(getGlobalConfigDir(), "vercel.json");
|
|
56
|
+
export function readVercelConfig() {
|
|
57
|
+
if (!existsSync(VERCEL_FILE))
|
|
58
|
+
return null;
|
|
55
59
|
try {
|
|
56
|
-
|
|
57
|
-
if (!contents.split("\n").some((line) => line.trim() === entry)) {
|
|
58
|
-
writeFileSync(gitignorePath, contents + (contents.endsWith("\n") ? "" : "\n") + entry + "\n");
|
|
59
|
-
}
|
|
60
|
+
return JSON.parse(readFileSync(VERCEL_FILE, "utf-8"));
|
|
60
61
|
}
|
|
61
62
|
catch {
|
|
62
|
-
|
|
63
|
+
return null;
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
export function writeVercelConfig(config) {
|
|
67
|
+
mkdirSync(getGlobalConfigDir(), { recursive: true });
|
|
68
|
+
writeFileSync(VERCEL_FILE, JSON.stringify(config, null, 2), { mode: 0o600 });
|
|
69
|
+
}
|
|
70
|
+
export function clearVercelConfig() {
|
|
71
|
+
if (existsSync(VERCEL_FILE)) {
|
|
72
|
+
unlinkSync(VERCEL_FILE);
|
|
63
73
|
}
|
|
64
74
|
}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Gathers a lightweight file tree and candidate file contents for AI detection.
|
|
3
|
+
* Scans cwd and common monorepo subdirectories.
|
|
4
|
+
*/
|
|
5
|
+
export declare function gatherProjectContext(cwd: string): {
|
|
6
|
+
fileTree: string[];
|
|
7
|
+
fileContents: Record<string, string>;
|
|
8
|
+
};
|
|
9
|
+
/**
|
|
10
|
+
* Returns true if any candidate file in the project already has the Inflight widget script.
|
|
11
|
+
*/
|
|
12
|
+
export declare function hasInflightWidget(cwd: string): boolean;
|
|
13
|
+
/**
|
|
14
|
+
* Inserts the script tag into a file at the specified location.
|
|
15
|
+
* Returns the file path that was modified, or null if insertion failed.
|
|
16
|
+
*/
|
|
17
|
+
export declare function insertWidgetScript(cwd: string, file: string, insertAfter: string, widgetId: string): string | null;
|
|
@@ -0,0 +1,154 @@
|
|
|
1
|
+
import { existsSync, readFileSync, writeFileSync, readdirSync, statSync } from "fs";
|
|
2
|
+
import { join, relative } from "path";
|
|
3
|
+
/** File patterns that are likely layout/root files where a script tag belongs */
|
|
4
|
+
const CANDIDATE_PATTERNS = [
|
|
5
|
+
"package.json",
|
|
6
|
+
"index.html",
|
|
7
|
+
"app/layout.tsx",
|
|
8
|
+
"app/layout.jsx",
|
|
9
|
+
"src/app/layout.tsx",
|
|
10
|
+
"src/app/layout.jsx",
|
|
11
|
+
"pages/_document.tsx",
|
|
12
|
+
"pages/_document.jsx",
|
|
13
|
+
"src/pages/_document.tsx",
|
|
14
|
+
"src/pages/_document.jsx",
|
|
15
|
+
"app/root.tsx",
|
|
16
|
+
"app/root.jsx",
|
|
17
|
+
"src/app.html",
|
|
18
|
+
"nuxt.config.ts",
|
|
19
|
+
"nuxt.config.js",
|
|
20
|
+
"src/layouts/Layout.astro",
|
|
21
|
+
"src/layouts/BaseLayout.astro",
|
|
22
|
+
];
|
|
23
|
+
/**
|
|
24
|
+
* Gathers a lightweight file tree and candidate file contents for AI detection.
|
|
25
|
+
* Scans cwd and common monorepo subdirectories.
|
|
26
|
+
*/
|
|
27
|
+
export function gatherProjectContext(cwd) {
|
|
28
|
+
const fileTree = [];
|
|
29
|
+
const fileContents = {};
|
|
30
|
+
const dirsToScan = [cwd];
|
|
31
|
+
// If monorepo, add common subdirectories
|
|
32
|
+
for (const dir of ["apps", "packages", "projects", "services", "libs"]) {
|
|
33
|
+
const baseDir = join(cwd, dir);
|
|
34
|
+
if (!existsSync(baseDir))
|
|
35
|
+
continue;
|
|
36
|
+
try {
|
|
37
|
+
for (const entry of readdirSync(baseDir)) {
|
|
38
|
+
const fullPath = join(baseDir, entry);
|
|
39
|
+
if (statSync(fullPath).isDirectory()) {
|
|
40
|
+
dirsToScan.push(fullPath);
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
catch {
|
|
45
|
+
continue;
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
for (const dir of dirsToScan) {
|
|
49
|
+
// Add shallow file listing (1 level deep + key subdirs)
|
|
50
|
+
try {
|
|
51
|
+
for (const entry of readdirSync(dir)) {
|
|
52
|
+
fileTree.push(relative(cwd, join(dir, entry)));
|
|
53
|
+
}
|
|
54
|
+
// Also list key subdirectories
|
|
55
|
+
for (const sub of ["app", "src", "src/app", "src/layouts", "pages", "src/pages"]) {
|
|
56
|
+
const subDir = join(dir, sub);
|
|
57
|
+
if (!existsSync(subDir))
|
|
58
|
+
continue;
|
|
59
|
+
for (const entry of readdirSync(subDir)) {
|
|
60
|
+
fileTree.push(relative(cwd, join(subDir, entry)));
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
catch {
|
|
65
|
+
continue;
|
|
66
|
+
}
|
|
67
|
+
// Read candidate files
|
|
68
|
+
for (const pattern of CANDIDATE_PATTERNS) {
|
|
69
|
+
const filePath = join(dir, pattern);
|
|
70
|
+
const relPath = relative(cwd, filePath);
|
|
71
|
+
if (existsSync(filePath) && !fileContents[relPath]) {
|
|
72
|
+
try {
|
|
73
|
+
const content = readFileSync(filePath, "utf-8");
|
|
74
|
+
// Truncate large files to save tokens
|
|
75
|
+
fileContents[relPath] = content.length > 3000 ? content.slice(0, 3000) + "\n... (truncated)" : content;
|
|
76
|
+
}
|
|
77
|
+
catch {
|
|
78
|
+
continue;
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
// Also check for astro layouts dynamically
|
|
83
|
+
const layoutsDir = join(dir, "src", "layouts");
|
|
84
|
+
if (existsSync(layoutsDir)) {
|
|
85
|
+
try {
|
|
86
|
+
for (const f of readdirSync(layoutsDir).filter((f) => f.endsWith(".astro"))) {
|
|
87
|
+
const filePath = join(layoutsDir, f);
|
|
88
|
+
const relPath = relative(cwd, filePath);
|
|
89
|
+
if (!fileContents[relPath]) {
|
|
90
|
+
const content = readFileSync(filePath, "utf-8");
|
|
91
|
+
fileContents[relPath] = content.length > 3000 ? content.slice(0, 3000) + "\n... (truncated)" : content;
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
catch {
|
|
96
|
+
// skip
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
return { fileTree, fileContents };
|
|
101
|
+
}
|
|
102
|
+
/**
|
|
103
|
+
* Returns true if any candidate file in the project already has the Inflight widget script.
|
|
104
|
+
*/
|
|
105
|
+
export function hasInflightWidget(cwd) {
|
|
106
|
+
const { fileContents } = gatherProjectContext(cwd);
|
|
107
|
+
return Object.values(fileContents).some((content) => content.includes("inflight.co/widget.js"));
|
|
108
|
+
}
|
|
109
|
+
/**
|
|
110
|
+
* Inserts the script tag into a file at the specified location.
|
|
111
|
+
* Returns the file path that was modified, or null if insertion failed.
|
|
112
|
+
*/
|
|
113
|
+
export function insertWidgetScript(cwd, file, insertAfter, widgetId) {
|
|
114
|
+
try {
|
|
115
|
+
const filePath = join(cwd, file);
|
|
116
|
+
const content = readFileSync(filePath, "utf-8");
|
|
117
|
+
if (content.includes("inflight.co/widget.js")) {
|
|
118
|
+
return file; // Already present
|
|
119
|
+
}
|
|
120
|
+
const isJsx = file.endsWith(".tsx") || file.endsWith(".jsx");
|
|
121
|
+
const tag = isJsx
|
|
122
|
+
? `<script src="https://www.inflight.co/widget.js" data-workspace="${widgetId}" async />`
|
|
123
|
+
: `<script src="https://www.inflight.co/widget.js" data-workspace="${widgetId}" async></script>`;
|
|
124
|
+
let newContent;
|
|
125
|
+
if (insertAfter === "</body>") {
|
|
126
|
+
const lines = content.split("\n");
|
|
127
|
+
const bodyIdx = lines.findIndex((line) => line.includes("</body>"));
|
|
128
|
+
const bodyIndent = bodyIdx >= 0 ? (lines[bodyIdx].match(/^(\s*)/)?.[1] ?? "") : "";
|
|
129
|
+
// Use indentation of the nearest non-empty sibling line before </body>
|
|
130
|
+
let tagIndent = bodyIndent + "\t"; // fallback: one tab deeper than </body>
|
|
131
|
+
for (let i = bodyIdx - 1; i >= 0; i--) {
|
|
132
|
+
if (lines[i].trim()) {
|
|
133
|
+
tagIndent = lines[i].match(/^(\s*)/)?.[1] ?? tagIndent;
|
|
134
|
+
break;
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
newContent = content.replace("</body>", `${tagIndent}${tag}\n${bodyIndent}</body>`);
|
|
138
|
+
}
|
|
139
|
+
else {
|
|
140
|
+
const markerLine = content.split("\n").find((line) => line.includes(insertAfter));
|
|
141
|
+
const indent = markerLine?.match(/^(\s*)/)?.[1] ?? "";
|
|
142
|
+
const markerIndex = content.indexOf(insertAfter);
|
|
143
|
+
if (markerIndex === -1)
|
|
144
|
+
return null;
|
|
145
|
+
const insertPos = markerIndex + insertAfter.length;
|
|
146
|
+
newContent = content.slice(0, insertPos) + "\n" + indent + tag + content.slice(insertPos);
|
|
147
|
+
}
|
|
148
|
+
writeFileSync(filePath, newContent);
|
|
149
|
+
return file;
|
|
150
|
+
}
|
|
151
|
+
catch {
|
|
152
|
+
return null;
|
|
153
|
+
}
|
|
154
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import { exec } from "child_process";
|
|
2
|
+
import { promisify } from "util";
|
|
3
|
+
import { existsSync } from "fs";
|
|
4
|
+
import { join } from "path";
|
|
5
|
+
import { homedir } from "os";
|
|
6
|
+
const execAsync = promisify(exec);
|
|
7
|
+
/**
|
|
8
|
+
* Installs the Inflight skill for all detected AI agents using the skills CLI.
|
|
9
|
+
* Skips if already installed. Non-fatal — setup continues even if this fails.
|
|
10
|
+
*/
|
|
11
|
+
export async function installSkill() {
|
|
12
|
+
if (existsSync(join(homedir(), ".claude", "skills", "inflight", "SKILL.md"))) {
|
|
13
|
+
return true;
|
|
14
|
+
}
|
|
15
|
+
try {
|
|
16
|
+
await execAsync("npx skills add inflightsoftware/skills -y -g");
|
|
17
|
+
return true;
|
|
18
|
+
}
|
|
19
|
+
catch {
|
|
20
|
+
return false;
|
|
21
|
+
}
|
|
22
|
+
}
|
package/dist/lib/vercel.d.ts
CHANGED
|
@@ -1,9 +1,16 @@
|
|
|
1
|
-
|
|
2
|
-
export declare function
|
|
3
|
-
/**
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
1
|
+
/** Ensures the Vercel CLI is available — installs globally if missing. */
|
|
2
|
+
export declare function ensureVercelCli(log?: (msg: string) => void): Promise<boolean>;
|
|
3
|
+
/**
|
|
4
|
+
* Gets a valid Vercel token. Refreshes silently via `vercel whoami` if expired.
|
|
5
|
+
* Does NOT prompt for login — returns null if no valid token available.
|
|
6
|
+
*/
|
|
7
|
+
export declare function getVercelToken(): string | null;
|
|
8
|
+
/**
|
|
9
|
+
* Ensures a valid Vercel auth token is available.
|
|
10
|
+
* Checks existing token → refreshes if expired → opens browser login if needed.
|
|
11
|
+
* For interactive commands only.
|
|
12
|
+
*/
|
|
13
|
+
export declare function ensureVercelAuth(): Promise<string | null>;
|
|
7
14
|
export interface VercelTeam {
|
|
8
15
|
id: string;
|
|
9
16
|
name: string;
|
|
@@ -13,8 +20,6 @@ export interface VercelProject {
|
|
|
13
20
|
id: string;
|
|
14
21
|
name: string;
|
|
15
22
|
}
|
|
16
|
-
export declare function getVercelTeams(): Promise<VercelTeam[]>;
|
|
17
|
-
export declare function getVercelProjects(teamId: string): Promise<VercelProject[]>;
|
|
18
23
|
export interface VercelDeployment {
|
|
19
24
|
url: string;
|
|
20
25
|
branch: string | null;
|
|
@@ -22,12 +27,17 @@ export interface VercelDeployment {
|
|
|
22
27
|
commitMessage: string | null;
|
|
23
28
|
createdAt: number;
|
|
24
29
|
}
|
|
30
|
+
export declare function getVercelTeams(token: string): Promise<VercelTeam[]>;
|
|
31
|
+
export declare function getVercelProjects(token: string, teamId: string): Promise<VercelProject[]>;
|
|
25
32
|
/**
|
|
26
33
|
* Fetches the branch alias URL (stable, auto-updates with each push).
|
|
27
34
|
* Returns null if no deployment exists for this branch.
|
|
28
35
|
*/
|
|
29
|
-
export declare function getBranchAliasUrl(
|
|
36
|
+
export declare function getBranchAliasUrl(token: string, teamId: string, projectId: string, branch: string | null): Promise<string | null>;
|
|
30
37
|
/**
|
|
31
|
-
* Fetches recent deployments for
|
|
38
|
+
* Fetches recent deployments for a project.
|
|
32
39
|
*/
|
|
33
|
-
export declare function getRecentDeployments(
|
|
40
|
+
export declare function getRecentDeployments(token: string, teamId: string, projectId: string, opts?: {
|
|
41
|
+
limit?: number;
|
|
42
|
+
branch?: string;
|
|
43
|
+
}): Promise<VercelDeployment[]>;
|