Skip to content

Commit 7fb0808

Browse files
authored
Merge pull request #1477 from zloirock/local-website-build
2 parents fe04540 + 9ffc519 commit 7fb0808

File tree

10 files changed

+227
-171
lines changed

10 files changed

+227
-171
lines changed

.github/workflows/build-web-for-branch.yml

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,15 @@ jobs:
3939
username: ci
4040
privateKey: ${{ secrets.CI_SSH_KEY }}
4141

42+
- name: Copy runner helpers file to remote server
43+
uses: garygrossgarten/github-action-scp@0.9.0
44+
with:
45+
local: website/scripts/helpers.mjs
46+
remote: /var/www/core-js/helpers.mjs
47+
host: ${{ secrets.REMOTE_HOST }}
48+
username: ci
49+
privateKey: ${{ secrets.CI_SSH_KEY }}
50+
4251
- name: Setup SSH
4352
uses: webfactory/ssh-agent@v0.9.1
4453
with:

.github/workflows/build-web.yml

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,15 @@ jobs:
3939
username: ci
4040
privateKey: ${{ secrets.CI_SSH_KEY }}
4141

42+
- name: Copy runner helpers file to remote server
43+
uses: garygrossgarten/github-action-scp@0.9.0
44+
with:
45+
local: website/scripts/helpers.mjs
46+
remote: /var/www/core-js/helpers.mjs
47+
host: ${{ secrets.REMOTE_HOST }}
48+
username: ci
49+
privateKey: ${{ secrets.CI_SSH_KEY }}
50+
4251
- name: Setup SSH
4352
uses: webfactory/ssh-agent@v0.9.1
4453
with:

package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919
"prepare": "npm run zxi scripts/prepare.mjs",
2020
"build-compat": "npm run zxi scripts/build-compat/index.mjs",
2121
"build-web": "npm run zxi time website/index.mjs",
22+
"build-web-local": "npm run zxi time website/build-local.mjs",
2223
"bundle": "run-s bundle-package bundle-tests",
2324
"bundle-package": "npm run zxi time scripts/bundle-package/bundle-package.mjs",
2425
"bundle-tests": "npm run zxi time cd scripts/bundle-tests/bundle-tests.mjs",

tests/eslint/eslint.config.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2392,6 +2392,7 @@ export default [
23922392
'tests/compat/*.mjs',
23932393
'tests/@(compat-@(data|tools)|eslint|entries|observables|promises-aplus|unit-@(karma|node))/**',
23942394
'website/runner.mjs',
2395+
'website/helpers.mjs',
23952396
],
23962397
rules: nodeDev,
23972398
},

website/build-local.mjs

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
import {
2+
hasDocs, copyBlogPosts, copyBabelStandalone, copyCommonFiles, buildAndCopyCoreJS, buildWeb, getCurrentBranch,
3+
} from './scripts/helpers.mjs';
4+
5+
const BUILD_SRC_DIR = './';
6+
const BUNDLES_DIR = 'bundles';
7+
8+
try {
9+
console.time('Finished in');
10+
const targetBranch = await getCurrentBranch(BUILD_SRC_DIR);
11+
12+
const version = { branch: targetBranch, label: targetBranch };
13+
await hasDocs(version, BUILD_SRC_DIR);
14+
await buildAndCopyCoreJS(version, false, BUILD_SRC_DIR, BUNDLES_DIR);
15+
16+
await copyBabelStandalone(BUILD_SRC_DIR);
17+
await copyBlogPosts(BUILD_SRC_DIR);
18+
await copyCommonFiles(BUILD_SRC_DIR);
19+
await buildWeb(targetBranch, BUILD_SRC_DIR);
20+
console.timeEnd('Finished in');
21+
} catch (error) {
22+
console.error(error);
23+
}

website/build.mjs

Lines changed: 7 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1,32 +1,26 @@
11
/* eslint-disable import/no-unresolved -- dependencies are not installed */
2+
import { getDefaultVersion } from './scripts/helpers.mjs';
23
import fm from 'front-matter';
34
import { JSDOM } from 'jsdom';
45
import { Marked } from 'marked';
56
import { gfmHeadingId, getHeadingList } from 'marked-gfm-heading-id';
67
import markedAlert from 'marked-alert';
78
import config from './config/config.mjs';
8-
import { fs } from 'zx';
9+
import { argv, fs } from 'zx';
910

1011
const { copy, mkdir, readFile, readJson, readdir, writeFile } = fs;
1112

