Compare commits

..

6 Commits

Author SHA1 Message Date
Chris Barber
17a73f4f11 Publish Stable
- vercel@28.7.2
2022-12-02 18:20:48 -06:00
Lee Robinson
2e0cbf10de [cli] Revert replace update-notifier dependency with built in (#9000)
Reverts https://github.com/vercel/vercel/pull/8090.


![image](https://user-images.githubusercontent.com/9113740/205410222-efd63ff6-8094-4cba-8316-559845c64289.png)
2022-12-02 18:20:11 -06:00
Sean Massa
b37ac5f798 Publish Stable
- @vercel/build-utils@5.7.0
 - vercel@28.7.1
 - @vercel/client@12.2.21
 - @vercel/go@2.2.19
 - @vercel/hydrogen@0.0.33
 - @vercel/next@3.3.2
 - @vercel/node@2.7.1
 - @vercel/python@3.1.29
 - @vercel/redwood@1.0.39
 - @vercel/remix@1.1.1
 - @vercel/ruby@1.3.45
 - @vercel/static-build@1.0.42
2022-12-02 14:15:48 -06:00
Sean Massa
01ad4c4c8e [build-utils] expand build result type for framework version (#8984)
Augments the `BuildResultV2Typical` type to support `framework` and `frameworkVersion` for use in Richer Deployment Outputs.

I added this to a new `meta` object because it contains data about the result, not really part of the result.

---

Supports a related builder container update.
2022-12-02 19:54:24 +00:00
Steven
577fd3e979 [cli] Replace update-notifier dependency with built in (#8090)
This PR replaces the `update-notifier` dependency with a custom
implementation.

There are a few reasons: the dependency is quite large, it requires ESM
in order to update, and can sometimes suggest an update to an older
version. For example:


![image](https://user-images.githubusercontent.com/229881/195891579-c8c047a6-51ec-45f2-b597-daf927f48203.png)


- Related to #8038

Co-authored-by: Chris Barber <chris.barber@vercel.com>
Co-authored-by: Chris Barber <chris@cb1inc.com>
Co-authored-by: Sean Massa <EndangeredMassa@gmail.com>
Co-authored-by: kodiakhq[bot] <49736102+kodiakhq[bot]@users.noreply.github.com>
2022-12-01 17:07:52 -06:00
Steven
d649a3c931 [node] Add caching for TS compile per file (#8987)
As a follow up to #8986, we can reduce the TS compile time even more by caching TS compile per file so we never compile the same file twice.  This brings down the total deployment time of a large app with many `api/*.ts` from 7 min to 5 min.

Note: review this PR with [whitespace disabled](https://github.com/vercel/vercel/pull/8987/files?w=1).

- Related to https://github.com/vercel/customer-issues/issues/925
2022-12-01 18:34:56 +00:00
14 changed files with 160 additions and 137 deletions

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/build-utils",
"version": "5.6.0",
"version": "5.7.0",
"license": "MIT",
"main": "./dist/index.js",
"types": "./dist/index.d.js",

View File

@@ -425,6 +425,9 @@ export interface BuildResultV2Typical {
domain: string;
value: string;
}>;
framework?: {
version: string;
};
}
export type BuildResultV2 = BuildResultV2Typical | BuildResultBuildOutput;

View File

@@ -1,6 +1,6 @@
{
"name": "vercel",
"version": "28.7.0",
"version": "28.7.2",
"preferGlobal": true,
"license": "Apache-2.0",
"description": "The command-line interface for Vercel",
@@ -41,16 +41,16 @@
"node": ">= 14"
},
"dependencies": {
"@vercel/build-utils": "5.6.0",
"@vercel/go": "2.2.18",
"@vercel/hydrogen": "0.0.32",
"@vercel/next": "3.3.1",
"@vercel/node": "2.7.0",
"@vercel/python": "3.1.28",
"@vercel/redwood": "1.0.38",
"@vercel/remix": "1.1.0",
"@vercel/ruby": "1.3.44",
"@vercel/static-build": "1.0.41",
"@vercel/build-utils": "5.7.0",
"@vercel/go": "2.2.19",
"@vercel/hydrogen": "0.0.33",
"@vercel/next": "3.3.2",
"@vercel/node": "2.7.1",
"@vercel/python": "3.1.29",
"@vercel/redwood": "1.0.39",
"@vercel/remix": "1.1.1",
"@vercel/ruby": "1.3.45",
"@vercel/static-build": "1.0.42",
"update-notifier": "5.1.0"
},
"devDependencies": {
@@ -95,7 +95,7 @@
"@types/which": "1.3.2",
"@types/write-json-file": "2.2.1",
"@types/yauzl-promise": "2.1.0",
"@vercel/client": "12.2.20",
"@vercel/client": "12.2.21",
"@vercel/error-utils": "1.0.3",
"@vercel/frameworks": "1.1.14",
"@vercel/fs-detectors": "3.5.4",

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/client",
"version": "12.2.20",
"version": "12.2.21",
"main": "dist/index.js",
"typings": "dist/index.d.ts",
"homepage": "https://vercel.com",
@@ -43,7 +43,7 @@
]
},
"dependencies": {
"@vercel/build-utils": "5.6.0",
"@vercel/build-utils": "5.7.0",
"@vercel/routing-utils": "2.1.3",
"@zeit/fetch": "5.2.0",
"async-retry": "1.2.3",

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/go",
"version": "2.2.18",
"version": "2.2.19",
"license": "MIT",
"main": "./dist/index",
"homepage": "https://vercel.com/docs/runtimes#official-runtimes/go",
@@ -35,7 +35,7 @@
"@types/jest": "28.1.6",
"@types/node-fetch": "^2.3.0",
"@types/tar": "^4.0.0",
"@vercel/build-utils": "5.6.0",
"@vercel/build-utils": "5.7.0",
"@vercel/ncc": "0.24.0",
"async-retry": "1.3.1",
"execa": "^1.0.0",

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/hydrogen",
"version": "0.0.32",
"version": "0.0.33",
"license": "MIT",
"main": "./dist/index.js",
"homepage": "https://vercel.com/docs",
@@ -21,7 +21,7 @@
"devDependencies": {
"@types/jest": "27.5.1",
"@types/node": "14.18.33",
"@vercel/build-utils": "5.6.0",
"@vercel/build-utils": "5.7.0",
"@vercel/static-config": "2.0.6",
"typescript": "4.6.4"
}

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/next",
"version": "3.3.1",
"version": "3.3.2",
"license": "MIT",
"main": "./dist/index",
"homepage": "https://vercel.com/docs/runtimes#official-runtimes/next-js",
@@ -45,7 +45,7 @@
"@types/semver": "6.0.0",
"@types/text-table": "0.2.1",
"@types/webpack-sources": "3.2.0",
"@vercel/build-utils": "5.6.0",
"@vercel/build-utils": "5.7.0",
"@vercel/nft": "0.22.1",
"@vercel/routing-utils": "2.1.3",
"async-sema": "3.0.1",

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/node",
"version": "2.7.0",
"version": "2.7.1",
"license": "MIT",
"main": "./dist/index",
"homepage": "https://vercel.com/docs/runtimes#official-runtimes/node-js",
@@ -31,7 +31,7 @@
"dependencies": {
"@edge-runtime/vm": "2.0.0",
"@types/node": "14.18.33",
"@vercel/build-utils": "5.6.0",
"@vercel/build-utils": "5.7.0",
"@vercel/node-bridge": "3.1.2",
"@vercel/static-config": "2.0.6",
"edge-runtime": "2.0.0",

View File

@@ -116,7 +116,7 @@ function cachedLookup<T>(fn: (arg: string) => T): (arg: string) => T {
/**
* Maps the config path to a build func
*/
const configFileToBuildMap = new Map<string, Build>();
const configFileToBuildMap = new Map<string, GetOutputFunction>();
/**
* Register TypeScript compiler.
@@ -189,16 +189,30 @@ export function register(opts: Options = {}): Register {
}
}
function getBuild(configFileName = ''): Build {
let build = configFileToBuildMap.get(configFileName);
if (build) return build;
function getBuild(
configFileName = '',
skipTypeCheck?: boolean
): GetOutputFunction {
const cachedGetOutput = configFileToBuildMap.get(configFileName);
if (cachedGetOutput) {
return cachedGetOutput;
}
const outFiles = new Map<string, SourceOutput>();
const config = readConfig(configFileName);
/**
* Create the basic required function using transpile mode.
* Create the basic function for transpile only (ts-node --transpileOnly)
*/
const getOutput = function (code: string, fileName: string): SourceOutput {
const getOutputTranspile: GetOutputFunction = (
code: string,
fileName: string
) => {
const outFile = outFiles.get(fileName);
if (outFile) {
return outFile;
}
const result = ts.transpileModule(code, {
fileName,
transformers,
@@ -212,114 +226,125 @@ export function register(opts: Options = {}): Register {
reportTSError(diagnosticList, config.options.noEmitOnError);
return { code: result.outputText, map: result.sourceMapText as string };
const file = {
code: result.outputText,
map: result.sourceMapText as string,
};
outFiles.set(fileName, file);
return file;
};
// Use full language services when the fast option is disabled.
let getOutputTypeCheck: (code: string, fileName: string) => SourceOutput;
{
const memoryCache = new MemoryCache(config.fileNames);
const cachedReadFile = cachedLookup(debugFn('readFile', readFile));
const memoryCache = new MemoryCache(config.fileNames);
const cachedReadFile = cachedLookup(readFile);
// Create the compiler host for type checking.
const serviceHost: _ts.LanguageServiceHost = {
getScriptFileNames: () => Array.from(memoryCache.fileVersions.keys()),
getScriptVersion: (fileName: string) => {
const version = memoryCache.fileVersions.get(fileName);
return version === undefined ? '' : version.toString();
},
getScriptSnapshot(fileName: string) {
let contents = memoryCache.fileContents.get(fileName);
// Create the compiler host for type checking.
const serviceHost: _ts.LanguageServiceHost = {
getScriptFileNames: () => Array.from(memoryCache.fileVersions.keys()),
getScriptVersion: (fileName: string) => {
const version = memoryCache.fileVersions.get(fileName);
return version === undefined ? '' : version.toString();
},
getScriptSnapshot(fileName: string) {
let contents = memoryCache.fileContents.get(fileName);
// Read contents into TypeScript memory cache.
if (contents === undefined) {
contents = cachedReadFile(fileName);
if (contents === undefined) return;
// Read contents into TypeScript memory cache.
if (contents === undefined) {
contents = cachedReadFile(fileName);
if (contents === undefined) return;
memoryCache.fileVersions.set(fileName, 1);
memoryCache.fileContents.set(fileName, contents);
}
memoryCache.fileVersions.set(fileName, 1);
memoryCache.fileContents.set(fileName, contents);
}
return ts.ScriptSnapshot.fromString(contents);
},
readFile: cachedReadFile,
readDirectory: cachedLookup(
debugFn('readDirectory', ts.sys.readDirectory)
),
getDirectories: cachedLookup(
debugFn('getDirectories', ts.sys.getDirectories)
),
fileExists: cachedLookup(debugFn('fileExists', fileExists)),
directoryExists: cachedLookup(
debugFn('directoryExists', ts.sys.directoryExists)
),
getNewLine: () => ts.sys.newLine,
useCaseSensitiveFileNames: () => ts.sys.useCaseSensitiveFileNames,
getCurrentDirectory: () => cwd,
getCompilationSettings: () => config.options,
getDefaultLibFileName: () => ts.getDefaultLibFilePath(config.options),
getCustomTransformers: () => transformers,
};
return ts.ScriptSnapshot.fromString(contents);
},
readFile: cachedReadFile,
readDirectory: cachedLookup(
debugFn('readDirectory', ts.sys.readDirectory)
),
getDirectories: cachedLookup(
debugFn('getDirectories', ts.sys.getDirectories)
),
fileExists: cachedLookup(debugFn('fileExists', fileExists)),
directoryExists: cachedLookup(
debugFn('directoryExists', ts.sys.directoryExists)
),
getNewLine: () => ts.sys.newLine,
useCaseSensitiveFileNames: () => ts.sys.useCaseSensitiveFileNames,
getCurrentDirectory: () => cwd,
getCompilationSettings: () => config.options,
getDefaultLibFileName: () => ts.getDefaultLibFilePath(config.options),
getCustomTransformers: () => transformers,
};
const registry = ts.createDocumentRegistry(
ts.sys.useCaseSensitiveFileNames,
cwd
);
const service = ts.createLanguageService(serviceHost, registry);
const registry = ts.createDocumentRegistry(
ts.sys.useCaseSensitiveFileNames,
cwd
);
const service = ts.createLanguageService(serviceHost, registry);
// Set the file contents into cache manually.
const updateMemoryCache = function (contents: string, fileName: string) {
const fileVersion = memoryCache.fileVersions.get(fileName) || 0;
// Set the file contents into cache manually.
const updateMemoryCache = function (contents: string, fileName: string) {
const fileVersion = memoryCache.fileVersions.get(fileName) || 0;
// Avoid incrementing cache when nothing has changed.
if (memoryCache.fileContents.get(fileName) === contents) return;
// Avoid incrementing cache when nothing has changed.
if (memoryCache.fileContents.get(fileName) === contents) return;
memoryCache.fileVersions.set(fileName, fileVersion + 1);
memoryCache.fileContents.set(fileName, contents);
};
memoryCache.fileVersions.set(fileName, fileVersion + 1);
memoryCache.fileContents.set(fileName, contents);
};
getOutputTypeCheck = function (code: string, fileName: string) {
updateMemoryCache(code, fileName);
/**
* Create complete function with full language services (normal behavior for `tsc`)
*/
const getOutputTypeCheck: GetOutputFunction = (
code: string,
fileName: string
) => {
const outFile = outFiles.get(fileName);
if (outFile) {
return outFile;
}
updateMemoryCache(code, fileName);
const output = service.getEmitOutput(fileName);
const output = service.getEmitOutput(fileName);
// Get the relevant diagnostics - this is 3x faster than `getPreEmitDiagnostics`.
const diagnostics = service
.getSemanticDiagnostics(fileName)
.concat(service.getSyntacticDiagnostics(fileName));
// Get the relevant diagnostics - this is 3x faster than `getPreEmitDiagnostics`.
const diagnostics = service
.getSemanticDiagnostics(fileName)
.concat(service.getSyntacticDiagnostics(fileName));
const diagnosticList = filterDiagnostics(
diagnostics,
ignoreDiagnostics
const diagnosticList = filterDiagnostics(diagnostics, ignoreDiagnostics);
reportTSError(diagnosticList, config.options.noEmitOnError);
if (output.emitSkipped) {
throw new TypeError(`${relative(cwd, fileName)}: Emit skipped`);
}
// Throw an error when requiring `.d.ts` files.
if (output.outputFiles.length === 0) {
throw new TypeError(
'Unable to require `.d.ts` file.\n' +
'This is usually the result of a faulty configuration or import. ' +
'Make sure there is a `.js`, `.json` or another executable extension and ' +
'loader (attached before `ts-node`) available alongside ' +
`\`${basename(fileName)}\`.`
);
}
reportTSError(diagnosticList, config.options.noEmitOnError);
if (output.emitSkipped) {
throw new TypeError(`${relative(cwd, fileName)}: Emit skipped`);
}
// Throw an error when requiring `.d.ts` files.
if (output.outputFiles.length === 0) {
throw new TypeError(
'Unable to require `.d.ts` file.\n' +
'This is usually the result of a faulty configuration or import. ' +
'Make sure there is a `.js`, `.json` or another executable extension and ' +
'loader (attached before `ts-node`) available alongside ' +
`\`${basename(fileName)}\`.`
);
}
return {
code: output.outputFiles[1].text,
map: output.outputFiles[0].text,
};
const file = {
code: output.outputFiles[1].text,
map: output.outputFiles[0].text,
};
}
outFiles.set(fileName, file);
return file;
};
build = { getOutput, getOutputTypeCheck };
configFileToBuildMap.set(configFileName, build);
return build;
const getOutput = skipTypeCheck ? getOutputTranspile : getOutputTypeCheck;
configFileToBuildMap.set(configFileName, getOutput);
return getOutput;
}
// determine the tsconfig.json path for a given folder
@@ -407,10 +432,8 @@ export function register(opts: Options = {}): Register {
skipTypeCheck?: boolean
): SourceOutput {
const configFileName = detectConfig();
const build = getBuild(configFileName);
const { code: value, map: sourceMap } = (
skipTypeCheck ? build.getOutput : build.getOutputTypeCheck
)(code, fileName);
const buildOutput = getBuild(configFileName, skipTypeCheck);
const { code: value, map: sourceMap } = buildOutput(code, fileName);
const output = {
code: value,
map: Object.assign(JSON.parse(sourceMap), {
@@ -425,10 +448,7 @@ export function register(opts: Options = {}): Register {
return compile;
}
interface Build {
getOutput(code: string, fileName: string): SourceOutput;
getOutputTypeCheck(code: string, fileName: string): SourceOutput;
}
type GetOutputFunction = (code: string, fileName: string) => SourceOutput;
/**
* Do post-processing on config options to support `ts-node`.

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/python",
"version": "3.1.28",
"version": "3.1.29",
"main": "./dist/index.js",
"license": "MIT",
"homepage": "https://vercel.com/docs/runtimes#official-runtimes/python",
@@ -22,7 +22,7 @@
"devDependencies": {
"@types/execa": "^0.9.0",
"@types/jest": "27.4.1",
"@vercel/build-utils": "5.6.0",
"@vercel/build-utils": "5.7.0",
"@vercel/ncc": "0.24.0",
"execa": "^1.0.0",
"typescript": "4.3.4"

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/redwood",
"version": "1.0.38",
"version": "1.0.39",
"main": "./dist/index.js",
"license": "MIT",
"homepage": "https://vercel.com/docs",
@@ -27,6 +27,6 @@
"@types/aws-lambda": "8.10.19",
"@types/node": "14.18.33",
"@types/semver": "6.0.0",
"@vercel/build-utils": "5.6.0"
"@vercel/build-utils": "5.7.0"
}
}

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/remix",
"version": "1.1.0",
"version": "1.1.1",
"license": "MIT",
"main": "./dist/index.js",
"homepage": "https://vercel.com/docs",
@@ -25,7 +25,7 @@
"devDependencies": {
"@types/jest": "27.5.1",
"@types/node": "14.18.33",
"@vercel/build-utils": "5.6.0",
"@vercel/build-utils": "5.7.0",
"typescript": "4.6.4"
}
}

View File

@@ -1,7 +1,7 @@
{
"name": "@vercel/ruby",
"author": "Nathan Cahill <nathan@nathancahill.com>",
"version": "1.3.44",
"version": "1.3.45",
"license": "MIT",
"main": "./dist/index",
"homepage": "https://vercel.com/docs/runtimes#official-runtimes/ruby",
@@ -22,7 +22,7 @@
"devDependencies": {
"@types/fs-extra": "8.0.0",
"@types/semver": "6.0.0",
"@vercel/build-utils": "5.6.0",
"@vercel/build-utils": "5.7.0",
"@vercel/ncc": "0.24.0",
"execa": "2.0.4",
"fs-extra": "^7.0.1",

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/static-build",
"version": "1.0.41",
"version": "1.0.42",
"license": "MIT",
"main": "./dist/index",
"homepage": "https://vercel.com/docs/build-step",
@@ -36,7 +36,7 @@
"@types/ms": "0.7.31",
"@types/node-fetch": "2.5.4",
"@types/promise-timeout": "1.3.0",
"@vercel/build-utils": "5.6.0",
"@vercel/build-utils": "5.7.0",
"@vercel/frameworks": "1.1.14",
"@vercel/ncc": "0.24.0",
"@vercel/routing-utils": "2.1.3",