@vercel/build-utils 2.15.2-canary.0 → 2.15.2-canary.3
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/fs/node-version.js +3 -0
- package/dist/fs/run-user-scripts.d.ts +6 -1
- package/dist/fs/run-user-scripts.js +69 -36
- package/dist/index.js +73 -36
- package/dist/types.d.ts +24 -1
- package/package.json +3 -3
package/dist/fs/node-version.js
CHANGED
@@ -40,6 +40,9 @@ function getDiscontinuedNodeVersions() {
|
|
40
40
|
exports.getDiscontinuedNodeVersions = getDiscontinuedNodeVersions;
|
41
41
|
async function getSupportedNodeVersion(engineRange, isAuto = false) {
|
42
42
|
let selection = getLatestNodeVersion();
|
43
|
+
if (process.env.ENABLE_EXPERIMENTAL_NODE16 === '1') {
|
44
|
+
return { major: 16, range: '16.x', runtime: 'nodejs16.x' };
|
45
|
+
}
|
43
46
|
if (engineRange) {
|
44
47
|
const found = semver_1.validRange(engineRange) &&
|
45
48
|
allOptions.some(o => {
|
@@ -7,6 +7,11 @@ export interface ScanParentDirsResult {
|
|
7
7
|
* "yarn", "npm", or "pnpm" depending on the presence of lockfiles.
|
8
8
|
*/
|
9
9
|
cliType: CliType;
|
10
|
+
/**
|
11
|
+
* The file path of found `package.json` file, or `undefined` if none was
|
12
|
+
* found.
|
13
|
+
*/
|
14
|
+
packageJsonPath?: string;
|
10
15
|
/**
|
11
16
|
* The contents of found `package.json` file, when the `readPackageJson`
|
12
17
|
* option is enabled.
|
@@ -56,7 +61,7 @@ export declare function getSpawnOptions(meta: Meta, nodeVersion: NodeVersion): S
|
|
56
61
|
export declare function getNodeVersion(destPath: string, _nodeVersion?: string, config?: Config, meta?: Meta): Promise<NodeVersion>;
|
57
62
|
export declare function scanParentDirs(destPath: string, readPackageJson?: boolean): Promise<ScanParentDirsResult>;
|
58
63
|
export declare function walkParentDirs({ base, start, filename, }: WalkParentDirsProps): Promise<string | null>;
|
59
|
-
export declare function runNpmInstall(destPath: string, args?: string[], spawnOpts?: SpawnOptions, meta?: Meta, nodeVersion?: NodeVersion): Promise<
|
64
|
+
export declare function runNpmInstall(destPath: string, args?: string[], spawnOpts?: SpawnOptions, meta?: Meta, nodeVersion?: NodeVersion): Promise<boolean>;
|
60
65
|
export declare function getEnvForPackageManager({ cliType, lockfileVersion, nodeVersion, env, }: {
|
61
66
|
cliType: CliType;
|
62
67
|
lockfileVersion: number | undefined;
|
@@ -7,12 +7,15 @@ exports.installDependencies = exports.getScriptName = exports.runPipInstall = ex
|
|
7
7
|
const assert_1 = __importDefault(require("assert"));
|
8
8
|
const fs_extra_1 = __importDefault(require("fs-extra"));
|
9
9
|
const path_1 = __importDefault(require("path"));
|
10
|
-
const
|
10
|
+
const async_sema_1 = __importDefault(require("async-sema"));
|
11
11
|
const cross_spawn_1 = __importDefault(require("cross-spawn"));
|
12
12
|
const util_1 = require("util");
|
13
|
+
const debug_1 = __importDefault(require("../debug"));
|
13
14
|
const errors_1 = require("../errors");
|
14
15
|
const node_version_1 = require("./node-version");
|
15
16
|
const read_config_file_1 = require("./read-config-file");
|
17
|
+
// Only allow one `runNpmInstall()` invocation to run concurrently
|
18
|
+
const runNpmInstallSema = new async_sema_1.default(1);
|
16
19
|
function spawnAsync(command, args, opts = {}) {
|
17
20
|
return new Promise((resolve, reject) => {
|
18
21
|
const stderrLogs = [];
|
@@ -151,11 +154,12 @@ async function scanParentDirs(destPath, readPackageJson = false) {
|
|
151
154
|
assert_1.default(path_1.default.isAbsolute(destPath));
|
152
155
|
let cliType = 'yarn';
|
153
156
|
let packageJson;
|
157
|
+
let packageJsonPath;
|
154
158
|
let currentDestPath = destPath;
|
155
159
|
let lockfileVersion;
|
156
160
|
// eslint-disable-next-line no-constant-condition
|
157
161
|
while (true) {
|
158
|
-
|
162
|
+
packageJsonPath = path_1.default.join(currentDestPath, 'package.json');
|
159
163
|
// eslint-disable-next-line no-await-in-loop
|
160
164
|
if (await fs_extra_1.default.pathExists(packageJsonPath)) {
|
161
165
|
// Only read the contents of the *first* `package.json` file found,
|
@@ -199,7 +203,7 @@ async function scanParentDirs(destPath, readPackageJson = false) {
|
|
199
203
|
break;
|
200
204
|
currentDestPath = newDestPath;
|
201
205
|
}
|
202
|
-
return { cliType, packageJson, lockfileVersion };
|
206
|
+
return { cliType, packageJson, lockfileVersion, packageJsonPath };
|
203
207
|
}
|
204
208
|
exports.scanParentDirs = scanParentDirs;
|
205
209
|
async function walkParentDirs({ base, start, filename, }) {
|
@@ -217,46 +221,75 @@ async function walkParentDirs({ base, start, filename, }) {
|
|
217
221
|
return null;
|
218
222
|
}
|
219
223
|
exports.walkParentDirs = walkParentDirs;
|
224
|
+
function isSet(v) {
|
225
|
+
var _a;
|
226
|
+
return ((_a = v === null || v === void 0 ? void 0 : v.constructor) === null || _a === void 0 ? void 0 : _a.name) === 'Set';
|
227
|
+
}
|
220
228
|
async function runNpmInstall(destPath, args = [], spawnOpts, meta, nodeVersion) {
|
221
229
|
if (meta === null || meta === void 0 ? void 0 : meta.isDev) {
|
222
230
|
debug_1.default('Skipping dependency installation because dev mode is enabled');
|
223
|
-
return;
|
231
|
+
return false;
|
224
232
|
}
|
225
233
|
assert_1.default(path_1.default.isAbsolute(destPath));
|
226
|
-
|
227
|
-
|
228
|
-
|
229
|
-
|
230
|
-
|
231
|
-
|
232
|
-
|
233
|
-
|
234
|
-
|
235
|
-
|
236
|
-
|
237
|
-
|
238
|
-
|
239
|
-
|
240
|
-
|
241
|
-
|
242
|
-
|
243
|
-
|
244
|
-
|
245
|
-
|
246
|
-
|
247
|
-
opts
|
248
|
-
|
249
|
-
|
250
|
-
|
251
|
-
|
252
|
-
|
253
|
-
|
254
|
-
|
234
|
+
try {
|
235
|
+
await runNpmInstallSema.acquire();
|
236
|
+
const { cliType, packageJsonPath, lockfileVersion } = await scanParentDirs(destPath);
|
237
|
+
// Only allow `runNpmInstall()` to run once per `package.json`
|
238
|
+
// when doing a default install (no additional args)
|
239
|
+
if (meta && packageJsonPath && args.length === 0) {
|
240
|
+
if (!isSet(meta.runNpmInstallSet)) {
|
241
|
+
meta.runNpmInstallSet = new Set();
|
242
|
+
}
|
243
|
+
if (isSet(meta.runNpmInstallSet)) {
|
244
|
+
if (meta.runNpmInstallSet.has(packageJsonPath)) {
|
245
|
+
return false;
|
246
|
+
}
|
247
|
+
else {
|
248
|
+
meta.runNpmInstallSet.add(packageJsonPath);
|
249
|
+
}
|
250
|
+
}
|
251
|
+
}
|
252
|
+
const installTime = Date.now();
|
253
|
+
console.log('Installing dependencies...');
|
254
|
+
debug_1.default(`Installing to ${destPath}`);
|
255
|
+
const opts = { cwd: destPath, ...spawnOpts };
|
256
|
+
const env = opts.env ? { ...opts.env } : { ...process.env };
|
257
|
+
delete env.NODE_ENV;
|
258
|
+
opts.env = getEnvForPackageManager({
|
259
|
+
cliType,
|
260
|
+
lockfileVersion,
|
261
|
+
nodeVersion,
|
262
|
+
env,
|
263
|
+
});
|
264
|
+
let commandArgs;
|
265
|
+
if (cliType === 'npm') {
|
266
|
+
opts.prettyCommand = 'npm install';
|
267
|
+
commandArgs = args
|
268
|
+
.filter(a => a !== '--prefer-offline')
|
269
|
+
.concat(['install', '--no-audit', '--unsafe-perm']);
|
270
|
+
}
|
271
|
+
else if (cliType === 'pnpm') {
|
272
|
+
// PNPM's install command is similar to NPM's but without the audit nonsense
|
273
|
+
// @see options https://pnpm.io/cli/install
|
274
|
+
opts.prettyCommand = 'pnpm install';
|
275
|
+
commandArgs = args
|
276
|
+
.filter(a => a !== '--prefer-offline')
|
277
|
+
.concat(['install', '--unsafe-perm']);
|
278
|
+
}
|
279
|
+
else {
|
280
|
+
opts.prettyCommand = 'yarn install';
|
281
|
+
commandArgs = ['install', ...args];
|
282
|
+
}
|
283
|
+
if (process.env.NPM_ONLY_PRODUCTION) {
|
284
|
+
commandArgs.push('--production');
|
285
|
+
}
|
286
|
+
await spawnAsync(cliType, commandArgs, opts);
|
287
|
+
debug_1.default(`Install complete [${Date.now() - installTime}ms]`);
|
288
|
+
return true;
|
255
289
|
}
|
256
|
-
|
257
|
-
|
290
|
+
finally {
|
291
|
+
runNpmInstallSema.release();
|
258
292
|
}
|
259
|
-
return spawnAsync(cliType, commandArgs, opts);
|
260
293
|
}
|
261
294
|
exports.runNpmInstall = runNpmInstall;
|
262
295
|
function getEnvForPackageManager({ cliType, lockfileVersion, nodeVersion, env, }) {
|
package/dist/index.js
CHANGED
@@ -26617,6 +26617,7 @@ exports.frameworks = [
|
|
26617
26617
|
slug: 'nextjs',
|
26618
26618
|
demo: 'https://nextjs-template.vercel.app',
|
26619
26619
|
logo: 'https://raw.githubusercontent.com/vercel/vercel/main/packages/frameworks/logos/next.svg',
|
26620
|
+
darkModeLogo: 'https://raw.githubusercontent.com/vercel/vercel/main/packages/frameworks/logos/next-dark.svg',
|
26620
26621
|
screenshot: 'https://assets.vercel.com/image/upload/v1647366075/front/import/nextjs.png',
|
26621
26622
|
tagline: 'Next.js makes you productive with React instantly — whether you want to build static or dynamic sites.',
|
26622
26623
|
description: 'A Next.js app and a Serverless Function API.',
|
@@ -34483,6 +34484,9 @@ function getDiscontinuedNodeVersions() {
|
|
34483
34484
|
exports.getDiscontinuedNodeVersions = getDiscontinuedNodeVersions;
|
34484
34485
|
async function getSupportedNodeVersion(engineRange, isAuto = false) {
|
34485
34486
|
let selection = getLatestNodeVersion();
|
34487
|
+
if (process.env.ENABLE_EXPERIMENTAL_NODE16 === '1') {
|
34488
|
+
return { major: 16, range: '16.x', runtime: 'nodejs16.x' };
|
34489
|
+
}
|
34486
34490
|
if (engineRange) {
|
34487
34491
|
const found = semver_1.validRange(engineRange) &&
|
34488
34492
|
allOptions.some(o => {
|
@@ -34621,12 +34625,15 @@ exports.installDependencies = exports.getScriptName = exports.runPipInstall = ex
|
|
34621
34625
|
const assert_1 = __importDefault(__webpack_require__(2357));
|
34622
34626
|
const fs_extra_1 = __importDefault(__webpack_require__(5392));
|
34623
34627
|
const path_1 = __importDefault(__webpack_require__(5622));
|
34624
|
-
const
|
34628
|
+
const async_sema_1 = __importDefault(__webpack_require__(5758));
|
34625
34629
|
const cross_spawn_1 = __importDefault(__webpack_require__(7618));
|
34626
34630
|
const util_1 = __webpack_require__(1669);
|
34631
|
+
const debug_1 = __importDefault(__webpack_require__(1868));
|
34627
34632
|
const errors_1 = __webpack_require__(3983);
|
34628
34633
|
const node_version_1 = __webpack_require__(7903);
|
34629
34634
|
const read_config_file_1 = __webpack_require__(7792);
|
34635
|
+
// Only allow one `runNpmInstall()` invocation to run concurrently
|
34636
|
+
const runNpmInstallSema = new async_sema_1.default(1);
|
34630
34637
|
function spawnAsync(command, args, opts = {}) {
|
34631
34638
|
return new Promise((resolve, reject) => {
|
34632
34639
|
const stderrLogs = [];
|
@@ -34765,11 +34772,12 @@ async function scanParentDirs(destPath, readPackageJson = false) {
|
|
34765
34772
|
assert_1.default(path_1.default.isAbsolute(destPath));
|
34766
34773
|
let cliType = 'yarn';
|
34767
34774
|
let packageJson;
|
34775
|
+
let packageJsonPath;
|
34768
34776
|
let currentDestPath = destPath;
|
34769
34777
|
let lockfileVersion;
|
34770
34778
|
// eslint-disable-next-line no-constant-condition
|
34771
34779
|
while (true) {
|
34772
|
-
|
34780
|
+
packageJsonPath = path_1.default.join(currentDestPath, 'package.json');
|
34773
34781
|
// eslint-disable-next-line no-await-in-loop
|
34774
34782
|
if (await fs_extra_1.default.pathExists(packageJsonPath)) {
|
34775
34783
|
// Only read the contents of the *first* `package.json` file found,
|
@@ -34813,7 +34821,7 @@ async function scanParentDirs(destPath, readPackageJson = false) {
|
|
34813
34821
|
break;
|
34814
34822
|
currentDestPath = newDestPath;
|
34815
34823
|
}
|
34816
|
-
return { cliType, packageJson, lockfileVersion };
|
34824
|
+
return { cliType, packageJson, lockfileVersion, packageJsonPath };
|
34817
34825
|
}
|
34818
34826
|
exports.scanParentDirs = scanParentDirs;
|
34819
34827
|
async function walkParentDirs({ base, start, filename, }) {
|
@@ -34831,46 +34839,75 @@ async function walkParentDirs({ base, start, filename, }) {
|
|
34831
34839
|
return null;
|
34832
34840
|
}
|
34833
34841
|
exports.walkParentDirs = walkParentDirs;
|
34842
|
+
function isSet(v) {
|
34843
|
+
var _a;
|
34844
|
+
return ((_a = v === null || v === void 0 ? void 0 : v.constructor) === null || _a === void 0 ? void 0 : _a.name) === 'Set';
|
34845
|
+
}
|
34834
34846
|
async function runNpmInstall(destPath, args = [], spawnOpts, meta, nodeVersion) {
|
34835
34847
|
if (meta === null || meta === void 0 ? void 0 : meta.isDev) {
|
34836
34848
|
debug_1.default('Skipping dependency installation because dev mode is enabled');
|
34837
|
-
return;
|
34849
|
+
return false;
|
34838
34850
|
}
|
34839
34851
|
assert_1.default(path_1.default.isAbsolute(destPath));
|
34840
|
-
|
34841
|
-
|
34842
|
-
|
34843
|
-
|
34844
|
-
|
34845
|
-
|
34846
|
-
|
34847
|
-
|
34848
|
-
|
34849
|
-
|
34850
|
-
|
34851
|
-
|
34852
|
-
|
34853
|
-
|
34854
|
-
|
34855
|
-
|
34856
|
-
|
34857
|
-
|
34858
|
-
|
34859
|
-
|
34860
|
-
|
34861
|
-
opts
|
34862
|
-
|
34863
|
-
|
34864
|
-
|
34865
|
-
|
34866
|
-
|
34867
|
-
|
34868
|
-
|
34852
|
+
try {
|
34853
|
+
await runNpmInstallSema.acquire();
|
34854
|
+
const { cliType, packageJsonPath, lockfileVersion } = await scanParentDirs(destPath);
|
34855
|
+
// Only allow `runNpmInstall()` to run once per `package.json`
|
34856
|
+
// when doing a default install (no additional args)
|
34857
|
+
if (meta && packageJsonPath && args.length === 0) {
|
34858
|
+
if (!isSet(meta.runNpmInstallSet)) {
|
34859
|
+
meta.runNpmInstallSet = new Set();
|
34860
|
+
}
|
34861
|
+
if (isSet(meta.runNpmInstallSet)) {
|
34862
|
+
if (meta.runNpmInstallSet.has(packageJsonPath)) {
|
34863
|
+
return false;
|
34864
|
+
}
|
34865
|
+
else {
|
34866
|
+
meta.runNpmInstallSet.add(packageJsonPath);
|
34867
|
+
}
|
34868
|
+
}
|
34869
|
+
}
|
34870
|
+
const installTime = Date.now();
|
34871
|
+
console.log('Installing dependencies...');
|
34872
|
+
debug_1.default(`Installing to ${destPath}`);
|
34873
|
+
const opts = { cwd: destPath, ...spawnOpts };
|
34874
|
+
const env = opts.env ? { ...opts.env } : { ...process.env };
|
34875
|
+
delete env.NODE_ENV;
|
34876
|
+
opts.env = getEnvForPackageManager({
|
34877
|
+
cliType,
|
34878
|
+
lockfileVersion,
|
34879
|
+
nodeVersion,
|
34880
|
+
env,
|
34881
|
+
});
|
34882
|
+
let commandArgs;
|
34883
|
+
if (cliType === 'npm') {
|
34884
|
+
opts.prettyCommand = 'npm install';
|
34885
|
+
commandArgs = args
|
34886
|
+
.filter(a => a !== '--prefer-offline')
|
34887
|
+
.concat(['install', '--no-audit', '--unsafe-perm']);
|
34888
|
+
}
|
34889
|
+
else if (cliType === 'pnpm') {
|
34890
|
+
// PNPM's install command is similar to NPM's but without the audit nonsense
|
34891
|
+
// @see options https://pnpm.io/cli/install
|
34892
|
+
opts.prettyCommand = 'pnpm install';
|
34893
|
+
commandArgs = args
|
34894
|
+
.filter(a => a !== '--prefer-offline')
|
34895
|
+
.concat(['install', '--unsafe-perm']);
|
34896
|
+
}
|
34897
|
+
else {
|
34898
|
+
opts.prettyCommand = 'yarn install';
|
34899
|
+
commandArgs = ['install', ...args];
|
34900
|
+
}
|
34901
|
+
if (process.env.NPM_ONLY_PRODUCTION) {
|
34902
|
+
commandArgs.push('--production');
|
34903
|
+
}
|
34904
|
+
await spawnAsync(cliType, commandArgs, opts);
|
34905
|
+
debug_1.default(`Install complete [${Date.now() - installTime}ms]`);
|
34906
|
+
return true;
|
34869
34907
|
}
|
34870
|
-
|
34871
|
-
|
34908
|
+
finally {
|
34909
|
+
runNpmInstallSema.release();
|
34872
34910
|
}
|
34873
|
-
return spawnAsync(cliType, commandArgs, opts);
|
34874
34911
|
}
|
34875
34912
|
exports.runNpmInstall = runNpmInstall;
|
34876
34913
|
function getEnvForPackageManager({ cliType, lockfileVersion, nodeVersion, env, }) {
|
package/dist/types.d.ts
CHANGED
@@ -294,6 +294,7 @@ export interface ProjectSettings {
|
|
294
294
|
sourceFilesOutsideRootDirectory?: boolean;
|
295
295
|
directoryListing?: boolean;
|
296
296
|
gitForkProtection?: boolean;
|
297
|
+
commandForIgnoringBuildStep?: string | null;
|
297
298
|
}
|
298
299
|
export interface BuilderV2 {
|
299
300
|
version: 2;
|
@@ -313,7 +314,28 @@ export interface Images {
|
|
313
314
|
minimumCacheTTL?: number;
|
314
315
|
formats?: ImageFormat[];
|
315
316
|
}
|
316
|
-
|
317
|
+
/**
|
318
|
+
* If a Builder ends up creating filesystem outputs conforming to
|
319
|
+
* the Build Output API, then the Builder should return this type.
|
320
|
+
*/
|
321
|
+
export interface BuildResultBuildOutput {
|
322
|
+
/**
|
323
|
+
* Version number of the Build Output API that was created.
|
324
|
+
* Currently only `3` is a valid value.
|
325
|
+
* @example 3
|
326
|
+
*/
|
327
|
+
buildOutputVersion: 3;
|
328
|
+
/**
|
329
|
+
* Filesystem path to the Build Output directory.
|
330
|
+
* @example "/path/to/.vercel/output"
|
331
|
+
*/
|
332
|
+
buildOutputPath: string;
|
333
|
+
}
|
334
|
+
/**
|
335
|
+
* When a Builder implements `version: 2`, the `build()` function is expected
|
336
|
+
* to return this type.
|
337
|
+
*/
|
338
|
+
export interface BuildResultV2Typical {
|
317
339
|
routes?: any[];
|
318
340
|
images?: Images;
|
319
341
|
output: {
|
@@ -324,6 +346,7 @@ export interface BuildResultV2 {
|
|
324
346
|
value: string;
|
325
347
|
}>;
|
326
348
|
}
|
349
|
+
export declare type BuildResultV2 = BuildResultV2Typical | BuildResultBuildOutput;
|
327
350
|
export interface BuildResultV3 {
|
328
351
|
output: Lambda;
|
329
352
|
}
|
package/package.json
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
{
|
2
2
|
"name": "@vercel/build-utils",
|
3
|
-
"version": "2.15.2-canary.
|
3
|
+
"version": "2.15.2-canary.3",
|
4
4
|
"license": "MIT",
|
5
5
|
"main": "./dist/index.js",
|
6
6
|
"types": "./dist/index.d.js",
|
@@ -30,7 +30,7 @@
|
|
30
30
|
"@types/node-fetch": "^2.1.6",
|
31
31
|
"@types/semver": "6.0.0",
|
32
32
|
"@types/yazl": "^2.4.1",
|
33
|
-
"@vercel/frameworks": "0.7.
|
33
|
+
"@vercel/frameworks": "0.7.2-canary.0",
|
34
34
|
"@vercel/ncc": "0.24.0",
|
35
35
|
"aggregate-error": "3.0.1",
|
36
36
|
"async-retry": "1.2.3",
|
@@ -49,5 +49,5 @@
|
|
49
49
|
"typescript": "4.3.4",
|
50
50
|
"yazl": "2.4.3"
|
51
51
|
},
|
52
|
-
"gitHead": "
|
52
|
+
"gitHead": "698b89a2ba83d98b5fa0773142e4f5df3a2c4a9a"
|
53
53
|
}
|