Skip to content

Commit

Permalink
initial commit
Browse files Browse the repository at this point in the history
  • Loading branch information
greggman committed Jan 4, 2025
0 parents commit 5b80d23
Show file tree
Hide file tree
Showing 16 changed files with 1,738 additions and 0 deletions.
99 changes: 99 additions & 0 deletions .github/workflows/build.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
name: Build cross platform

permissions:
contents: write

# Controls when the action will run. Triggers the workflow on push
on:
push:
pull_request:
release:
# tags:
# - 'v*' # Push events to matching v*, i.e. v1.0, v20.15.10

jobs:
build:
name: ${{ matrix.config.name }}
runs-on: ${{ matrix.config.os }}
strategy:
fail-fast: false
matrix:
config:
- {
name: "Windows Latest MSVC",
os: windows-latest,
artifact: win32-x64,
}
- {
name: "Ubuntu_Latest_GCC",
os: ubuntu-latest,
artifact: linux-x64,
}
- {
name: "macOS Latest Clang",
os: macos-latest,
artifact: darwin-arm64,
}

steps:
# Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it
- name: Checkout
uses: actions/checkout@v4
with:
persist-credentials: false

- name: Use Node.js
uses: actions/setup-node@v4
with:
node-version: '20.x'

- name: Print env
run: |
echo github.event.action: ${{ github.event.action }}
echo github.event_name: ${{ github.event_name }}
- name: Install dependencies on windows
if: startsWith(matrix.config.os, 'windows')
run: |
choco install node cmake
node --version
cmake --version
"C:/Program Files/Microsoft Visual Studio/2022/Enterprise/VC/Auxiliary/Build/vcvars64.bat"
- name: Add msbuild to PATH
if: startsWith(matrix.config.os, 'windows')
uses: microsoft/setup-msbuild@v2

