@vercel/build-utils 2.12.3-canary.2 → 2.12.3-canary.20
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/convert-runtime-to-plugin.d.ts +38 -0
- package/dist/convert-runtime-to-plugin.js +157 -0
- package/dist/fs/glob.js +2 -1
- package/dist/fs/normalize-path.d.ts +4 -0
- package/dist/fs/normalize-path.js +11 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.js +4169 -3528
- package/dist/lambda.d.ts +7 -3
- package/dist/lambda.js +14 -4
- package/dist/prerender.d.ts +3 -1
- package/dist/prerender.js +10 -1
- package/dist/types.d.ts +1 -0
- package/package.json +6 -6
@@ -0,0 +1,38 @@
|
|
1
|
+
import { Lambda } from './lambda';
|
2
|
+
import type { BuildOptions } from './types';
|
3
|
+
/**
|
4
|
+
* Convert legacy Runtime to a Plugin.
|
5
|
+
* @param buildRuntime - a legacy build() function from a Runtime
|
6
|
+
* @param ext - the file extension, for example `.py`
|
7
|
+
*/
|
8
|
+
export declare function convertRuntimeToPlugin(buildRuntime: (options: BuildOptions) => Promise<{
|
9
|
+
output: Lambda;
|
10
|
+
}>, ext: string): ({ workPath }: {
|
11
|
+
workPath: string;
|
12
|
+
}) => Promise<void>;
|
13
|
+
/**
|
14
|
+
* If `.output/functions-manifest.json` exists, append to the pages
|
15
|
+
* property. Otherwise write a new file. This will also read `vercel.json`
|
16
|
+
* and apply relevant `functions` property config.
|
17
|
+
*/
|
18
|
+
export declare function updateFunctionsManifest({ workPath, pages, }: {
|
19
|
+
workPath: string;
|
20
|
+
pages: {
|
21
|
+
[key: string]: any;
|
22
|
+
};
|
23
|
+
}): Promise<void>;
|
24
|
+
/**
|
25
|
+
* Will append routes to the `routes-manifest.json` file.
|
26
|
+
* If the file does not exist, it'll be created.
|
27
|
+
*/
|
28
|
+
export declare function updateRoutesManifest({ workPath, dynamicRoutes, }: {
|
29
|
+
workPath: string;
|
30
|
+
dynamicRoutes?: {
|
31
|
+
page: string;
|
32
|
+
regex: string;
|
33
|
+
namedRegex?: string;
|
34
|
+
routeKeys?: {
|
35
|
+
[named: string]: string;
|
36
|
+
};
|
37
|
+
}[];
|
38
|
+
}): Promise<void>;
|
@@ -0,0 +1,157 @@
|
|
1
|
+
"use strict";
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
4
|
+
};
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
6
|
+
exports.updateRoutesManifest = exports.updateFunctionsManifest = exports.convertRuntimeToPlugin = void 0;
|
7
|
+
const fs_extra_1 = __importDefault(require("fs-extra"));
|
8
|
+
const path_1 = require("path");
|
9
|
+
const glob_1 = __importDefault(require("./fs/glob"));
|
10
|
+
const normalize_path_1 = require("./fs/normalize-path");
|
11
|
+
const lambda_1 = require("./lambda");
|
12
|
+
const minimatch_1 = __importDefault(require("minimatch"));
|
13
|
+
/**
|
14
|
+
* Convert legacy Runtime to a Plugin.
|
15
|
+
* @param buildRuntime - a legacy build() function from a Runtime
|
16
|
+
* @param ext - the file extension, for example `.py`
|
17
|
+
*/
|
18
|
+
function convertRuntimeToPlugin(buildRuntime, ext) {
|
19
|
+
return async function build({ workPath }) {
|
20
|
+
const opts = { cwd: workPath };
|
21
|
+
const files = await glob_1.default('**', opts);
|
22
|
+
delete files['vercel.json']; // Builders/Runtimes didn't have vercel.json
|
23
|
+
const entrypoints = await glob_1.default(`api/**/*${ext}`, opts);
|
24
|
+
const pages = {};
|
25
|
+
const { functions = {} } = await readVercelConfig(workPath);
|
26
|
+
const traceDir = path_1.join(workPath, '.output', 'runtime-traced-files');
|
27
|
+
await fs_extra_1.default.ensureDir(traceDir);
|
28
|
+
for (const entrypoint of Object.keys(entrypoints)) {
|
29
|
+
const key = Object.keys(functions).find(src => src === entrypoint || minimatch_1.default(entrypoint, src)) || '';
|
30
|
+
const config = functions[key] || {};
|
31
|
+
const { output } = await buildRuntime({
|
32
|
+
files,
|
33
|
+
entrypoint,
|
34
|
+
workPath,
|
35
|
+
config: {
|
36
|
+
zeroConfig: true,
|
37
|
+
includeFiles: config.includeFiles,
|
38
|
+
excludeFiles: config.excludeFiles,
|
39
|
+
},
|
40
|
+
});
|
41
|
+
pages[entrypoint] = {
|
42
|
+
handler: output.handler,
|
43
|
+
runtime: output.runtime,
|
44
|
+
memory: output.memory,
|
45
|
+
maxDuration: output.maxDuration,
|
46
|
+
environment: output.environment,
|
47
|
+
allowQuery: output.allowQuery,
|
48
|
+
regions: output.regions,
|
49
|
+
};
|
50
|
+
// @ts-ignore This symbol is a private API
|
51
|
+
const lambdaFiles = output[lambda_1.FILES_SYMBOL];
|
52
|
+
const entry = path_1.join(workPath, '.output', 'server', 'pages', entrypoint);
|
53
|
+
await fs_extra_1.default.ensureDir(path_1.dirname(entry));
|
54
|
+
await linkOrCopy(files[entrypoint].fsPath, entry);
|
55
|
+
const tracedFiles = [];
|
56
|
+
Object.entries(lambdaFiles).forEach(async ([relPath, file]) => {
|
57
|
+
const newPath = path_1.join(traceDir, relPath);
|
58
|
+
tracedFiles.push({ absolutePath: newPath, relativePath: relPath });
|
59
|
+
if (file.fsPath) {
|
60
|
+
await linkOrCopy(file.fsPath, newPath);
|
61
|
+
}
|
62
|
+
else if (file.type === 'FileBlob') {
|
63
|
+
const { data, mode } = file;
|
64
|
+
await fs_extra_1.default.writeFile(newPath, data, { mode });
|
65
|
+
}
|
66
|
+
else {
|
67
|
+
throw new Error(`Unknown file type: ${file.type}`);
|
68
|
+
}
|
69
|
+
});
|
70
|
+
const nft = path_1.join(workPath, '.output', 'server', 'pages', `${entrypoint}.nft.json`);
|
71
|
+
const json = JSON.stringify({
|
72
|
+
version: 1,
|
73
|
+
files: tracedFiles.map(f => ({
|
74
|
+
input: normalize_path_1.normalizePath(path_1.relative(nft, f.absolutePath)),
|
75
|
+
output: normalize_path_1.normalizePath(f.relativePath),
|
76
|
+
})),
|
77
|
+
});
|
78
|
+
await fs_extra_1.default.ensureDir(path_1.dirname(nft));
|
79
|
+
await fs_extra_1.default.writeFile(nft, json);
|
80
|
+
}
|
81
|
+
await updateFunctionsManifest({ workPath, pages });
|
82
|
+
};
|
83
|
+
}
|
84
|
+
exports.convertRuntimeToPlugin = convertRuntimeToPlugin;
|
85
|
+
async function linkOrCopy(existingPath, newPath) {
|
86
|
+
try {
|
87
|
+
await fs_extra_1.default.createLink(existingPath, newPath);
|
88
|
+
}
|
89
|
+
catch (err) {
|
90
|
+
if (err.code !== 'EEXIST') {
|
91
|
+
await fs_extra_1.default.copyFile(existingPath, newPath);
|
92
|
+
}
|
93
|
+
}
|
94
|
+
}
|
95
|
+
async function readJson(filePath) {
|
96
|
+
try {
|
97
|
+
const str = await fs_extra_1.default.readFile(filePath, 'utf8');
|
98
|
+
return JSON.parse(str);
|
99
|
+
}
|
100
|
+
catch (err) {
|
101
|
+
if (err.code === 'ENOENT') {
|
102
|
+
return {};
|
103
|
+
}
|
104
|
+
throw err;
|
105
|
+
}
|
106
|
+
}
|
107
|
+
async function readVercelConfig(workPath) {
|
108
|
+
const vercelJsonPath = path_1.join(workPath, 'vercel.json');
|
109
|
+
return readJson(vercelJsonPath);
|
110
|
+
}
|
111
|
+
/**
|
112
|
+
* If `.output/functions-manifest.json` exists, append to the pages
|
113
|
+
* property. Otherwise write a new file. This will also read `vercel.json`
|
114
|
+
* and apply relevant `functions` property config.
|
115
|
+
*/
|
116
|
+
async function updateFunctionsManifest({ workPath, pages, }) {
|
117
|
+
const functionsManifestPath = path_1.join(workPath, '.output', 'functions-manifest.json');
|
118
|
+
const vercelConfig = await readVercelConfig(workPath);
|
119
|
+
const functionsManifest = await readJson(functionsManifestPath);
|
120
|
+
if (!functionsManifest.version)
|
121
|
+
functionsManifest.version = 1;
|
122
|
+
if (!functionsManifest.pages)
|
123
|
+
functionsManifest.pages = {};
|
124
|
+
for (const [pageKey, pageConfig] of Object.entries(pages)) {
|
125
|
+
const fnConfig = await lambda_1.getLambdaOptionsFromFunction({
|
126
|
+
sourceFile: pageKey,
|
127
|
+
config: vercelConfig,
|
128
|
+
});
|
129
|
+
functionsManifest.pages[pageKey] = {
|
130
|
+
...pageConfig,
|
131
|
+
memory: fnConfig.memory || pageConfig.memory,
|
132
|
+
maxDuration: fnConfig.maxDuration || pageConfig.maxDuration,
|
133
|
+
regions: vercelConfig.regions || pageConfig.regions,
|
134
|
+
};
|
135
|
+
}
|
136
|
+
await fs_extra_1.default.writeFile(functionsManifestPath, JSON.stringify(functionsManifest));
|
137
|
+
}
|
138
|
+
exports.updateFunctionsManifest = updateFunctionsManifest;
|
139
|
+
/**
|
140
|
+
* Will append routes to the `routes-manifest.json` file.
|
141
|
+
* If the file does not exist, it'll be created.
|
142
|
+
*/
|
143
|
+
async function updateRoutesManifest({ workPath, dynamicRoutes, }) {
|
144
|
+
const routesManifestPath = path_1.join(workPath, '.output', 'routes-manifest.json');
|
145
|
+
const routesManifest = await readJson(routesManifestPath);
|
146
|
+
if (!routesManifest.version)
|
147
|
+
routesManifest.version = 1;
|
148
|
+
if (routesManifest.pages404 === undefined)
|
149
|
+
routesManifest.pages404 = true;
|
150
|
+
if (dynamicRoutes) {
|
151
|
+
if (!routesManifest.dynamicRoutes)
|
152
|
+
routesManifest.dynamicRoutes = [];
|
153
|
+
routesManifest.dynamicRoutes.push(...dynamicRoutes);
|
154
|
+
}
|
155
|
+
await fs_extra_1.default.writeFile(routesManifestPath, JSON.stringify(routesManifest));
|
156
|
+
}
|
157
|
+
exports.updateRoutesManifest = updateRoutesManifest;
|
package/dist/fs/glob.js
CHANGED
@@ -8,6 +8,7 @@ const assert_1 = __importDefault(require("assert"));
|
|
8
8
|
const glob_1 = __importDefault(require("glob"));
|
9
9
|
const util_1 = require("util");
|
10
10
|
const fs_extra_1 = require("fs-extra");
|
11
|
+
const normalize_path_1 = require("./normalize-path");
|
11
12
|
const file_fs_ref_1 = __importDefault(require("../file-fs-ref"));
|
12
13
|
const vanillaGlob = util_1.promisify(glob_1.default);
|
13
14
|
async function glob(pattern, opts, mountpoint) {
|
@@ -31,7 +32,7 @@ async function glob(pattern, opts, mountpoint) {
|
|
31
32
|
options.dot = true;
|
32
33
|
const files = await vanillaGlob(pattern, options);
|
33
34
|
for (const relativePath of files) {
|
34
|
-
const fsPath = path_1.default.join(options.cwd, relativePath)
|
35
|
+
const fsPath = normalize_path_1.normalizePath(path_1.default.join(options.cwd, relativePath));
|
35
36
|
let stat = options.statCache[fsPath];
|
36
37
|
assert_1.default(stat, `statCache does not contain value for ${relativePath} (resolved to ${fsPath})`);
|
37
38
|
const isSymlink = options.symlinks[fsPath];
|
@@ -0,0 +1,11 @@
|
|
1
|
+
"use strict";
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
3
|
+
exports.normalizePath = void 0;
|
4
|
+
const isWin = process.platform === 'win32';
|
5
|
+
/**
|
6
|
+
* Convert Windows separators to Unix separators.
|
7
|
+
*/
|
8
|
+
function normalizePath(p) {
|
9
|
+
return isWin ? p.replace(/\\/g, '/') : p;
|
10
|
+
}
|
11
|
+
exports.normalizePath = normalizePath;
|
package/dist/index.d.ts
CHANGED
@@ -17,6 +17,8 @@ export { detectBuilders, detectOutputDirectory, detectApiDirectory, detectApiExt
|
|
17
17
|
export { detectFramework } from './detect-framework';
|
18
18
|
export { DetectorFilesystem } from './detectors/filesystem';
|
19
19
|
export { readConfigFile } from './fs/read-config-file';
|
20
|
+
export { normalizePath } from './fs/normalize-path';
|
21
|
+
export { convertRuntimeToPlugin, updateFunctionsManifest, updateRoutesManifest, } from './convert-runtime-to-plugin';
|
20
22
|
export * from './schemas';
|
21
23
|
export * from './types';
|
22
24
|
export * from './errors';
|