12-
const args = process.argv;
13-
const lastArg = args.at(-1);
14-
const BRANCH = lastArg.startsWith('branch=') ? lastArg.slice('branch='.length) : undefined;
15-
const DEFAULT_VERSION = await getDefaultVersion();
16-
const BASE = BRANCH ? `/branches/${ BRANCH }/` : '/';
13+
const branchArg = argv._.find(item => item.startsWith('branch='));
14+
const BRANCH = branchArg ? branchArg.slice('branch='.length) : undefined;
15+
const LOCAL = argv._.includes('local');
16+
const BASE = LOCAL && BRANCH ? '/core-js/website/dist/' : BRANCH ? `/branches/${ BRANCH }/` : '/';
17+
const DEFAULT_VERSION = await getDefaultVersion(config.versionsFile, BRANCH);
1718

1819
let htmlFileName = '';
1920
let docsMenu = '';
2021
let isBlog = false;
2122
let isDocs = false;
2223

23-
async function getDefaultVersion() {
24-
if (BRANCH) return BRANCH;
25-
26-
const versions = await readJson(config.versionsFile);
27-
return versions.find(v => v.default)?.label;
28-
}
29-
3024
async function getAllMdFiles(dir) {
3125
const entries = await readdir(dir, { withFileTypes: true });
3226
const files = [];
@@ -209,12 +203,6 @@ async function buildBlogMenu() {
209203
return menu;
210204
}
211205

212-
// eslint-disable-next-line no-unused-vars -- use it later
213-
async function getVersionTags() {
214-
const tagsString = await $`git tag | grep -E "^v[4-9]\\.[0-9]+\\.[0-9]+$" | sort -V`;
215-
return tagsString.stdout.split('\n');
216-
}
217-
218206
async function getVersionFromMdFile(mdPath) {
219207
const match = mdPath.match(/\/web\/(?<version>[^/]+)\/docs\//);
220208
return match?.groups?.version ?? DEFAULT_VERSION;

website/scripts/helpers.mjs

Lines changed: 151 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,151 @@
1+
/* eslint-disable no-console -- needed for logging */
2+
import childProcess from 'node:child_process';
3+
import { constants } from 'node:fs';
4+
import fs from 'node:fs/promises';
5+
import path from 'node:path';
6+
import { promisify } from 'node:util';
7+
8+
const exec = promisify(childProcess.exec);
9+
const { cp, access, readdir, readFile } = fs;
10+
11+
const BABEL_PATH = 'website/node_modules/@babel/standalone/babel.min.js';
12+
13+
export async function isExists(target) {
14+
try {
15+
await access(target, constants.F_OK);
16+
return true;
17+
} catch {
18+
return false;
19+
}
20+
}
21+
22+
export async function hasDocs(version, execDir) {
23+
const target = version.branch ? `origin/${ version.branch }` : version.tag;
24+
console.log(`Checking if docs exist in "${ target }"...`);
25+
try {
26+
await exec(`git ls-tree -r --name-only ${ target } | grep "docs/web/docs/"`, { cwd: execDir });
27+
} catch {
28+
throw new Error(`Docs not found in "${ target }".`);
29+
}
30+
}
31+
32+
export async function installDependencies(execDir) {
33+
console.log('Installing dependencies...');
34+
console.time('Installed dependencies');
35+
await exec('npm ci', { cwd: execDir });
36+
console.timeEnd('Installed dependencies');
37+
}
38+
39+
export async function copyBabelStandalone(srcDir) {
40+
console.log('Copying Babel standalone...');
41+
await installDependencies(`${ srcDir }website`);
42+
console.time('Copied Babel standalone');
43+
const babelPath = `${ srcDir }${ BABEL_PATH }`;
44+
const destPath = `${ srcDir }website/src/public/babel.min.js`;
45+
await cp(babelPath, destPath);
46+
console.timeEnd('Copied Babel standalone');
47+
}
48+
49+
export async function copyBlogPosts(srcDir) {
50+
console.log('Copying blog posts...');
51+
console.time('Copied blog posts');
52+
const fromDir = `${ srcDir }docs/`;
53+
const toDir = `${ srcDir }docs/web/blog/`;
54+
const entries = await readdir(fromDir, { withFileTypes: true });
55+
for (const entry of entries) {
56+
if (entry.isFile()) {
57+
const srcFile = path.join(fromDir, entry.name);
58+
const destFile = path.join(toDir, entry.name);
59+
await cp(srcFile, destFile);
60+
}
61+
}
62+
console.timeEnd('Copied blog posts');
63+
}
64+
65+
export async function copyCommonFiles(srcDir) {
66+
console.log('Copying common files...');
67+
console.time('Copied common files');
68+
const fromDir = `${ srcDir }`;
69+
const toDir = `${ srcDir }docs/web/`;
70+
await cp(`${ fromDir }CHANGELOG.md`, `${ toDir }changelog.md`);
71+
await cp(`${ fromDir }CONTRIBUTING.md`, `${ toDir }contributing.md`);
72+
await cp(`${ fromDir }SECURITY.md`, `${ toDir }security.md`);
73+
console.timeEnd('Copied common files');
74+
}
75+
76+
export async function buildAndCopyCoreJS(version, checkout, srcDir, destDir) {
77+
const target = version.branch ?? version.tag;
78+
const name = version.path ?? version.label;
79+
console.log(`Building and copying core-js for ${ target }`);
80+
const targetBundlePath = `${ destDir }/${ target }/`;
81+
82+
if (await isExists(targetBundlePath)) {
83+
console.time('Core JS bundles copied');
84+
const bundlePath = `${ targetBundlePath }core-js-bundle.js`;
85+
const destBundlePath = `${ srcDir }website/src/public/bundles/${ name }/core-js-bundle.js`;
86+
const esmodulesBundlePath = `${ targetBundlePath }core-js-bundle-esmodules.js`;
87+
const esmodulesDestBundlePath = `${ srcDir }website/src/public/bundles/${ name }/core-js-bundle-esmodules.js`;
88+
await cp(bundlePath, destBundlePath);
89+
await cp(esmodulesBundlePath, esmodulesDestBundlePath);
90+
console.timeEnd('Core JS bundles copied');
91+
return;
92+
}
93+
94+
console.time('Core JS bundles built');
95+
if (checkout) {
96+
await checkoutVersion(version, srcDir);
97+
}
98+
await installDependencies(srcDir);
99+
await exec('npm run bundle-package', { cwd: srcDir });
100+
const bundlePath = `${ srcDir }packages/core-js-bundle/minified.js`;
101+
const destPath = `${ srcDir }website/src/public/bundles/${ name }/core-js-bundle.js`;
102+
const destBundlePath = `${ targetBundlePath }core-js-bundle.js`;
103+
await cp(bundlePath, destPath);
104+
await cp(bundlePath, destBundlePath);
105+
106+
await exec('npm run bundle-package esmodules', { cwd: srcDir });
107+
const esmodulesBundlePath = `${ srcDir }packages/core-js-bundle/minified.js`;
108+
const esmodulesDestBundlePath = `${ srcDir }website/src/public/bundles/${ name }/core-js-bundle-esmodules.js`;
109+
const destEsmodulesBundlePath = `${ targetBundlePath }core-js-bundle-esmodules.js`;
110+
await cp(esmodulesBundlePath, esmodulesDestBundlePath);
111+
await cp(esmodulesBundlePath, destEsmodulesBundlePath);
112+
console.timeEnd('Core JS bundles built');
113+
}
114+
115+
export async function checkoutVersion(version, execDir) {
116+
if (version.branch) {
117+
await exec(`git checkout origin/${ version.branch }`, { cwd: execDir });
118+
} else {
119+
await exec(`git checkout ${ version.tag }`, { cwd: execDir });
120+
}
121+
}
122+
123+
export async function buildWeb(branch, execDir) {
124+
console.log('Building web...');
125+
console.time('Built web');
126+
let command = 'npm run build-web';
127+
if (branch) command += ` branch=${ branch }`;
128+
const stdout = await exec(command, { cwd: execDir });
129+
console.timeEnd('Built web');
130+
return stdout;
131+
}
132+
133+
export async function getCurrentBranch(execDir) {
134+
console.log('Getting current branch...');
135+
console.time('Got current branch');
136+
const { stdout } = await exec('git rev-parse --abbrev-ref HEAD', { cwd: execDir });
137+
console.timeEnd('Got current branch');
138+
return stdout.trim();
139+
}
140+
141+
export async function getDefaultVersion(versionFile, defaultVersion = null) {
142+
if (defaultVersion) return defaultVersion;
143+
144+
const versions = await readJSON(versionFile);
145+
return versions.find(v => v.default)?.label;
146+
}
147+
148+
export async function readJSON(filePath) {
149+
const buffer = await readFile(filePath);
150+
return JSON.parse(buffer);
151+
}

0 commit comments

Comments
 (0)