- name: Install dependencies on ubuntu
if: startsWith(matrix.config.name, 'Ubuntu_Latest_GCC')
run: |
sudo apt-get update
sudo apt-get install cmake
cmake --version
gcc --version
- name: Install dependencies on macos
if: startsWith(matrix.config.os, 'macos')
run: |
brew install cmake
cmake --version
- name: Build
shell: bash
run: |
npm ci
npm run build
- name: Upload Artifact ⬆️
uses: actions/upload-artifact@v4
with:
path: ./dist/*.dawn.node
name: ${{ matrix.config.artifact }}.dawn.node
overwrite: true

- name: Release
uses: softprops/action-gh-release@v2
if: startsWith(github.ref, 'refs/tags/')
with:
files: dist/*.dawn.node

4 changes: 4 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
*.pyc
.DS_Store
node_modules
dist
6 changes: 6 additions & 0 deletions .gitmodules
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
[submodule "dawn"]
path = third_party/dawn
url = https://dawn.googlesource.com/dawn.git
[submodule "depot_tools"]
path = third_party/depot_tools
url = https://chromium.googlesource.com/chromium/tools/depot_tools.git
96 changes: 96 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,96 @@
# webgpu - dawn.node bundler.

This is a script to bundle/package dawn.node and hopefully publish it on npm

[Dawn](https://dawn.googlesource.com/dawn) is an implementation of [WebGPU](https://gpuweb.github.io/gpuweb/).
It includes a node plugin and this repo builds that plugin.

# Updating

This updates to the latest dawn and depot_tools

```sh
npm ci
npm run update
```

# Publishing

To publish

1. Bump the package version and tag.

The easiest way is `npm version patch`

2. Push the patch

```sh
git push --tag origin main
```

3. Wait for github actions to successfully build all the versions

4. Run `npm run publish`

This will download the files from the latest release to the `dist` folder
and then publish them.

```sh
npm run login <your-publisher-id>
```

Then run `npm run publish`

# Building on all supported platforms

Push a new version. Check the github actions. You should see build artifacts
added to the bottom of the latest action run.

# Building

This builds for the local OS (win64,macOS-intel,macOS-arm,linux)

```sh
npm ci
npm run build
```

## Prerequisites

### Windows

Before running the build script above you must have
Visual Studio C++ installed and have run the `vcvars64.bat` file.
I've tested with Visual Studio Community Edition 2022

Further you must have [cmake installed](https://cmake.org/download/)
and either in your path or at it's standard place of `C:\Program Files\CMake`

And you must have `node.js` installed, at least version 18.
I recommend using [nvm-windows](https://github.com/coreybutler/nvm-windows) to install it
as it makes it easy to switch version

### MacOS

Before running the build script above you must have
XCode installed and its command line tools

Further you must have [cmake installed](https://cmake.org/download/)
and either in your path or at it's standard place of `/Applications/CMake.app`

And you must have `node.js` installed, at least version 18.
I recommend using [nvm](https://github.com/nvm-sh/nvm) to install it
as it makes it easy to switch versions.

### Linux (Ubuntu)

Before running the build script above you need to install
the following dependencies

```sh
sudo apt-get install cmake
```

And you must have `node.js` installed, at least version 18.
I recommend using [nvm](https://github.com/nvm-sh/nvm) to install it
as it makes it easy to switch versions.
99 changes: 99 additions & 0 deletions build/build.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
import path from 'path';
import fs from 'fs';

import {execute} from './execute.js';
import {addElemIf, appendPathIfItExists, prependPathIfItExists} from './utils.js';

//const __dirname = dirname(fileURLToPath(import.meta.url));
const cwd = process.cwd();
const depotToolsPath = path.join(cwd, 'third_party', 'depot_tools');
const dawnPath = `${cwd}/third_party/dawn`;
const buildPath = `${dawnPath}/out/cmake-release`

const isMac = process.platform === 'darwin';
const isWin = process.platform === 'win32';

prependPathIfItExists(depotToolsPath);
appendPathIfItExists('/Applications/CMake.app/Contents/bin');
appendPathIfItExists('C:\\Program Files\\CMake\\bin');

function fixupPackageJson(filename) {
const pkg = JSON.parse(fs.readFileSync('package.json', {encoding: 'utf8'}));
const vsPkg = JSON.parse(fs.readFileSync(filename, {encoding: 'utf8'}));
const newPkg = {
...pkg,
...vsPkg,
type: "commonjs",
scripts: {},
version: pkg.version,
};
fs.writeFileSync(filename, JSON.stringify(newPkg, null, 2));
}

async function buildDawnNode() {
try {
process.env.DEPOT_TOOLS_WIN_TOOLCHAIN = '0'
process.chdir('third_party/dawn');
fs.copyFileSync('scripts/standalone-with-node.gclient', '.gclient');
await execute('gclient', ['metrics', '--opt-out']);
await execute('gclient', ['sync']);
fs.mkdirSync('out/cmake-release', {recursive: true});
process.chdir('out/cmake-release');

await execute('cmake', [
dawnPath,
...addElemIf(!isWin, '-GNinja'),
'-DDAWN_BUILD_NODE_BINDINGS=1',
...addElemIf(isMac, '-DCMAKE_OSX_SYSROOT=/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk'),
]);
if (isWin) {
await execute('cmake', ['--build', '.', '-target', 'dawn.node'])
} else {
await execute('ninja', ['dawn.node']);
}
} finally {
process.chdir(cwd);
}
}

async function packageExtension(target) {
try {
process.chdir(buildPath);
await execute('npm', ['install']);
await execute(`${cwd}/node_modules/.bin/vsce`, [
'package',
'--allow-star-activation',
'--target', target,
]);
} finally {
process.chdir(cwd);
}
}

async function copyResult(filepath, target) {
const srcFilename = path.join(filepath, 'dawn.node');
const dstFilename = path.join('dist', `${target}.dawn.node`);
fs.mkdirSync(path.dirname(dstFilename), {recursive: true});
fs.copyFileSync(srcFilename, dstFilename);
return dstFilename;
}

async function main() {
try {
const target = `${process.platform}-${process.arch}`;
console.log('building for:', target);
await execute('git', ['submodule', 'update', '--init']);
await buildDawnNode();
//fixupPackageJson(`${buildPath}/package.json`);
//fs.copyFileSync('third_party/dawn/LICENSE', `${buildPath}/LICENSE`);
//await packageExtension(target);
const packageName = await copyResult(buildPath, target);
console.log('created:', packageName);
} catch (e) {
console.error(e);
console.error(e.stack);
process.exit(1);
}
}

main();
15 changes: 15 additions & 0 deletions build/execute.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import {spawn} from 'child_process';

export function execute(cmd, args, options) {
return new Promise((resolve, reject) => {
const proc = spawn(cmd, args, {...options || {}, shell: true, stdio: 'inherit'});
proc.on('close', function(code) {
const result = {exitCode: code};
if (parseInt(code) !== 0) {
reject(result);
} else {
resolve(null, result);
}
});
});
}
9 changes: 9 additions & 0 deletions build/github.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
export async function getLatestRelease({owner, repo}) {
const res = await fetch(`https://api.github.com/repos/${owner}/${repo}/releases/latest`, {
headers: {
'Accept': 'application/vnd.github+json',
'X-GitHub-Api-Version': '2022-11-28',
}
});
return await res.json();
}
38 changes: 38 additions & 0 deletions build/publish.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
import path from 'path';
import fs from 'fs';

import {execute} from './execute.js';
import * as github from './github.js';

const owner = 'greggman';
const repo = 'node-webgpu';

function executeL(cmd, args) {
console.log(cmd, args.join(' '));
execute(cmd, args);
}

async function downloadFile(name, url, filepath) {
const res = await fetch(url);
const data = await res.arrayBuffer();
const filename = path.join(filepath, name);
console.log('download:', filename);
fs.mkdirSync(filepath, {recursive: true});
fs.writeFileSync(filename, new Uint8Array(data));
return filename;
}

async function main() {
const data = await github.getLatestRelease({
owner,
repo,
});
//const vsixFilenames = await Promise.all(
// data.assets
// .filter(({name}) => name?.endsWith('.vsix'))
// .map(({name, browser_download_url}) => downloadFile(name, browser_download_url, 'dist'))
//);
//executeL('./node_modules/.bin/vsce', ['publish', '--packagePath', ...vsixFilenames]);
}

main();
23 changes: 23 additions & 0 deletions build/update.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
import path from 'path';
import fs from 'fs';

import {execute} from './execute.js';

const cwd = process.cwd();

async function main() {
try {
await execute('git', ['submodule', 'update', '--init']);
process.chdir('third_party/dawn');
await execute('git', ['pull', 'origin', 'main']);
process.chdir(cwd);
process.chdir('third_party/depot_tools');
await execute('git', ['pull', 'origin', 'main']);
} catch (e) {
console.error(e);
console.error(e.stack);
process.exit(1);
}
}

main();
Loading

0 comments on commit 5b80d23

Please sign in to comment.