Skip to content

Commit

Permalink
WIP entrypoints
Browse files Browse the repository at this point in the history
  • Loading branch information
GregBrimble committed Mar 9, 2024
1 parent 1235d48 commit 6a5ec8e
Show file tree
Hide file tree
Showing 14 changed files with 127 additions and 43 deletions.
46 changes: 30 additions & 16 deletions packages/wrangler/src/__tests__/configuration.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -937,6 +937,7 @@ describe("normalizeAndValidateConfig()", () => {
binding: "SERVICE_BINDING_1",
service: "SERVICE_TYPE_1",
environment: "SERVICE_BINDING_ENVIRONMENT_1",
entrypoint: "SERVICE_BINDING_ENVIRONMENT_1",
},
],
analytics_engine_datasets: [
Expand Down Expand Up @@ -2465,6 +2466,17 @@ describe("normalizeAndValidateConfig()", () => {
service: 456,
environment: "SERVICE_BINDING_ENVIRONMENT_1",
},
{
binding: "SERVICE_BINDING_1",
service: "SERVICE_BINDING_SERVICE_1",
environment: "SERVICE_BINDING_ENVIRONMENT_1",
entrypoint: 123,
},
{
binding: "SERVICE_BINDING_1",
service: "SERVICE_BINDING_SERVICE_1",
entrypoint: 123,
},
],
} as unknown as RawConfig,
undefined,
Expand All @@ -2478,22 +2490,24 @@ describe("normalizeAndValidateConfig()", () => {
"
`);
expect(diagnostics.renderErrors()).toMatchInlineSnapshot(`
"Processing wrangler configuration:
- \\"services[0]\\" bindings should have a string \\"binding\\" field but got {}.
- \\"services[0]\\" bindings should have a string \\"service\\" field but got {}.
- \\"services[1]\\" bindings should have a string \\"service\\" field but got {\\"binding\\":\\"SERVICE_BINDING_1\\"}.
- \\"services[2]\\" bindings should have a string \\"binding\\" field but got {\\"binding\\":123,\\"service\\":456}.
- \\"services[2]\\" bindings should have a string \\"service\\" field but got {\\"binding\\":123,\\"service\\":456}.
- \\"services[3]\\" bindings should have a string \\"binding\\" field but got {\\"binding\\":123,\\"service\\":456,\\"environment\\":789}.
- \\"services[3]\\" bindings should have a string \\"service\\" field but got {\\"binding\\":123,\\"service\\":456,\\"environment\\":789}.
- \\"services[3]\\" bindings should have a string \\"environment\\" field but got {\\"binding\\":123,\\"service\\":456,\\"environment\\":789}.
- \\"services[4]\\" bindings should have a string \\"service\\" field but got {\\"binding\\":\\"SERVICE_BINDING_1\\",\\"service\\":456,\\"environment\\":789}.
- \\"services[4]\\" bindings should have a string \\"environment\\" field but got {\\"binding\\":\\"SERVICE_BINDING_1\\",\\"service\\":456,\\"environment\\":789}.
- \\"services[5]\\" bindings should have a string \\"binding\\" field but got {\\"binding\\":123,\\"service\\":\\"SERVICE_BINDING_SERVICE_1\\",\\"environment\\":789}.
- \\"services[5]\\" bindings should have a string \\"environment\\" field but got {\\"binding\\":123,\\"service\\":\\"SERVICE_BINDING_SERVICE_1\\",\\"environment\\":789}.
- \\"services[6]\\" bindings should have a string \\"binding\\" field but got {\\"binding\\":123,\\"service\\":456,\\"environment\\":\\"SERVICE_BINDING_ENVIRONMENT_1\\"}.
- \\"services[6]\\" bindings should have a string \\"service\\" field but got {\\"binding\\":123,\\"service\\":456,\\"environment\\":\\"SERVICE_BINDING_ENVIRONMENT_1\\"}."
`);
"Processing wrangler configuration:
- \\"services[0]\\" bindings should have a string \\"binding\\" field but got {}.
- \\"services[0]\\" bindings should have a string \\"service\\" field but got {}.
- \\"services[1]\\" bindings should have a string \\"service\\" field but got {\\"binding\\":\\"SERVICE_BINDING_1\\"}.
- \\"services[2]\\" bindings should have a string \\"binding\\" field but got {\\"binding\\":123,\\"service\\":456}.
- \\"services[2]\\" bindings should have a string \\"service\\" field but got {\\"binding\\":123,\\"service\\":456}.
- \\"services[3]\\" bindings should have a string \\"binding\\" field but got {\\"binding\\":123,\\"service\\":456,\\"environment\\":789}.
- \\"services[3]\\" bindings should have a string \\"service\\" field but got {\\"binding\\":123,\\"service\\":456,\\"environment\\":789}.
- \\"services[3]\\" bindings should have a string \\"environment\\" field but got {\\"binding\\":123,\\"service\\":456,\\"environment\\":789}.
- \\"services[4]\\" bindings should have a string \\"service\\" field but got {\\"binding\\":\\"SERVICE_BINDING_1\\",\\"service\\":456,\\"environment\\":789}.
- \\"services[4]\\" bindings should have a string \\"environment\\" field but got {\\"binding\\":\\"SERVICE_BINDING_1\\",\\"service\\":456,\\"environment\\":789}.
- \\"services[5]\\" bindings should have a string \\"binding\\" field but got {\\"binding\\":123,\\"service\\":\\"SERVICE_BINDING_SERVICE_1\\",\\"environment\\":789}.
- \\"services[5]\\" bindings should have a string \\"environment\\" field but got {\\"binding\\":123,\\"service\\":\\"SERVICE_BINDING_SERVICE_1\\",\\"environment\\":789}.
- \\"services[6]\\" bindings should have a string \\"binding\\" field but got {\\"binding\\":123,\\"service\\":456,\\"environment\\":\\"SERVICE_BINDING_ENVIRONMENT_1\\"}.
- \\"services[6]\\" bindings should have a string \\"service\\" field but got {\\"binding\\":123,\\"service\\":456,\\"environment\\":\\"SERVICE_BINDING_ENVIRONMENT_1\\"}.
- \\"services[7]\\" bindings should have a string \\"entrypoint\\" field but got {\\"binding\\":\\"SERVICE_BINDING_1\\",\\"service\\":\\"SERVICE_BINDING_SERVICE_1\\",\\"environment\\":\\"SERVICE_BINDING_ENVIRONMENT_1\\",\\"entrypoint\\":123}.
- \\"services[8]\\" bindings should have a string \\"entrypoint\\" field but got {\\"binding\\":\\"SERVICE_BINDING_1\\",\\"service\\":\\"SERVICE_BINDING_SERVICE_1\\",\\"entrypoint\\":123}."
`);
});
});

