Skip to content

Commit

Permalink
C3 e2e (#3483)
Browse files Browse the repository at this point in the history
* fix: ensure that `wrangler init` passes the `name` arg to C3

* e2e clean up for c3 integration testing

* test: add C3 integration test to Wrangler e2e tests
  • Loading branch information
petebacondarwin authored Jun 20, 2023
1 parent 91135e0 commit a9349a8
Show file tree
Hide file tree
Showing 16 changed files with 437 additions and 347 deletions.
5 changes: 5 additions & 0 deletions .changeset/purple-buttons-carry.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"wrangler": patch
---

fix: ensure that the script name is passed through to C3 from `wrangler init`
2 changes: 1 addition & 1 deletion .github/workflows/e2e.yml
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,7 @@ jobs:
run: npm ci

- name: Run builds
run: npm run -w wrangler build
run: npm run build
env:
NODE_ENV: "production"

Expand Down
90 changes: 90 additions & 0 deletions packages/wrangler/e2e/c3-integration.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
import crypto from "node:crypto";
import { existsSync } from "node:fs";
import path from "node:path";
import shellac from "shellac";
import { fetch } from "undici";
import { beforeAll, describe, expect, it } from "vitest";
import { normalizeOutput } from "./helpers/normalize";
import { retry } from "./helpers/retry";
import { makeRoot } from "./helpers/setup";
import { WRANGLER } from "./helpers/wrangler-command";

function matchWorkersDev(stdout: string): string {
return stdout.match(
/https:\/\/smoke-test-worker-.+?\.(.+?\.workers\.dev)/
)?.[1] as string;
}

describe("c3 integration", () => {
let workerName: string;
let workerPath: string;
let workersDev: string | null = null;
let runInRoot: typeof shellac;
let runInWorker: typeof shellac;
let normalize: (str: string) => string;

beforeAll(async () => {
const root = await makeRoot();
runInRoot = shellac.in(root).env(process.env);
workerName = `smoke-test-worker-${crypto.randomBytes(4).toString("hex")}`;
workerPath = path.join(root, workerName);
runInWorker = shellac.in(workerPath).env(process.env);
normalize = (str) =>
normalizeOutput(str, { [workerName]: "smoke-test-worker" });
});

it("init project via c3", async () => {
const pathToC3 = path.resolve(__dirname, "../../create-cloudflare");
const env = {
...process.env,
WRANGLER_C3_COMMAND: `exec ${pathToC3}`,
GIT_AUTHOR_NAME: "test-user",
GIT_AUTHOR_EMAIL: "test-user@cloudflare.com",
GIT_COMMITTER_NAME: "test-user",
GIT_COMMITTER_EMAIL: "test-user@cloudflare.com",
};

await runInRoot.env(env)`$ ${WRANGLER} init ${workerName} --yes`;

expect(existsSync(workerPath)).toBe(true);
});

it("deploy the worker", async () => {
const { stdout, stderr } = await runInWorker`$ ${WRANGLER} deploy`;
expect(normalize(stdout)).toMatchInlineSnapshot(`
"Total Upload: xx KiB / gzip: xx KiB
Uploaded smoke-test-worker (TIMINGS)
Published smoke-test-worker (TIMINGS)
https://smoke-test-worker.SUBDOMAIN.workers.dev
Current Deployment ID: 00000000-0000-0000-0000-000000000000"
`);
expect(stderr).toMatchInlineSnapshot('""');
workersDev = matchWorkersDev(stdout);
const { text } = await retry(
(s) => s.status !== 200,
async () => {
const r = await fetch(`https://${workerName}.${workersDev}`);
return { text: await r.text(), status: r.status };
}
);
expect(text).toMatchInlineSnapshot('"Hello World!"');
});

it("delete the worker", async () => {
const { stdout, stderr } = await runInWorker`$$ ${WRANGLER} delete`;
expect(normalize(stdout)).toMatchInlineSnapshot(`
"? Are you sure you want to delete smoke-test-worker? This action cannot be undone.
🤖 Using default value in non-interactive context: yes
Successfully deleted smoke-test-worker"
`);
expect(stderr).toMatchInlineSnapshot('""');
const { status } = await retry(
(s) => s.status === 200 || s.status === 500,
async () => {
const r = await fetch(`https://${workerName}.${workersDev}`);
return { text: await r.text(), status: r.status };
}
);
expect(status).toBe(404);
});
});
103 changes: 55 additions & 48 deletions packages/wrangler/e2e/deploy.test.ts
Original file line number Diff line number Diff line change
@@ -1,30 +1,42 @@
import crypto from "node:crypto";
import path from "node:path";
import shellac from "shellac";
import { fetch } from "undici";
import { describe, expect, it } from "vitest";
import { beforeAll, describe, expect, it } from "vitest";
import { normalizeOutput } from "./helpers/normalize";
import { retry } from "./helpers/retry";
import { RUN, runIn } from "./helpers/run";
import { dedent, makeRoot, seed } from "./helpers/setup";
import { WRANGLER } from "./helpers/wrangler-command";

function matchWorkersDev(stdout: string): string {
return stdout.match(
/https:\/\/smoke-test-worker-.+?\.(.+?\.workers\.dev)/
)?.[1] as string;
}

describe("deploy", async () => {
const root = await makeRoot();
const workerName = `smoke-test-worker-${crypto
.randomBytes(4)
.toString("hex")}`;
const workerPath = path.join(root, workerName);
describe("deploy", () => {
let workerName: string;
let workerPath: string;
let workersDev: string | null = null;
let runInRoot: typeof shellac;
let runInWorker: typeof shellac;
let normalize: (str: string) => string;

beforeAll(async () => {
const root = await makeRoot();
runInRoot = shellac.in(root).env(process.env);
workerName = `smoke-test-worker-${crypto.randomBytes(4).toString("hex")}`;
workerPath = path.join(root, workerName);
runInWorker = shellac.in(workerPath).env(process.env);
normalize = (str) =>
normalizeOutput(str, { [workerName]: "smoke-test-worker" });
});

it("init worker", async () => {
const { stdout } = await runIn(root, { [workerName]: "smoke-test-worker" })`
$ ${RUN} init --yes --no-delegate-c3 ${workerName}
`;
expect(stdout).toMatchInlineSnapshot(`
const { stdout } =
await runInRoot`$ ${WRANGLER} init --yes --no-delegate-c3 ${workerName}`;

expect(normalize(stdout)).toMatchInlineSnapshot(`
"Using npm as package manager.
✨ Created smoke-test-worker/wrangler.toml
✨ Initialized git repository at smoke-test-worker
Expand All @@ -43,30 +55,29 @@ describe("deploy", async () => {
To publish your Worker to the Internet, run \`npm run deploy\`"
`);
});

it("deploy worker", async () => {
const {
stdout,
stderr,
raw: { stdout: rawStdout },
} = await runIn(workerPath, { [workerName]: "smoke-test-worker" })`
$ ${RUN} deploy
`;
expect(stdout).toMatchInlineSnapshot(`
const { stdout, stderr } = await runInWorker`$ ${WRANGLER} deploy`;
expect(normalize(stdout)).toMatchInlineSnapshot(`
"Total Upload: xx KiB / gzip: xx KiB
Uploaded smoke-test-worker (TIMINGS)
Published smoke-test-worker (TIMINGS)
https://smoke-test-worker.SUBDOMAIN.workers.dev
Current Deployment ID: 00000000-0000-0000-0000-000000000000"
`);
expect(stderr).toMatchInlineSnapshot('""');
workersDev = matchWorkersDev(rawStdout);
workersDev = matchWorkersDev(stdout);

await retry(() =>
expect(
fetch(`https://${workerName}.${workersDev}`).then((r) => r.text())
).resolves.toMatchInlineSnapshot('"Hello World!"')
const { text } = await retry(
(s) => s.status !== 200,
async () => {
const r = await fetch(`https://${workerName}.${workersDev}`);
return { text: await r.text(), status: r.status };
}
);
expect(text).toMatchInlineSnapshot('"Hello World!"');
});

it("modify & deploy worker", async () => {
await seed(workerPath, {
"src/index.ts": dedent`
Expand All @@ -76,46 +87,42 @@ describe("deploy", async () => {
}
}`,
});
const {
stdout,
stderr,
raw: { stdout: rawStdout },
} = await runIn(workerPath, { [workerName]: "smoke-test-worker" })`
$ ${RUN} deploy
`;
expect(stdout).toMatchInlineSnapshot(`
const { stdout, stderr } = await runInWorker`$ ${WRANGLER} deploy`;
expect(normalize(stdout)).toMatchInlineSnapshot(`
"Total Upload: xx KiB / gzip: xx KiB
Uploaded smoke-test-worker (TIMINGS)
Published smoke-test-worker (TIMINGS)
https://smoke-test-worker.SUBDOMAIN.workers.dev
Current Deployment ID: 00000000-0000-0000-0000-000000000000"
`);
expect(stderr).toMatchInlineSnapshot('""');
workersDev = matchWorkersDev(rawStdout);
workersDev = matchWorkersDev(stdout);

await retry(() =>
expect(
fetch(`https://${workerName}.${workersDev}`).then((r) => r.text())
).resolves.toMatchInlineSnapshot('"Updated Worker!"')
const { text } = await retry(
(s) => s.status !== 200 || s.text === "Hello World!",
async () => {
const r = await fetch(`https://${workerName}.${workersDev}`);
return { text: await r.text(), status: r.status };
}
);
expect(text).toMatchInlineSnapshot('"Updated Worker!"');
});

it("delete worker", async () => {
const { stdout, stderr } = await runIn(workerPath, {
[workerName]: "smoke-test-worker",
})`
$ ${RUN} delete
`;
expect(stdout).toMatchInlineSnapshot(`
const { stdout, stderr } = await runInWorker`$ ${WRANGLER} delete`;
expect(normalize(stdout)).toMatchInlineSnapshot(`
"? Are you sure you want to delete smoke-test-worker? This action cannot be undone.
🤖 Using default value in non-interactive context: yes
Successfully deleted smoke-test-worker"
`);
expect(stderr).toMatchInlineSnapshot('""');
await retry(() =>
expect(
fetch(`https://${workerName}.${workersDev}`).then((r) => r.status)
).resolves.toBe(404)
const { status } = await retry(
(s) => s.status === 200 || s.status === 500,
async () => {
const r = await fetch(`https://${workerName}.${workersDev}`);
return { text: await r.text(), status: r.status };
}
);
expect(status).toBe(404);
});
});
Loading

0 comments on commit a9349a8

Please sign in to comment.