Skip to content

Commit

Permalink
[client] Always use v13 of create deployment API endpoint (#11351)
Browse files Browse the repository at this point in the history
Updates `@vercel/client` to always use the v13 create-deployment endpoint, even when `builds` is present. This allows for `projectSettings.nodeVersion` to be passed when `builds` is present.
  • Loading branch information
TooTallNate committed Apr 10, 2024
1 parent 7259a32 commit 627b79f
Show file tree
Hide file tree
Showing 11 changed files with 108 additions and 31 deletions.
5 changes: 5 additions & 0 deletions .changeset/famous-apples-unite.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'vercel': patch
---

Always set `projectSettings.nodeVersion` in `vc deploy`
5 changes: 5 additions & 0 deletions .changeset/small-ghosts-kiss.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'@vercel/client': minor
---

Always use v13 of create deployment API endpoint
42 changes: 24 additions & 18 deletions packages/cli/src/commands/deploy/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -520,23 +520,6 @@ export default async (client: Client): Promise<number> => {
);
}

const { packageJson } = await scanParentDirs(
join(cwd, project?.rootDirectory ?? ''),
true,
cwd
);
let nodeVersion: string | undefined;
if (packageJson?.engines?.node) {
try {
const { range } = await getSupportedNodeVersion(packageJson.engines.node);
nodeVersion = range;
} catch (error) {
if (error instanceof Error) {
output.warn(error.message);
}
}
}

try {
// if this flag is not set, use `undefined` to allow the project setting to be used
const autoAssignCustomDomains = argv['--skip-domain'] ? false : undefined;
Expand Down Expand Up @@ -573,7 +556,6 @@ export default async (client: Client): Promise<number> => {
createArgs.projectSettings = {
sourceFilesOutsideRootDirectory,
rootDirectory,
nodeVersion,
};

if (status === 'linked') {
Expand All @@ -584,6 +566,30 @@ export default async (client: Client): Promise<number> => {
}
}

// Read the `engines.node` field from `package.json` and send as a
// `projectSettings` property as an optimization (so that the API
// does not need to retrieve the file to do this check).
const { packageJson } = await scanParentDirs(
join(cwd, project?.rootDirectory ?? ''),
true,
cwd
);
let nodeVersion: string | undefined;
if (packageJson?.engines?.node) {
try {
const { range } = await getSupportedNodeVersion(
packageJson.engines.node
);
nodeVersion = range;
} catch (error) {
if (error instanceof Error) {
output.warn(error.message);
}
}
}
if (!createArgs.projectSettings) createArgs.projectSettings = {};
createArgs.projectSettings.nodeVersion = nodeVersion;

deployment = await createDeploy(
client,
now,
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
{
"orgId": "team_dummy",
"projectId": "legacy-builds"
}
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
module.exports = (req, res) => res.end('Vercel');
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
{
"name": "node",
"version": "1.0.0",
"private": true,
"engines": {
"node": "18.x"
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
{
"builds": [
{ "src": "index.js", "use": "@vercel/node" }
]
}
48 changes: 48 additions & 0 deletions packages/cli/test/unit/commands/deploy.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -466,6 +466,54 @@ describe('deploy', () => {
});
});

it('should send `projectSettings.nodeVersion` based on `engines.node` package.json field with `builds` in `vercel.json`', async () => {
const user = useUser();
useTeams('team_dummy');
useProject({
...defaultProject,
name: 'legacy-builds',
id: 'QmbKpqpiUqbcke',
});

let body: any;
client.scenario.post(`/v13/deployments`, (req, res) => {
body = req.body;
res.json({
creator: {
uid: user.id,
username: user.username,
},
id: 'dpl_',
});
});
client.scenario.get(`/v13/deployments/dpl_`, (req, res) => {
res.json({
creator: {
uid: user.id,
username: user.username,
},
id: 'dpl_',
readyState: 'READY',
aliasAssigned: true,
alias: [],
});
});

const repoRoot = setupUnitFixture('commands/deploy/legacy-builds');
client.cwd = repoRoot;
client.setArgv('deploy');
const exitCode = await deploy(client);
expect(exitCode).toEqual(0);
expect(body).toMatchObject({
source: 'cli',
version: 2,
projectSettings: {
nodeVersion: '18.x',
sourceFilesOutsideRootDirectory: true,
},
});
});

it('should send latest supported node version when given a >low-node-version based on `engines.node` package.json field', async () => {
const user = useUser();
useTeams('team_dummy');
Expand Down
5 changes: 1 addition & 4 deletions packages/client/src/check-deployment-status.ts
Original file line number Diff line number Diff line change
Expand Up @@ -31,10 +31,7 @@ export async function* checkDeploymentStatus(

let deploymentState = deployment;

const apiDeployments = getApiDeploymentsUrl({
builds: deployment.builds,
functions: deployment.functions,
});
const apiDeployments = getApiDeploymentsUrl();

// If the deployment is ready, we don't want any of this to run
if (isDone(deploymentState) && isAliasAssigned(deploymentState)) {
Expand Down
6 changes: 5 additions & 1 deletion packages/client/src/deploy.ts
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,11 @@ async function* postDeployment(
}> {
const debug = createDebug(clientOptions.debug);
const preparedFiles = prepareFiles(files, clientOptions);
const apiDeployments = getApiDeploymentsUrl(deploymentOptions);
const apiDeployments = getApiDeploymentsUrl();

if (deploymentOptions?.builds && !deploymentOptions.functions) {
clientOptions.skipAutoDetectionConfirmation = true;
}

debug('Sending deployment creation API request');
try {
Expand Down
10 changes: 2 additions & 8 deletions packages/client/src/utils/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ import { URL } from 'url';
import ignore from 'ignore';
import { pkgVersion } from '../pkg';
import { NowBuildError } from '@vercel/build-utils';
import { VercelClientOptions, DeploymentOptions, VercelConfig } from '../types';
import { VercelClientOptions, VercelConfig } from '../types';
import { Sema } from 'async-sema';
import { readFile } from 'fs-extra';
import readdir from './readdir-recursive';
Expand Down Expand Up @@ -46,13 +46,7 @@ const EVENTS_ARRAY = [
export type DeploymentEventType = typeof EVENTS_ARRAY[number];
export const EVENTS = new Set(EVENTS_ARRAY);

export function getApiDeploymentsUrl(
metadata?: Pick<DeploymentOptions, 'builds' | 'functions'>
) {
if (metadata && metadata.builds && !metadata.functions) {
return '/v10/deployments';
}

export function getApiDeploymentsUrl() {
return '/v13/deployments';
}

Expand Down

0 comments on commit 627b79f

Please sign in to comment.