Skip to content

Commit 91e77c9

Browse files
committed
Addition of an ESBuild sample
1 parent 5d892cc commit 91e77c9

File tree

12 files changed

+1892
-0
lines changed

12 files changed

+1892
-0
lines changed

esbuild-sample/.eslintrc.js

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
/**@type {import('eslint').Linter.Config} */
2+
// eslint-disable-next-line no-undef
3+
module.exports = {
4+
root: true,
5+
parser: '@typescript-eslint/parser',
6+
plugins: ['@typescript-eslint'],
7+
extends: ['eslint:recommended', 'plugin:@typescript-eslint/recommended'],
8+
rules: {
9+
semi: [2, 'always'],
10+
'@typescript-eslint/no-unused-vars': 0,
11+
'@typescript-eslint/no-explicit-any': 0,
12+
'@typescript-eslint/explicit-module-boundary-types': 0,
13+
'@typescript-eslint/no-non-null-assertion': 0,
14+
},
15+
};

esbuild-sample/.gitignore

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
dist
2+
node_modules
3+
*.vsix
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
{
2+
// See https://go.microsoft.com/fwlink/?LinkId=827846 to learn about workspace recommendations.
3+
// Extension identifier format: ${publisher}.${name}. Example: vscode.csharp
4+
5+
// List of extensions which should be recommended for users of this workspace.
6+
"recommendations": ["dbaeumer.vscode-eslint"]
7+
}

esbuild-sample/.vscode/launch.json

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
// A launch configuration that compiles the extension and then opens it inside a new window
2+
{
3+
"version": "0.2.0",
4+
"configurations": [
5+
{
6+
"name": "Launch Extension",
7+
"type": "extensionHost",
8+
"request": "launch",
9+
"runtimeExecutable": "${execPath}",
10+
"args": ["--extensionDevelopmentPath=${workspaceFolder}"],
11+
"outFiles": ["${workspaceFolder}/dist/**/*.js"],
12+
"preLaunchTask": "npm: build"
13+
},
14+
{
15+
"name": "Launch Web Extension",
16+
"type": "extensionHost",
17+
"request": "launch",
18+
"runtimeExecutable": "${execPath}",
19+
"args": [
20+
"--extensionDevelopmentKind=web",
21+
"--extensionDevelopmentPath=${workspaceFolder}"
22+
],
23+
"outFiles": ["${workspaceFolder}/dist/**/*.js"],
24+
"preLaunchTask": "npm: build"
25+
}
26+
]
27+
}

esbuild-sample/.vscodeignore

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
.vscode
2+
node_modules
3+
src/**
4+
package-lock.json
5+
tsconfig.json
6+
build.mjs

esbuild-sample/README.md

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
# ESBuild & Extensions
2+
3+
This is an extension that uses [https://esbuild.github.io/]() to bundle and minify its sources. Using ESBuild will help to reduce the install- and startup-time of large extensions because instead of hundreds of files, a single file is produced. It is also much faster than the [Webpack](https://github.com/microsoft/vscode-extension-samples/tree/main/webpack-sample) alternative and should be preferred.
4+
5+
## Configuration
6+
7+
ESBuild is configured in the [`build.mjs`](./build.mjs)-file. Find annotation inside the file itself or refer to the excellent ESBuild documentation: [https://esbuild.github.io/api/](). In short, the config-files defines the entry point of the extension, to use TypeScript, to produce a commonjs-module, and what modules not to bundle.
8+
9+
## Web Extension Support
10+
11+
This ESBuild config is already setup to support both Desktop and Web extensions, it will build both versions in parallel. The package.json then has a "browser" and "main" entry to point to the correct bundles once built.
12+
13+
## Scripts
14+
15+
The `scripts`-section of the [`package.json`](./package.json)-file has entries for ESBuild. Those compile TypeScript and produce the bundle as well as producing a minified production build.

esbuild-sample/build.mjs

Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,57 @@
1+
/*---------------------------------------------------------------------------------------------
2+
* Copyright (c) Microsoft Corporation. All rights reserved.
3+
* Licensed under the MIT License. See License.txt in the project root for license information.
4+
*--------------------------------------------------------------------------------------------*/
5+
6+
import esbuild from 'esbuild';
7+
import console from 'node:console';
8+
import process from 'node:process';
9+
10+
const production = process.argv[2] === '--production';
11+
const watch = process.argv[2] === '--watch';
12+
let desktopContext, browserContext;
13+
14+
// This is the base config that will be used by both web and desktop versions of the extension
15+
const baseConfig = {
16+
entryPoints: ['./src/extension.ts'], // the entry point of this extension, 📖 -> https://esbuild.github.io/api/#entry-points
17+
bundle: true,
18+
external: ['vscode'], // the vscode-module is created on-the-fly and must be excluded. Add other modules that cannot be packaged, 📖 -> https://esbuild.github.io/api/#external
19+
sourcemap: !production,
20+
minify: production,
21+
format: 'cjs',
22+
target: 'ES2022', // VS Code 1.82 onwards will support ES2022, this also overrides tsconfig.json.
23+
};
24+
25+
// Build both desktop and web versions of the extension in parallel
26+
// By using .context() instead of .build() we can rebuild in watch mode when the source changes
27+
try {
28+
[desktopContext, browserContext] = await Promise.all([
29+
// https://esbuild.github.io/getting-started/#bundling-for-node
30+
esbuild.context({
31+
...baseConfig,
32+
outfile: './dist/extension.js',
33+
platform: 'node',
34+
}),
35+
// If you're building for the browser, you'll need to generate a second bundle which is suitable
36+
// https://esbuild.github.io/getting-started/#bundling-for-the-browser
37+
esbuild.context({
38+
...baseConfig,
39+
outfile: './dist/browser.js',
40+
platform: 'browser',
41+
}),
42+
]);
43+
} catch (e) {
44+
console.error(e);
45+
process.exit(1);
46+
}
47+
48+
if (watch) {
49+
await desktopContext.watch();
50+
await browserContext.watch();
51+
} else {
52+
desktopContext.rebuild();
53+
browserContext.rebuild();
54+
55+
desktopContext.dispose();
56+
browserContext.dispose();
57+
}

0 commit comments

Comments
 (0)