Compare commits

..

5 Commits

Author SHA1 Message Date
IgorKlopov
dca8b07952 Revert "break intentionally"
This reverts commit 7c9db4da39.
2020-07-24 18:16:03 +03:00
IgorKlopov
7c9db4da39 break intentionally 2020-07-24 16:17:19 +03:00
IgorKlopov
24a229384e remove tests to make it pass 2020-07-24 15:18:05 +03:00
IgorKlopov
ec0f97d093 regress to make it pass 2020-07-24 14:56:11 +03:00
IgorKlopov
4ff3697d81 print the url of static-single-file/first.png 2020-07-24 14:18:47 +03:00
60 changed files with 641 additions and 15664 deletions

View File

@@ -3,6 +3,6 @@
"version": "0.0.0",
"private": true,
"dependencies": {
"@redwoodjs/api": "0.15.0"
"@redwoodjs/api": "0.14.0"
}
}

View File

@@ -7,7 +7,7 @@
]
},
"devDependencies": {
"@redwoodjs/core": "0.15.0"
"@redwoodjs/core": "0.14.0"
},
"eslintConfig": {
"extends": "@redwoodjs/eslint-config"

View File

@@ -6,8 +6,8 @@
"defaults"
],
"dependencies": {
"@redwoodjs/router": "0.15.0",
"@redwoodjs/web": "0.15.0",
"@redwoodjs/router": "0.14.0",
"@redwoodjs/web": "0.14.0",
"prop-types": "^15.7.2",
"react": "^16.13.1",
"react-dom": "^16.13.1"

File diff suppressed because it is too large Load Diff

View File

@@ -685,7 +685,6 @@
{
"name": "RedwoodJS",
"slug": "redwoodjs",
"demo": "https://redwoodjs.now-examples.now.sh",
"logo": "https://raw.githubusercontent.com/vercel/vercel/master/packages/frameworks/logos/redwood.svg",
"tagline": "RedwoodJS is a full-stack framework for the Jamstack.",
"description": "A RedwoodJS app, bootstraped with create-redwood-app.",
@@ -703,7 +702,7 @@
"value": "yarn rw db up --no-db-client --auto-approve && yarn rw build"
},
"devCommand": {
"value": "yarn rw dev --fwd=\"--port=$PORT --open=false\""
"value": "yarn rw dev"
},
"outputDirectory": {
"value": "RedwoodJS default"
@@ -832,7 +831,7 @@
"description": "No framework or a unoptimized framework.",
"settings": {
"buildCommand": {
"placeholder": "`npm run vercel-build` or `npm run build`"
"placeholder": "`npm run now-build` or `npm run build`"
},
"devCommand": {
"placeholder": "None"

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/frameworks",
"version": "0.0.18-canary.2",
"version": "0.0.18-canary.0",
"main": "frameworks.json",
"license": "UNLICENSED",
"scripts": {

View File

@@ -1,6 +1,6 @@
{
"name": "vercel",
"version": "20.0.0-canary.8",
"version": "20.0.0-canary.4",
"preferGlobal": true,
"license": "Apache-2.0",
"description": "The command-line interface for Vercel",
@@ -64,10 +64,10 @@
"dependencies": {
"@vercel/build-utils": "2.4.3-canary.2",
"@vercel/go": "1.1.5-canary.0",
"@vercel/next": "2.6.16",
"@vercel/node": "1.7.5-canary.0",
"@vercel/next": "2.6.14-canary.1",
"@vercel/node": "1.7.4-canary.0",
"@vercel/python": "1.2.2",
"@vercel/redwood": "0.0.2-canary.2",
"@vercel/redwood": "0.0.2-canary.1",
"@vercel/ruby": "1.2.3",
"@vercel/static-build": "0.17.7-canary.1",
"update-notifier": "4.1.0"

View File

@@ -669,7 +669,7 @@ export default async function main(
}
if (err instanceof BuildError) {
output.error(err.message || 'Build failed');
output.error('Build failed');
output.error(
`Check your logs at https://${now.url}/_logs or run ${getCommandName(
`logs ${now.url}`,

View File

@@ -118,16 +118,7 @@ export async function devRouter(
continue;
}
// if the destination is an external URL (rewrite or redirect)
const isDestUrl = isURL(destPath);
if (
routeConfig.check &&
devServer &&
nowConfig &&
phase !== 'hit' &&
!isDestUrl
) {
if (routeConfig.check && devServer && nowConfig && phase !== 'hit') {
const { pathname = '/' } = url.parse(destPath);
const hasDestFile = await devServer.hasFilesystem(
pathname,
@@ -165,6 +156,7 @@ export async function devRouter(
}
}
const isDestUrl = isURL(destPath);
if (isDestUrl) {
result = {
found: true,

View File

@@ -1,7 +1,7 @@
import { join, basename } from 'path';
import chalk from 'chalk';
import { remove } from 'fs-extra';
import { NowContext, ProjectLinkResult, ProjectSettings } from '../../types';
import { NowContext, ProjectLinkResult } from '../../types';
import { NowConfig } from '../dev/types';
import { Output } from '../output';
import {
@@ -142,75 +142,69 @@ export default async function setupAndLink(
if (ctx.localConfig && !(ctx.localConfig instanceof Error)) {
localConfig = ctx.localConfig;
}
client.currentTeam = org.type === 'team' ? org.id : undefined;
const isZeroConfig = !localConfig.builds || localConfig.builds.length === 0;
const now = new Now({
apiUrl,
token,
debug,
currentTeam: client.currentTeam,
});
let deployment = null;
try {
let settings: ProjectSettings = {};
const createArgs: any = {
name: newProjectName,
env: {},
build: { env: {} },
forceNew: undefined,
withCache: undefined,
quiet,
wantsPublic: localConfig.public,
isFile,
type: null,
nowConfig: localConfig,
regions: undefined,
meta: {},
deployStamp: stamp(),
target: undefined,
skipAutoDetectionConfirmation: false,
};
if (isZeroConfig) {
const now = new Now({
apiUrl,
token,
debug,
currentTeam: client.currentTeam,
});
const createArgs: any = {
name: newProjectName,
env: {},
build: { env: {} },
forceNew: undefined,
withCache: undefined,
quiet,
wantsPublic: localConfig.public,
isFile,
type: null,
nowConfig: localConfig,
regions: undefined,
meta: {},
deployStamp: stamp(),
target: undefined,
skipAutoDetectionConfirmation: false,
};
deployment = await createDeploy(
output,
now,
client.currentTeam || 'current user',
[sourcePath],
createArgs,
org,
!isFile,
path
);
const deployment = await createDeploy(
output,
now,
client.currentTeam || 'current user',
[sourcePath],
createArgs,
org,
!isFile,
path
);
if (
!deployment ||
!('code' in deployment) ||
deployment.code !== 'missing_project_settings'
) {
output.error('Failed to detect project settings. Please try again.');
if (output.isDebugEnabled()) {
console.log(deployment);
}
return { status: 'error', exitCode: 1 };
if (
!deployment ||
!('code' in deployment) ||
deployment.code !== 'missing_project_settings'
) {
output.error('Failed to detect project settings. Please try again.');
if (output.isDebugEnabled()) {
console.log(deployment);
}
const { projectSettings, framework } = deployment;
settings = await editProjectSettings(
output,
projectSettings,
framework,
autoConfirm
);
return { status: 'error', exitCode: 1 };
}
const { projectSettings, framework } = deployment;
if (rootDirectory) {
settings.rootDirectory = rootDirectory;
projectSettings.rootDirectory = rootDirectory;
}
const settings = await editProjectSettings(
output,
projectSettings,
framework,
autoConfirm
);
const project = await createProject(client, newProjectName);
await updateProject(client, project.id, settings);
Object.assign(project, settings);

View File

@@ -1,14 +0,0 @@
{
"version": 2,
"rewrites": [
{ "source": "/rewrite", "destination": "https://vercel.com/robots.txt" }
],
"redirects": [
{ "source": "/redirect", "destination": "https://vercel.com/robots.txt" },
{
"source": "/tempRedirect",
"destination": "https://vercel.com/robots.txt",
"permanent": false
}
]
}

View File

@@ -111,7 +111,7 @@ async function exec(directory, args = []) {
}
async function runNpmInstall(fixturePath) {
if (await fs.pathExists(join(fixturePath, 'package.json'))) {
if (await fs.exists(join(fixturePath, 'package.json'))) {
await execa('yarn', ['install'], {
cwd: fixturePath,
shell: true,
@@ -817,20 +817,6 @@ test(
})
);
test(
'[vercel dev] test rewrites and redirects serve correct external content',
testFixtureStdio('test-external-rewrites-and-redirects', async testPath => {
const vcRobots = `https://vercel.com/robots.txt`;
await testPath(200, '/rewrite', /User-Agent: \*/m);
await testPath(308, '/redirect', `Redirecting to ${vcRobots} (308)`, {
Location: vcRobots,
});
await testPath(307, '/tempRedirect', `Redirecting to ${vcRobots} (307)`, {
Location: vcRobots,
});
})
);
test(
'[vercel dev] test rewrites and redirects is case sensitive',
testFixtureStdio('test-routing-case-sensitive', async testPath => {

View File

@@ -500,21 +500,14 @@ CMD ["node", "index.js"]`,
},
}),
},
'project-link-deploy': {
'package.json': '{}',
},
'project-link-zeroconf': {
'package.json': '{}',
'project-link': {
'package.json': JSON.stringify({}),
},
'project-link-confirm': {
'package.json': '{}',
'package.json': JSON.stringify({}),
},
'project-link-dev': {
'package.json': '{}',
},
'project-link-legacy': {
'index.html': 'Hello',
'vercel.json': '{"builds":[{"src":"*.html","use":"@vercel/static"}]}',
'package.json': JSON.stringify({}),
},
'dev-proxy-headers-and-env': {
'package.json': JSON.stringify({}),

View File

@@ -1885,6 +1885,7 @@ test('deploying a file should not show prompts and display deprecation', async t
// Test if the output is really a URL
const { href, host } = new URL(stdout);
t.is(host.split('-')[0], 'files');
console.log('static-single-file/first.png: stdout', stdout);
// Send a test request to the deployment
const response = await fetch(href);
@@ -2321,11 +2322,7 @@ test('render build errors', async t => {
console.log(output.exitCode);
t.is(output.exitCode, 1, formatOutput(output));
t.regex(
output.stderr,
/Command "yarn run build" exited with 1/gm,
formatOutput(output)
);
t.regex(output.stderr, /Build failed/gm, formatOutput(output));
});
test('invalid deployment, projects and alias names', async t => {
@@ -2554,18 +2551,6 @@ test('deploy a Lambda with a specific runtime', async t => {
t.is(build.use, 'vercel-php@0.1.0', JSON.stringify(build, null, 2));
});
test('fail to deploy a Lambda with a specific runtime but without a locked version', async t => {
const directory = fixture('lambda-with-invalid-runtime');
const output = await execute([directory, '--confirm']);
t.is(output.exitCode, 1, formatOutput(output));
t.regex(
output.stderr,
/Function Runtimes must have a valid version/gim,
formatOutput(output)
);
});
test('fail to add a domain without a project', async t => {
const output = await execute(['domains', 'add', 'my-domain.now.sh']);
t.is(output.exitCode, 1, formatOutput(output));
@@ -2661,9 +2646,9 @@ test('ensure `github` and `scope` are not sent to the API', async t => {
t.is(output.exitCode, 0, formatOutput(output));
});
test('should show prompts to set up project during first deploy', async t => {
const directory = fixture('project-link-deploy');
const projectName = `project-link-deploy-${
test('should show prompts to set up project', async t => {
const directory = fixture('project-link');
const projectName = `project-link-${
Math.random().toString(36).split('.')[1]
}`;
@@ -3288,8 +3273,8 @@ test('reject deploying with wrong team .vercel config', async t => {
});
test('[vc link] should show prompts to set up project', async t => {
const dir = fixture('project-link-zeroconf');
const projectName = `project-link-zeroconf-${
const dir = fixture('project-link');
const projectName = `project-link-${
Math.random().toString(36).split('.')[1]
}`;
@@ -3498,61 +3483,6 @@ test('[vc dev] should show prompts to set up project', async t => {
}
});
test('[vc link] should show project prompts but not framework when `builds` defined', async t => {
const dir = fixture('project-link-legacy');
const projectName = `project-link-legacy-${
Math.random().toString(36).split('.')[1]
}`;
// remove previously linked project if it exists
await remove(path.join(dir, '.vercel'));
const vc = execa(binaryPath, ['link', ...defaultArgs], { cwd: dir });
await waitForPrompt(vc, chunk => /Set up [^?]+\?/.test(chunk));
vc.stdin.write('yes\n');
await waitForPrompt(vc, chunk =>
chunk.includes('Which scope should contain your project?')
);
vc.stdin.write('\n');
await waitForPrompt(vc, chunk => chunk.includes('Link to existing project?'));
vc.stdin.write('no\n');
await waitForPrompt(vc, chunk =>
chunk.includes('Whats your projects name?')
);
vc.stdin.write(`${projectName}\n`);
await waitForPrompt(vc, chunk =>
chunk.includes('In which directory is your code located?')
);
vc.stdin.write('\n');
await waitForPrompt(vc, chunk => chunk.includes('Linked to'));
const output = await vc;
// Ensure the exit code is right
t.is(output.exitCode, 0, formatOutput(output));
// Ensure .gitignore is created
t.is((await readFile(path.join(dir, '.gitignore'))).toString(), '.vercel');
// Ensure .vercel/project.json and .vercel/README.txt are created
t.is(
await exists(path.join(dir, '.vercel', 'project.json')),
true,
'project.json should be created'
);
t.is(
await exists(path.join(dir, '.vercel', 'README.txt')),
true,
'README.txt should be created'
);
});
test('[vc dev] should send the platform proxy request headers to frontend dev server ', async t => {
const dir = fixture('dev-proxy-headers-and-env');
const port = 58353;

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/client",
"version": "8.2.2-canary.4",
"version": "8.2.2-canary.3",
"main": "dist/index.js",
"typings": "dist/index.d.ts",
"homepage": "https://vercel.com",

View File

@@ -80,11 +80,7 @@ export default function buildCreateDeployment(version: number) {
rootFiles = [path];
}
let { fileList } = await buildFileTree(
path,
clientOptions.isDirectory,
debug
);
let fileList = await buildFileTree(path, clientOptions.isDirectory, debug);
let configPath: string | undefined;
if (!nowConfig) {

View File

@@ -1,6 +1,6 @@
import buildCreateDeployment from './create-deployment';
export { getVercelIgnore, buildFileTree } from './utils/index';
export { getVercelIgnore } from './utils/index';
export const createDeployment = buildCreateDeployment(2);
export const createLegacyDeployment = buildCreateDeployment(1);
export * from './errors';

View File

@@ -35,7 +35,7 @@ const EVENTS_ARRAY = [
'canceled',
] as const;
export type DeploymentEventType = typeof EVENTS_ARRAY[number];
export type DeploymentEventType = (typeof EVENTS_ARRAY)[number];
export const EVENTS = new Set(EVENTS_ARRAY);
export function getApiDeploymentsUrl(
@@ -69,7 +69,7 @@ export async function parseVercelConfig(filePath?: string): Promise<NowConfig> {
}
}
const maybeRead = async function <T>(path: string, default_: T) {
const maybeRead = async function<T>(path: string, default_: T) {
try {
return await readFile(path, 'utf8');
} catch (err) {
@@ -81,26 +81,19 @@ export async function buildFileTree(
path: string | string[],
isDirectory: boolean,
debug: Debug
): Promise<{ fileList: string[]; ignoreList: string[] }> {
const ignoreList: string[] = [];
): Promise<string[]> {
let fileList: string[];
let { ig, ignores } = await getVercelIgnore(path);
let { ig } = await getVercelIgnore(path);
debug(`Found ${ignores.length} rules in .vercelignore`);
debug(`Found ${ig.ignores.length} rules in .vercelignore`);
debug('Building file tree...');
if (isDirectory && !Array.isArray(path)) {
// Directory path
const ignores = (absPath: string) => {
const rel = relative(path, absPath);
const ignored = ig.ignores(rel);
if (ignored) {
ignoreList.push(rel);
}
return ignored;
};
const cwd = process.cwd();
const ignores = (absPath: string) => ig.ignores(relative(cwd, absPath));
fileList = await readdir(path, [ignores]);
debug(`Found ${fileList.length} files in the specified directory`);
debug(`Read ${fileList.length} files in the specified directory`);
} else if (Array.isArray(path)) {
// Array of file paths
fileList = path;
@@ -111,7 +104,7 @@ export async function buildFileTree(
debug(`Deploying the provided path as single file`);
}
return { fileList, ignoreList };
return fileList;
}
export async function getVercelIgnore(

View File

@@ -14,30 +14,18 @@ const normalizeWindowsPaths = (files: string[]) => {
const toAbsolutePaths = (cwd: string, files: string[]) =>
files.map(p => join(cwd, p));
describe('buildFileTree()', () => {
describe('buildFileTree', () => {
it('should exclude files using `.nowignore` blocklist', async () => {
const cwd = fixture('nowignore');
const { fileList, ignoreList } = await buildFileTree(cwd, true, noop);
const expectedFileList = toAbsolutePaths(cwd, ['.nowignore', 'index.txt']);
expect(normalizeWindowsPaths(expectedFileList).sort()).toEqual(
normalizeWindowsPaths(fileList).sort()
);
const expectedIgnoreList = [
'ignore.txt',
'folder/ignore.txt',
'node_modules/ignore.txt',
];
expect(normalizeWindowsPaths(expectedIgnoreList).sort()).toEqual(
normalizeWindowsPaths(ignoreList).sort()
const expected = toAbsolutePaths(cwd, ['.nowignore', 'index.txt']);
const actual = await buildFileTree(cwd, true, noop);
expect(normalizeWindowsPaths(expected).sort()).toEqual(
normalizeWindowsPaths(actual).sort()
);
});
it('should include the node_modules using `.vercelignore` allowlist', async () => {
const cwd = fixture('vercelignore-allow-nodemodules');
const { fileList, ignoreList } = await buildFileTree(cwd, true, noop);
const expected = toAbsolutePaths(cwd, [
'node_modules/one.txt',
'sub/node_modules/two.txt',
@@ -45,13 +33,9 @@ describe('buildFileTree()', () => {
'.vercelignore',
'hello.txt',
]);
const actual = await buildFileTree(cwd, true, noop);
expect(normalizeWindowsPaths(expected).sort()).toEqual(
normalizeWindowsPaths(fileList).sort()
);
const expectedIgnoreList = ['.env.local', 'exclude.txt'];
expect(normalizeWindowsPaths(expectedIgnoreList).sort()).toEqual(
normalizeWindowsPaths(ignoreList).sort()
normalizeWindowsPaths(actual).sort()
);
});
});

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/next",
"version": "2.6.16",
"version": "2.6.14-canary.1",
"license": "MIT",
"main": "./dist/index",
"homepage": "https://vercel.com/docs/runtimes#official-runtimes/next-js",
@@ -26,7 +26,7 @@
"@types/resolve-from": "5.0.1",
"@types/semver": "6.0.0",
"@types/yazl": "2.4.1",
"@zeit/node-file-trace": "0.8.1",
"@zeit/node-file-trace": "0.8.0",
"async-sema": "3.0.1",
"buffer-crc32": "0.2.13",
"escape-string-regexp": "3.0.0",

View File

@@ -880,13 +880,7 @@ export const build = async ({
!prerenderManifest.fallbackRoutes[route] &&
!prerenderManifest.legacyBlockingRoutes[route]
) {
// if the 404 page used getStaticProps we need to update static404Page
// since it wasn't populated from the staticPages group
if (route === '/404') {
static404Page = path.join(entryDirectory, '404');
}
nonLambdaSsgPages.add(route === '/' ? '/index' : route);
nonLambdaSsgPages.add(route);
}
};

View File

@@ -3,13 +3,13 @@
"builds": [{ "src": "package.json", "use": "@vercel/next" }],
"probes": [
{
"path": "/_next/__NEXT_SCRIPT__(/)",
"path": "/_next/static/testing-build-id/pages/index.js",
"responseHeaders": {
"cache-control": "public,max-age=31536000,immutable"
}
},
{
"path": "/_next/static/invalid-build-id/pages/non-existent.js",
"path": "/_next/static/invalid-build-id/pages/index.js",
"notResponseHeaders": {
"cache-control": "public,max-age=31536000,immutable"
}

View File

@@ -1,6 +1,6 @@
{
"dependencies": {
"next": "canary",
"next": "latest",
"react": "^16.8.6",
"react-dom": "^16.8.6"
}

View File

@@ -1,6 +1,6 @@
{
"dependencies": {
"next": "canary",
"next": "^9.1.2-canary.8",
"react": "^16.8.6",
"react-dom": "^16.8.6"
}

View File

@@ -1,6 +1,6 @@
{
"dependencies": {
"next": "canary",
"next": "9.2.1-canary.3",
"react": "^16.8.6",
"react-dom": "^16.8.6"
}

View File

@@ -1,6 +1,6 @@
{
"dependencies": {
"next": "canary",
"next": "latest",
"react": "^16.8.6",
"react-dom": "^16.8.6"
}

View File

@@ -3,7 +3,7 @@
"build": "next build"
},
"dependencies": {
"next": "canary",
"next": "^9.1.2-canary.8",
"react": "^16.8.6",
"react-dom": "^16.8.6"
}

View File

@@ -1,5 +0,0 @@
module.exports = {
generateBuildId() {
return 'testing-build-id';
},
};

View File

@@ -1,42 +0,0 @@
{
"version": 2,
"builds": [{ "src": "package.json", "use": "@now/next" }],
"probes": [
{
"path": "/",
"mustContain": "hello from index"
},
{
"path": "/index",
"mustContain": "hello from index"
},
{
"path": "/nested-index/index",
"mustContain": "hello from nested index"
},
{
"path": "/sub",
"mustContain": "hello from sub index"
},
{
"path": "/sub/index",
"mustContain": "hello from sub id"
},
{
"path": "/sub/another",
"mustContain": "hello from sub id"
},
{
"path": "/api/sub",
"mustContain": "hi from sub index"
},
{
"path": "/api/sub/index",
"mustContain": "hi from sub id"
},
{
"path": "/api/sub/another",
"mustContain": "hi from sub id"
}
]
}

View File

@@ -1,7 +0,0 @@
{
"dependencies": {
"next": "latest",
"react": "^16.8.6",
"react-dom": "^16.8.6"
}
}

View File

@@ -1 +0,0 @@
export default (req, res) => res.end('hi from sub id')

View File

@@ -1 +0,0 @@
export default (req, res) => res.end('hi from sub index');

View File

@@ -1,2 +0,0 @@
const page = () => 'hello from index';
export default page;

View File

@@ -1 +0,0 @@
export default () => 'hello from nested index';

View File

@@ -1,3 +0,0 @@
const page = () => "hello from sub id"
page.getInitialProps = () => ({ hello: 'hi' })
export default page

View File

@@ -1,3 +0,0 @@
const page = () => 'hello from sub index';
page.getInitialProps = () => ({ hello: 'hi' });
export default page;

View File

@@ -1,5 +0,0 @@
module.exports = {
generateBuildId() {
return 'testing-build-id';
},
};

View File

@@ -1,113 +0,0 @@
{
"version": 2,
"uploadNowJson": true,
"builds": [{ "src": "package.json", "use": "@vercel/next" }],
"probes": [
{
"path": "/forever",
"status": 200,
"mustContain": "hello"
},
{
"path": "/blog/post-1",
"status": 200,
"mustContain": "post-1"
},
{
"path": "/blog/post-2",
"status": 200,
"mustContain": "post-2"
},
{
"path": "/_next/data/testing-build-id/blog/post-1.json",
"status": 200,
"mustContain": "post-1"
},
{
"path": "/_next/data/testing-build-id/blog/post-2.json",
"status": 200,
"mustContain": "post-2"
},
{
"path": "/blog/post-1/comment-1",
"status": 200,
"mustContain": "comment-1"
},
{
"path": "/blog/post-2/comment-2",
"status": 200,
"mustContain": "comment-2"
},
{
"path": "/_next/data/testing-build-id/blog/post-1/comment-1.json",
"status": 200,
"mustContain": "comment-1"
},
{
"path": "/_next/data/testing-build-id/blog/post-2/comment-2.json",
"status": 200,
"mustContain": "comment-2"
},
{
"path": "/_next/data/testing-build-id/forever.json",
"status": 200,
"mustContain": "world"
},
{
"path": "/_next/data/testing-build-id/another2.json",
"status": 200,
"mustContain": "world"
},
{
"path": "/nofallback/one",
"status": 200,
"mustContain": "one"
},
{
"path": "/nofallback/two",
"status": 200,
"mustContain": "two"
},
{
"path": "/nofallback/nope",
"status": 404,
"mustContain": "page not <!-- -->found"
},
{
"path": "/_next/data/testing-build-id/nofallback/one.json",
"status": 200,
"mustContain": "one"
},
{
"path": "/_next/data/testing-build-id/nofallback/two.json",
"status": 200,
"mustContain": "two"
},
{
"path": "/_next/data/testing-build-id/nofallback/nope.json",
"status": 404
},
{
"path": "/404",
"status": 404,
"mustContain": "page not <!-- -->found"
},
{
"logMustNotContain": "WARNING: your application is being opted out of @vercel/next's optimized lambdas mode due to legacy routes"
},
{
"logMustNotContain": "WARNING: Your application is being opted out of \"@vercel/next\" optimized lambdas mode due to `functions` config"
},
{
"logMustNotContain": "Traced Next.js serverless functions for external files in"
},
{
"logMustNotContain": "All serverless functions created in"
},
{
"logMustNotContain": "Compressed shared serverless function files"
}
]
}

View File

@@ -1,7 +0,0 @@
{
"dependencies": {
"next": "canary",
"react": "^16.8.6",
"react-dom": "^16.8.6"
}
}

View File

@@ -1,11 +0,0 @@
export default function Page({ found }) {
return <p>page not {found}</p>;
}
export const getStaticProps = () => {
return {
props: {
found: 'found',
},
};
};

View File

@@ -1,22 +0,0 @@
import React from 'react';
// eslint-disable-next-line camelcase
export async function getStaticProps() {
return {
props: {
world: 'world',
random: Math.random(),
time: new Date().getTime(),
},
};
}
export default ({ world, time, random }) => {
return (
<>
<p id="hello">hello: {world}</p>
<span id="time">time: {time}</span>
<span id="random">random: {random}</span>
</>
);
};

View File

@@ -1,20 +0,0 @@
import React from 'react';
// eslint-disable-next-line camelcase
export async function getStaticProps() {
return {
props: {
world: 'world',
time: new Date().getTime(),
},
};
}
export default ({ world, time }) => {
return (
<>
<p>hello: {world}</p>
<span>time: {time}</span>
</>
);
};

View File

@@ -1,39 +0,0 @@
import React from 'react';
// eslint-disable-next-line camelcase
export async function getStaticPaths() {
return {
paths: [
'/blog/post-1/comment-1',
{ params: { post: 'post-2', comment: 'comment-2' } },
'/blog/post-1337/comment-1337',
'/blog/post-123/comment-321',
],
fallback: false,
};
}
// eslint-disable-next-line camelcase
export async function getStaticProps({ params }) {
return {
props: {
post: params.post,
random: Math.random(),
comment: params.comment,
time: new Date().getTime(),
},
};
}
export default ({ post, comment, time, random }) => {
if (!post) return <p>loading...</p>;
return (
<>
<p id="post">Post: {post}</p>
<p id="comment">Comment: {comment}</p>
<span id="time">time: {time}</span>
<span id="random">random: {random}</span>
</>
);
};

View File

@@ -1,38 +0,0 @@
import React from 'react';
// eslint-disable-next-line camelcase
export async function getStaticPaths() {
return {
paths: ['/blog/post-1', { params: { post: 'post-2' } }, '/blog/post-123'],
fallback: false,
};
}
// eslint-disable-next-line camelcase
export async function getStaticProps({ params }) {
if (params.post === 'post-10') {
await new Promise(resolve => {
setTimeout(() => resolve(), 1000);
});
}
return {
props: {
post: params.post,
random: Math.random(),
time: (await import('perf_hooks')).performance.now(),
},
};
}
export default ({ post, time, random }) => {
if (!post) return <p>loading...</p>;
return (
<>
<p id="post">Post: {post}</p>
<span id="time">time: {time}</span>
<span id="random">random: {random}</span>
</>
);
};

View File

@@ -1,21 +0,0 @@
import React from 'react';
// eslint-disable-next-line camelcase
export async function getStaticProps() {
return {
props: {
world: 'world',
time: new Date().getTime(),
},
revalidate: false,
};
}
export default ({ world, time }) => {
return (
<>
<p>hello: {world}</p>
<span>time: {time}</span>
</>
);
};

View File

@@ -1,9 +0,0 @@
export default () => 'Hi';
export const getStaticProps = () => {
return {
props: {
hello: 'world',
},
};
};

View File

@@ -1,30 +0,0 @@
import React from 'react';
// eslint-disable-next-line camelcase
export async function getStaticPaths() {
return {
paths: ['/nofallback/one', { params: { slug: 'two' } }],
fallback: false,
};
}
// eslint-disable-next-line camelcase
export async function getStaticProps({ params }) {
return {
props: {
slug: params.slug,
time: (await import('perf_hooks')).performance.now(),
},
};
}
export default ({ slug, time }) => {
return (
<>
<p>
Slug ({slug.length}): {slug}
</p>
<span>time: {time}</span>
</>
);
};

View File

@@ -1,9 +0,0 @@
export default () => 'Hi';
export const getStaticProps = () => {
return {
props: {
hello: 'world',
},
};
};

View File

@@ -1,9 +1 @@
export default () => 'Hi';
export const getStaticProps = () => {
return {
props: {
hello: 'world',
},
};
};

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/node",
"version": "1.7.5-canary.0",
"version": "1.7.4-canary.0",
"license": "MIT",
"main": "./dist/index",
"homepage": "https://vercel.com/docs/runtimes#official-runtimes/node-js",
@@ -33,7 +33,7 @@
"@types/etag": "1.8.0",
"@types/test-listen": "1.1.0",
"@zeit/ncc": "0.20.4",
"@zeit/node-file-trace": "0.8.1",
"@zeit/node-file-trace": "0.8.0",
"content-type": "1.0.4",
"cookie": "0.4.0",
"etag": "1.8.1",

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/routing-utils",
"version": "1.8.4-canary.0",
"version": "1.8.3",
"description": "Vercel routing utilities",
"main": "./dist/index.js",
"types": "./dist/index.d.ts",

View File

@@ -218,42 +218,18 @@ function replaceSegments(
return destination;
}
function safelyCompile(
value: string,
indexes: { [k: string]: string }
): string {
if (!value) {
return value;
function safelyCompile(str: string, indexes: { [k: string]: string }): string {
if (!str) {
return str;
}
for (const key of Object.keys(indexes)) {
if (value.includes(`:${key}`)) {
value = value
.replace(
new RegExp(`:${key}\\*`, 'g'),
`:${key}--ESCAPED_PARAM_ASTERISK`
)
.replace(
new RegExp(`:${key}\\?`, 'g'),
`:${key}--ESCAPED_PARAM_QUESTION`
)
.replace(new RegExp(`:${key}\\+`, 'g'), `:${key}--ESCAPED_PARAM_PLUS`)
.replace(
new RegExp(`:${key}(?!\\w)`, 'g'),
`--ESCAPED_PARAM_COLON${key}`
);
}
}
value = value
.replace(/(:|\*|\?|\+|\(|\)|\{|\})/g, '\\$1')
.replace(/--ESCAPED_PARAM_PLUS/g, '+')
.replace(/--ESCAPED_PARAM_COLON/g, ':')
.replace(/--ESCAPED_PARAM_QUESTION/g, '?')
.replace(/--ESCAPED_PARAM_ASTERISK/g, '*');
// the value needs to start with a forward-slash to be compiled
// correctly
return compile(`/${value}`, { validate: false })(indexes).substr(1);
// path-to-regexp cannot compile question marks
return str
.split('?')
.map(part => {
const compiler = compile(part);
return compiler(indexes);
})
.join('?');
}
function toSegmentDest(index: number): string {

View File

@@ -508,60 +508,6 @@ test('convertHeaders', () => {
},
],
},
{
source: '/like/params/:path',
headers: [
{
key: 'x-path',
value: ':path',
},
{
key: 'some:path',
value: 'hi',
},
{
key: 'x-test',
value: 'some:value*',
},
{
key: 'x-test-2',
value: 'value*',
},
{
key: 'x-test-3',
value: ':value?',
},
{
key: 'x-test-4',
value: ':value+',
},
{
key: 'x-test-5',
value: 'something https:',
},
{
key: 'x-test-6',
value: ':hello(world)',
},
{
key: 'x-test-7',
value: 'hello(world)',
},
{
key: 'x-test-8',
value: 'hello{1,}',
},
{
key: 'x-test-9',
value: ':hello{1,2}',
},
{
key: 'content-security-policy',
value:
"default-src 'self'; img-src *; media-src media1.com media2.com; script-src userscripts.example.com/:path",
},
],
},
]);
const expected = [
@@ -580,25 +526,6 @@ test('convertHeaders', () => {
headers: { 'on-blog': '$1', $1: 'blog' },
continue: true,
},
{
continue: true,
headers: {
'content-security-policy':
"default-src 'self'; img-src *; media-src media1.com media2.com; script-src userscripts.example.com/$1",
some$1: 'hi',
'x-path': '$1',
'x-test': 'some:value*',
'x-test-2': 'value*',
'x-test-3': ':value?',
'x-test-4': ':value+',
'x-test-5': 'something https:',
'x-test-6': ':hello(world)',
'x-test-7': 'hello(world)',
'x-test-8': 'hello{1,}',
'x-test-9': ':hello{1,2}',
},
src: '^\\/like\\/params(?:\\/([^\\/]+?))$',
},
];
deepEqual(actual, expected);
@@ -607,14 +534,12 @@ test('convertHeaders', () => {
['hello/world/file.eot', 'another/font.ttf', 'dir/arial.font.css'],
['404.html'],
['/blog/first-post', '/blog/another/one'],
['/like/params/first', '/like/params/second'],
];
const mustNotMatch = [
['hello/file.jpg', 'hello/font-css', 'dir/arial.font-css'],
['403.html', '500.html'],
['/blogg', '/random'],
['/non-match', '/like/params', '/like/params/'],
];
assertRegexMatches(actual, mustMatch, mustNotMatch);

View File

@@ -1,6 +1,6 @@
{
"name": "@vercel/redwood",
"version": "0.0.2-canary.2",
"version": "0.0.2-canary.1",
"main": "./dist/index.js",
"license": "MIT",
"homepage": "https://vercel.com/docs",

View File

@@ -3,6 +3,6 @@
"version": "0.0.0",
"private": true,
"dependencies": {
"@redwoodjs/api": "0.15.0"
"@redwoodjs/api": "0.14.0"
}
}

View File

@@ -7,7 +7,7 @@
]
},
"devDependencies": {
"@redwoodjs/core": "0.15.0"
"@redwoodjs/core": "0.14.0"
},
"engines": {
"node": ">=12",

View File

@@ -14,7 +14,7 @@
"method": "POST",
"headers": { "Accept": "application/json" },
"body": { "query": "{ redwood { version } }" },
"mustContain": "0.15.0"
"mustContain": "0.14.0"
}
]
}

View File

@@ -6,8 +6,8 @@
"defaults"
],
"dependencies": {
"@redwoodjs/router": "0.15.0",
"@redwoodjs/web": "0.15.0",
"@redwoodjs/router": "0.14.0",
"@redwoodjs/web": "0.14.0",
"prop-types": "^15.7.2",
"react": "^16.13.1",
"react-dom": "^16.13.1"

File diff suppressed because it is too large Load Diff

View File

@@ -2292,10 +2292,10 @@
resolved "https://registry.yarnpkg.com/@zeit/ncc/-/ncc-0.20.4.tgz#00f0a25a88cac3712af4ba66561d9e281c6f05c9"
integrity sha512-fmq+F/QxPec+k/zvT7HiVpk7oiGFseS6brfT/AYqmCUp6QFRK7vZf2Ref46MImsg/g2W3g5X6SRvGRmOAvEfdA==
"@zeit/node-file-trace@0.8.1":
version "0.8.1"
resolved "https://registry.yarnpkg.com/@zeit/node-file-trace/-/node-file-trace-0.8.1.tgz#ace86b366c86f0522e953a2441dfc915fd485df4"
integrity sha512-r92pdExhK1cf9Ao5LaT/Ii7JLwv9O4o987cB1SiFIbAnxvW4+xqR1oCYRRvtjU1ildKKGpiBBjGRChyeYRcvxw==
"@zeit/node-file-trace@0.8.0":
version "0.8.0"
resolved "https://registry.yarnpkg.com/@zeit/node-file-trace/-/node-file-trace-0.8.0.tgz#fe597a8f63c1a6eb38cee92ab4eef322897b4173"
integrity sha512-itrVZUwqJSbURaRNxOAJUVkhCjl8BgQpTxy+i5m4Akdacn5CzKAHlschTcTvdcnYGtKoilDwYFuPenS5zHfDQw==
dependencies:
acorn "^7.1.1"
acorn-class-fields "^0.3.2"