Skip to content

Commit 489cbb3

Browse files
committed
add blink init happy path test
1 parent c2e25da commit 489cbb3

File tree

2 files changed

+69
-1
lines changed

2 files changed

+69
-1
lines changed

packages/blink/src/cli/init.test.ts

Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
import { describe, it, expect } from "bun:test";
22
import { getFilesForTemplate } from "./init";
3+
import { render, BLINK_COMMAND, makeTmpDir, KEY_CODES } from "./lib/terminal";
4+
import { join } from "path";
5+
import { readFile } from "fs/promises";
36

47
const getFile = (files: Record<string, string>, filename: string): string => {
58
const fileContent = files[filename];
@@ -212,3 +215,43 @@ describe("getFilesForTemplate", () => {
212215
});
213216
});
214217
});
218+
219+
describe("init command", () => {
220+
it("scratch template, happy path", async () => {
221+
await using tempDir = await makeTmpDir();
222+
using term = render(`${BLINK_COMMAND} init`, { cwd: tempDir.path });
223+
await term.waitUntil((screen) => screen.includes("Scratch"));
224+
// by default, the first option should be selected. Scratch is second in the list.
225+
expect(term.getScreen()).not.toContain("Basic agent with example tool");
226+
term.write(KEY_CODES.DOWN);
227+
await term.waitUntil((screen) =>
228+
screen.includes("Basic agent with example tool")
229+
);
230+
term.write(KEY_CODES.ENTER);
231+
await term.waitUntil((screen) =>
232+
screen.includes("Which AI provider do you want to use?")
233+
);
234+
term.write(KEY_CODES.ENTER);
235+
await term.waitUntil((screen) =>
236+
screen.includes("Enter your OpenAI API key:")
237+
);
238+
term.write("sk-test-123");
239+
term.write(KEY_CODES.ENTER);
240+
await term.waitUntil((screen) =>
241+
screen.includes("What package manager do you want to use?")
242+
);
243+
const screen = term.getScreen();
244+
expect(screen).toContain("Bun");
245+
expect(screen).toContain("NPM");
246+
expect(screen).toContain("PNPM");
247+
expect(screen).toContain("Yarn");
248+
term.write(KEY_CODES.ENTER);
249+
await term.waitUntil((screen) =>
250+
screen.includes("API key saved to .env.local")
251+
);
252+
await term.waitUntil((screen) => screen.includes("To get started, run:"));
253+
const envFilePath = join(tempDir.path, ".env.local");
254+
const envFileContent = await readFile(envFilePath, "utf-8");
255+
expect(envFileContent.split("\n")).toContain("OPENAI_API_KEY=sk-test-123");
256+
});
257+
});

packages/blink/src/cli/lib/terminal.ts

Lines changed: 26 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,12 @@
11
import {
22
spawn,
33
spawnSync,
4-
ChildProcessWithoutNullStreams,
4+
type ChildProcessWithoutNullStreams,
55
} from "node:child_process";
66
import { Terminal } from "@xterm/headless";
77
import { join } from "path";
8+
import { mkdtemp, rm } from "fs/promises";
9+
import { tmpdir } from "os";
810

911
export interface RenderOptions {
1012
cols?: number;
@@ -218,3 +220,26 @@ export function render(
218220
): TerminalInstance {
219221
return new TerminalInstanceImpl(command, options);
220222
}
223+
224+
export async function makeTmpDir(): Promise<
225+
AsyncDisposable & { path: string }
226+
> {
227+
const dirPath = await mkdtemp(join(tmpdir(), "blink-tmp-"));
228+
return {
229+
path: dirPath,
230+
[Symbol.asyncDispose](): Promise<void> {
231+
return rm(dirPath, { recursive: true });
232+
},
233+
};
234+
}
235+
236+
export const KEY_CODES = {
237+
ENTER: "\r",
238+
TAB: "\t",
239+
BACKSPACE: "\x08",
240+
DELETE: "\x7f",
241+
UP: "\x1b[A",
242+
DOWN: "\x1b[B",
243+
LEFT: "\x1b[D",
244+
RIGHT: "\x1b[C",
245+
} as const;

0 commit comments

Comments
 (0)