Expand Down
40 changes: 40 additions & 0 deletions packages/wrangler/src/__tests__/deploy.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6730,6 +6730,46 @@ addEventListener('fetch', event => {});`
Published test-name (TIMINGS)
https://test-name.test-sub-domain.workers.dev
Current Deployment ID: Galaxy-Class"
`);
expect(std.err).toMatchInlineSnapshot(`""`);
expect(std.warn).toMatchInlineSnapshot(`""`);
});

it("should support service bindings with entrypoints", async () => {
writeWranglerToml({
services: [
{
binding: "FOO",
service: "foo-service",
environment: "production",
entrypoint: "MyHandler",
},
],
});
writeWorkerSource();
mockSubDomainRequest();
mockUploadWorkerRequest({
expectedBindings: [
{
type: "service",
name: "FOO",
service: "foo-service",
environment: "production",
entrypoint: "MyHandler",
},
],
});

await runWrangler("deploy index.js");
expect(std.out).toMatchInlineSnapshot(`
"Total Upload: xx KiB / gzip: xx KiB
Your worker has access to the following bindings:
- Services:
- FOO: foo-service - production (#MyHandler)
Uploaded test-name (TIMINGS)
Published test-name (TIMINGS)
https://test-name.test-sub-domain.workers.dev
Current Deployment ID: Galaxy-Class"
`);
expect(std.err).toMatchInlineSnapshot(`""`);
expect(std.warn).toMatchInlineSnapshot(`""`);
Expand Down
3 changes: 3 additions & 0 deletions packages/wrangler/src/__tests__/init.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2516,6 +2516,7 @@ describe("init", () => {
name: "website",
service: "website",
type: "service",
entrypoint: "WWWHandler",
},
{
type: "dispatch_namespace",
Expand Down Expand Up @@ -2686,6 +2687,7 @@ describe("init", () => {
environment: "production",
binding: "website",
service: "website",
entrypoint: "WWWHandler",
},
],
triggers: {
Expand Down Expand Up @@ -3158,6 +3160,7 @@ describe("init", () => {
binding = \\"website\\"
service = \\"website\\"
environment = \\"production\\"
entrypoint = \\"WWWHandler\\"
[[dispatch_namespaces]]
binding = \\"name-namespace-mock\\"
Expand Down
1 change: 1 addition & 0 deletions packages/wrangler/src/api/dev.ts
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,7 @@ export interface UnstableDevOptions {
binding: string;
service: string;
environment?: string | undefined;
entrypoint?: string | undefined;
}[];
r2?: {
binding: string;
Expand Down
2 changes: 2 additions & 0 deletions packages/wrangler/src/config/environment.ts
Original file line number Diff line number Diff line change
Expand Up @@ -571,6 +571,8 @@ export interface EnvironmentNonInheritable {
service: string;
/** The environment of the service (e.g. production, staging, etc). */
environment?: string;
/** Optionally, the entrypoint (named export) of the service to bind to. */
entrypoint?: string;
}[]
| undefined;

Expand Down
4 changes: 2 additions & 2 deletions packages/wrangler/src/config/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -289,10 +289,10 @@ export function printBindings(bindings: CfWorkerInit["bindings"]) {
if (services !== undefined && services.length > 0) {
output.push({
type: "Services",
entries: services.map(({ binding, service, environment }) => {
entries: services.map(({ binding, service, environment, entrypoint }) => {
let value = service;
if (environment) {
value += ` - ${environment}`;
value += ` - ${environment}${entrypoint ? ` (#${entrypoint})` : ""}`;
}

return {
Expand Down
10 changes: 9 additions & 1 deletion packages/wrangler/src/config/validation.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2566,7 +2566,7 @@ const validateServiceBinding: ValidatorFn = (diagnostics, field, value) => {
return false;
}
let isValid = true;
// Service bindings must have a binding, service, and environment.
// Service bindings must have a binding, a service, optionally an environment, and, optionally an entrypoint.
if (!isRequiredProperty(value, "binding", "string")) {
diagnostics.errors.push(
`"${field}" bindings should have a string "binding" field but got ${JSON.stringify(
Expand All @@ -2591,6 +2591,14 @@ const validateServiceBinding: ValidatorFn = (diagnostics, field, value) => {
);
isValid = false;
}
if (!isOptionalProperty(value, "entrypoint", "string")) {
diagnostics.errors.push(
`"${field}" bindings should have a string "entrypoint" field but got ${JSON.stringify(
value
)}.`
);
isValid = false;
}
return isValid;
};

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -74,7 +74,13 @@ export type WorkerMetadataBinding =
}
| { type: "constellation"; name: string; project: string }
| { type: "hyperdrive"; name: string; id: string }
| { type: "service"; name: string; service: string; environment?: string }
| {
type: "service";
name: string;
service: string;
environment?: string;
entrypoint?: string;
}
| { type: "analytics_engine"; name: string; dataset?: string }
| {
type: "dispatch_namespace";
Expand Down Expand Up @@ -229,14 +235,17 @@ export function createWorkerUploadForm(worker: CfWorkerInit): FormData {
});
});

bindings.services?.forEach(({ binding, service, environment }) => {
metadataBindings.push({
name: binding,
type: "service",
service,
...(environment && { environment }),
});
});
bindings.services?.forEach(
({ binding, service, environment, entrypoint }) => {
metadataBindings.push({
name: binding,
type: "service",
service,
...(environment && { environment }),
...(entrypoint && { entrypoint }),
});
}
);

bindings.analytics_engine_datasets?.forEach(({ binding, dataset }) => {
metadataBindings.push({
Expand Down
1 change: 1 addition & 0 deletions packages/wrangler/src/deployment-bundle/worker.ts
Original file line number Diff line number Diff line change
Expand Up @@ -173,6 +173,7 @@ interface CfService {
binding: string;
service: string;
environment?: string;
entrypoint?: string;
}

interface CfAnalyticsEngineDataset {
Expand Down
1 change: 1 addition & 0 deletions packages/wrangler/src/dev-registry.ts
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ export type WorkerDefinition = {
host: string | undefined;
mode: "local" | "remote";
headers?: Record<string, string>;
entrypoints?: string[];
durableObjects: { name: string; className: string }[];
durableObjectsHost?: string;
durableObjectsPort?: number;
Expand Down
3 changes: 2 additions & 1 deletion packages/wrangler/src/dev.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -329,6 +329,7 @@ export type AdditionalDevProps = {
binding: string;
service: string;
environment?: string;
entrypoint?: string;
}[];
r2?: {
binding: string;
Expand Down Expand Up @@ -740,7 +741,7 @@ async function validateDevServerSettings(
(service) =>
`${service.binding} (${service.service}${
service.environment ? `@${service.environment}` : ""
})`
}${service.entrypoint ? `#${service.entrypoint}` : ""})`
)
.join(", ")}`
);
Expand Down
1 change: 1 addition & 0 deletions packages/wrangler/src/init.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1070,6 +1070,7 @@ export function mapBindings(bindings: WorkerMetadataBinding[]): RawConfig {
binding: binding.name,
service: binding.service,
environment: binding.environment,
entrypoint: binding.entrypoint,
},
];
}
Expand Down
19 changes: 11 additions & 8 deletions packages/wrangler/src/pages/dev.ts
Original file line number Diff line number Diff line change
Expand Up @@ -60,11 +60,13 @@ const BINDING_REGEXP = new RegExp(/^(?<binding>[^=]+)(?:=(?<ref>[^\s]+))?$/);
/* SERVICE_BINDING_REGEXP matches strings like:
* - "binding=service"
* - "binding=service@environment"
* - "binding=service#entrypoint"
* This is used to capture both the binding name (how the binding is used in JS) alongside the name of the service it needs to bind to.
* Additionally it can also accept an environment which indicates what environment the service has to be running for.
* Additionally it can also accept an entrypoint which indicates what named entrypoint of the service to use, if not the default.
*/
const SERVICE_BINDING_REGEXP = new RegExp(
/^(?<binding>[^=]+)=(?<service>[^@\s]+)(@(?<environment>.*)$)?$/
/^(?<binding>[^=]+)=(?<service>[^@\s]+)(@(?<environment>.*)$)?(#(?<entrypoint>.*))?$/
);

export function Options(yargs: CommonYargsArgv) {
Expand Down Expand Up @@ -500,7 +502,7 @@ export const Handler = async ({
);
}

let entrypoint = scriptPath;
let scriptEntrypoint = scriptPath;

Check warning on line 505 in packages/wrangler/src/pages/dev.ts

View check run for this annotation

Codecov / codecov/patch

packages/wrangler/src/pages/dev.ts#L505

Added line #L505 was not covered by tests

// custom _routes.json apply only to Functions or Advanced Mode Pages projects
if (
Expand Down Expand Up @@ -545,11 +547,11 @@ export const Handler = async ({
routesJSONContents = readFileSync(routesJSONPath, "utf-8");
validateRoutes(JSON.parse(routesJSONContents), directory);

entrypoint = join(
scriptEntrypoint = join(

Check warning on line 550 in packages/wrangler/src/pages/dev.ts

View check run for this annotation

Codecov / codecov/patch

packages/wrangler/src/pages/dev.ts#L550

Added line #L550 was not covered by tests
getPagesTmpDir(),
`${Math.random().toString(36).slice(2)}.js`
);
await runBuild(scriptPath, entrypoint, routesJSONContents);
await runBuild(scriptPath, scriptEntrypoint, routesJSONContents);

Check warning on line 554 in packages/wrangler/src/pages/dev.ts

View check run for this annotation

Codecov / codecov/patch

packages/wrangler/src/pages/dev.ts#L554

Added line #L554 was not covered by tests
} catch (err) {
if (err instanceof FatalError) {
throw err;
Expand All @@ -575,7 +577,7 @@ export const Handler = async ({
*/
routesJSONContents = readFileSync(routesJSONPath, "utf-8");
validateRoutes(JSON.parse(routesJSONContents), directory as string);
await runBuild(scriptPath, entrypoint, routesJSONContents);
await runBuild(scriptPath, scriptEntrypoint, routesJSONContents);

Check warning on line 580 in packages/wrangler/src/pages/dev.ts

View check run for this annotation

Codecov / codecov/patch

packages/wrangler/src/pages/dev.ts#L580

Added line #L580 was not covered by tests
} catch (err) {
/**
* If _routes.json is invalid, don't exit but instead fallback to a sensible default
Expand Down Expand Up @@ -604,15 +606,15 @@ export const Handler = async ({
);

routesJSONContents = JSON.stringify(defaultRoutesJSONSpec);
await runBuild(scriptPath, entrypoint, routesJSONContents);
await runBuild(scriptPath, scriptEntrypoint, routesJSONContents);

Check warning on line 609 in packages/wrangler/src/pages/dev.ts

View check run for this annotation

Codecov / codecov/patch

packages/wrangler/src/pages/dev.ts#L609

Added line #L609 was not covered by tests
}
});
}
}

const services = requestedServices
.map((serviceBinding) => {
const { binding, service, environment } =
const { binding, service, environment, entrypoint } =
SERVICE_BINDING_REGEXP.exec(serviceBinding.toString())?.groups || {};

if (!binding || !service) {
Expand All @@ -633,6 +635,7 @@ export const Handler = async ({
binding,
service: serviceName,
environment,
entrypoint,
};
})
.filter(Boolean) as NonNullable<AdditionalDevProps["services"]>;
Expand All @@ -644,7 +647,7 @@ export const Handler = async ({
logger.warn("Support for service binding environments is experimental.");
}

const { stop, waitUntilExit } = await unstable_dev(entrypoint, {
const { stop, waitUntilExit } = await unstable_dev(scriptEntrypoint, {

Check warning on line 650 in packages/wrangler/src/pages/dev.ts

View check run for this annotation

Codecov / codecov/patch

packages/wrangler/src/pages/dev.ts#L650

Added line #L650 was not covered by tests
ip,
port,
inspectorPort,
Expand Down
12 changes: 6 additions & 6 deletions pnpm-lock.yaml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

0 comments on commit 6a5ec8e

Please sign in to comment.