nw-builder 4.5.3 → 4.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +277 -61
- package/package.json +29 -13
- package/src/bld.js +25 -76
- package/src/get/decompress.js +96 -0
- package/src/get/decompress.test.js +27 -0
- package/src/get/ffmpeg.js +38 -0
- package/src/get/ffmpeg.test.js +28 -0
- package/src/get/node.js +50 -0
- package/src/get/node.test.js +25 -0
- package/src/get/nw.js +60 -0
- package/src/get/nw.test.js +29 -0
- package/src/get/request.js +27 -0
- package/src/get/request.test.js +22 -0
- package/src/get.js +46 -195
- package/src/index.js +11 -48
- package/src/run.js +11 -16
- package/src/util.js +299 -13
- package/patches/node_header.patch +0 -4
- package/src/util/parse.js +0 -112
- package/src/util/validate.js +0 -117
package/README.md
CHANGED
|
@@ -15,80 +15,296 @@ For version 3, please go to the [corresponding branch](https://github.com/nwutil
|
|
|
15
15
|
- Downloading from mirrors
|
|
16
16
|
- Node Native Addon support
|
|
17
17
|
|
|
18
|
-
|
|
18
|
+
## Table of Contents
|
|
19
19
|
|
|
20
|
-
|
|
20
|
+
- [Installation](https://github.com/nwutils/nw-builder#install)
|
|
21
|
+
- [Usage](https://github.com/nwutils/nw-builder#usage)
|
|
22
|
+
- [Concepts](https://github.com/nwutils/nw-builder#concepts)
|
|
23
|
+
- [API Reference](https://github.com/nwutils/nw-builder#api-reference)
|
|
24
|
+
- [Guides](https://github.com/nwutils/nw-builder#guides)
|
|
25
|
+
- [Contributing](https://github.com/nwutils/nw-builder#contributing)
|
|
26
|
+
- [Roadmap](https://github.com/nwutils/nw-builder#roadmap)
|
|
27
|
+
- [FAQ](https://github.com/nwutils/nw-builder#faq)
|
|
28
|
+
- [License](https://github.com/nwutils/nw-builder#license)
|
|
21
29
|
|
|
22
|
-
##
|
|
30
|
+
## Install
|
|
23
31
|
|
|
24
|
-
|
|
32
|
+
Every NW.js release includes a modified Node.js binary at a specific version. It is recommended to [install](https://nodejs.org/en/download/package-manager) exactly that version on the host system. Not doing so may download ABI incompatible Node modules. Consult the NW.js [versions manifest](https://nwjs.io/versions) for what Node.js version to install. It is recommended to use a Node version manager (such as [volta](https://volta.sh), n, nvm, or nvm-windows) to be able to easily install and switch between Node versions.
|
|
33
|
+
|
|
34
|
+
For example, NW.js v0.83.0 comes with Node.js v21.1.0.
|
|
25
35
|
|
|
26
36
|
```shell
|
|
27
|
-
|
|
37
|
+
$: node --version
|
|
38
|
+
v21.1.0
|
|
39
|
+
```
|
|
40
|
+
|
|
41
|
+
## Usage
|
|
42
|
+
|
|
43
|
+
This package can be used via a command line interface, be imported as a JavaScript module, or configured via the Node manifest as a JSON object.
|
|
44
|
+
|
|
45
|
+
ESM import:
|
|
46
|
+
|
|
47
|
+
```javascript
|
|
48
|
+
import nwbuild from "nw-builder";
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
CJS import:
|
|
52
|
+
|
|
53
|
+
```javascript
|
|
54
|
+
let nwbuild;
|
|
55
|
+
import("nwbuild")
|
|
56
|
+
.then((object) => {
|
|
57
|
+
nwbuild = obj;
|
|
58
|
+
})
|
|
59
|
+
.catch((error) => {
|
|
60
|
+
console.error(error);
|
|
61
|
+
});
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
Node manifest usage:
|
|
65
|
+
|
|
66
|
+
```json
|
|
67
|
+
{
|
|
68
|
+
"nwbuild": {
|
|
69
|
+
// user specified options
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
```
|
|
73
|
+
|
|
74
|
+
> From here on we will show `nw-builder` functionality by using the JavaScript module. Please note that the same method applies when using a command line or Node manifest.
|
|
75
|
+
|
|
76
|
+
## Concepts
|
|
77
|
+
|
|
78
|
+
`nw-builder` can get, run and build NW.js applications. We refer to them as get, run and build modes.
|
|
79
|
+
|
|
80
|
+
### Get Mode
|
|
81
|
+
|
|
82
|
+
By default you get the normal build of the latest NW.js release for your specific platform and arch. For more information, please refer to the API reference.
|
|
83
|
+
|
|
84
|
+
```javascript
|
|
85
|
+
nwbuild({
|
|
86
|
+
mode: "get"
|
|
87
|
+
});
|
|
88
|
+
```
|
|
89
|
+
|
|
90
|
+
Get the community built FFmeg which contains proprietary codecs. This options is disabled by default. Please read the [license's constraints](https://nwjs.readthedocs.io/en/latest/For%20Developers/Enable%20Proprietary%20Codecs/#get-ffmpeg-binaries-from-the-community) before enabling this option.
|
|
91
|
+
|
|
92
|
+
```javascript
|
|
93
|
+
nwbuild({
|
|
94
|
+
mode: "get",
|
|
95
|
+
ffmpeg: true
|
|
96
|
+
});
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
Get Node headers if you have to rebuild Node addons.
|
|
100
|
+
|
|
101
|
+
```javascript
|
|
102
|
+
nwbuild({
|
|
103
|
+
mode: "get",
|
|
104
|
+
nativeAddon: "gyp"
|
|
105
|
+
});
|
|
106
|
+
```
|
|
107
|
+
|
|
108
|
+
### Run Mode
|
|
109
|
+
|
|
110
|
+
```javascript
|
|
111
|
+
nwbuild({
|
|
112
|
+
mode: "run",
|
|
113
|
+
srcDir: "./app",
|
|
114
|
+
glob: false,
|
|
115
|
+
});
|
|
116
|
+
```
|
|
117
|
+
|
|
118
|
+
### Build Mode
|
|
119
|
+
|
|
120
|
+
Build with defaults:
|
|
121
|
+
|
|
122
|
+
```javascript
|
|
123
|
+
nwbuild({
|
|
124
|
+
mode: "build",
|
|
125
|
+
});
|
|
126
|
+
```
|
|
127
|
+
|
|
128
|
+
Managed Manifest
|
|
129
|
+
|
|
130
|
+
You can let `nw-builder` manage your node modules. The `managedManifest` options accepts a `boolean`, `string` or `object` type. It will then remove `devDependencies`, autodetect and download `dependencies` via the relevant `packageManager`. If none is specified, it uses `npm` as default.
|
|
131
|
+
|
|
132
|
+
Setting it to `true` will parse the first Node manifest it encounters as the NW manifest.
|
|
133
|
+
|
|
134
|
+
```javascript
|
|
135
|
+
nwbuild({
|
|
136
|
+
mode: "build",
|
|
137
|
+
managedManifest: true,
|
|
138
|
+
});
|
|
139
|
+
```
|
|
140
|
+
|
|
141
|
+
Setting it to a `string` implies that you are passing the file path to the NW manifest.
|
|
142
|
+
|
|
143
|
+
```javascript
|
|
144
|
+
nwbuild({
|
|
145
|
+
mode: "build",
|
|
146
|
+
managedManifest: "./nw.js",
|
|
147
|
+
});
|
|
28
148
|
```
|
|
29
149
|
|
|
30
|
-
|
|
150
|
+
Setting it to a `object` implies you are directly passing the NW manifest as a JavaScript object.
|
|
151
|
+
|
|
152
|
+
```javascript
|
|
153
|
+
nwbuild({
|
|
154
|
+
mode: "build",
|
|
155
|
+
managedManifest: {
|
|
156
|
+
name: "nwdemo",
|
|
157
|
+
main: "index.html"
|
|
158
|
+
},
|
|
159
|
+
});
|
|
160
|
+
```
|
|
161
|
+
|
|
162
|
+
Rebuild Node addons
|
|
163
|
+
|
|
164
|
+
Currently this feature is quite limited. It only builds node addons which have a `binding.gyp` file in the `srcDir`. There are plans to support nan, cmake, ffi and gn and auto rebuild native addons which are installed as node modules.
|
|
165
|
+
|
|
166
|
+
```javascript
|
|
167
|
+
nwbuild({
|
|
168
|
+
mode: "build",
|
|
169
|
+
nodeAddon: "gyp",
|
|
170
|
+
});
|
|
171
|
+
```
|
|
172
|
+
|
|
173
|
+
We recommend rebuilding Node addons for NW.js via `node-gyp` if you are using NW.js v0.83.0 or above.
|
|
31
174
|
|
|
32
175
|
```shell
|
|
33
|
-
|
|
176
|
+
node-gyp rebuild --target=21.1.0 --nodedir=/path/to/nw/node/headers
|
|
34
177
|
```
|
|
35
178
|
|
|
36
|
-
|
|
179
|
+
NW.js's Node version should match the Node version on the host machine due to [ABI differences in V8](https://github.com/nwjs/nw.js/issues/5025).
|
|
180
|
+
|
|
181
|
+
## API Reference
|
|
182
|
+
|
|
183
|
+
Options
|
|
184
|
+
|
|
185
|
+
| Name | Type | Default | Description |
|
|
186
|
+
| ---- | ------- | --------- | ----------- |
|
|
187
|
+
| mode | `"get" \| "run" \| "build"` | `"build"` | Choose between get, run or build mode |
|
|
188
|
+
| version | `string \| "latest" \| "stable"` | `"latest"` | Runtime version |
|
|
189
|
+
| flavor | `"normal" \| "sdk"` | `"normal"` | Runtime flavor |
|
|
190
|
+
| platform | `"linux" \| "osx" \| "win"` | | Host platform |
|
|
191
|
+
| arch | `"ia32" \| "x64" \| "arm64"` | | Host architecture |
|
|
192
|
+
| downloadUrl | `"https://dl.nwjs.io" \| "https://npm.taobao.org/mirrors/nwjs" \| https://npmmirror.com/mirrors/nwjs \| "https://github.com/corwin-of-amber/nw.js/releases/"` | `"https://dl.nwjs.io"` | Download server |
|
|
193
|
+
| manifestUrl | `"https://nwjs.io/versions" \| "https://raw.githubusercontent.com/nwutils/nw-builder/main/src/util/osx.arm.versions.json"` | `"https://nwjs.io/versions"` | Versions manifest |
|
|
194
|
+
| cacheDir | `string` | `"./cache"` | Directory to cache NW binaries |
|
|
195
|
+
| srcDir | `string` | `"./"` | File paths to application code |
|
|
196
|
+
| outDir | `string` | `"./out"` | Directory to store build artifacts |
|
|
197
|
+
| managedManifest | `boolean \| string \| object` | `false` | Managed manifest |
|
|
198
|
+
| nodeAddon | `false \| "gyp"` | `false` | Rebuild Node native addons |
|
|
199
|
+
| cache | `boolean` | `true`| If true the existing cache is used. Otherwise it removes and redownloads it. |
|
|
200
|
+
| ffmpeg | `boolean` | `false`| If true the chromium ffmpeg is replaced by community version with proprietary codecs. |
|
|
201
|
+
| glob | `boolean` | `true`| If true file globbing is enabled when parsing `srcDir`. |
|
|
202
|
+
| logLevel | `"error" \| "warn" \| "info" \| "debug"` | `"info"`| Specify level of logging. |
|
|
203
|
+
| zip | `boolean \| "zip" \| "tar" \| "tgz"` | `false`| If true, "zip", "tar" or "tgz" the `outDir` directory is compressed. |
|
|
204
|
+
|
|
205
|
+
## Guides
|
|
206
|
+
|
|
207
|
+
### Get unofficial MacOS builds
|
|
208
|
+
|
|
209
|
+
If you're running older Apple machines, you can download the unofficial builds.
|
|
210
|
+
|
|
211
|
+
> Note: You will have to manually remove quarantine flag.
|
|
37
212
|
|
|
38
213
|
```shell
|
|
39
|
-
|
|
214
|
+
sudo xattr -r -d com.apple.quarantine /path/to/nwjs.app
|
|
40
215
|
```
|
|
41
216
|
|
|
42
|
-
|
|
217
|
+
```javascript
|
|
218
|
+
nwbuild({
|
|
219
|
+
mode: "get",
|
|
220
|
+
platform: "osx",
|
|
221
|
+
arch: "arm64",
|
|
222
|
+
downloadUrl: "https://github.com/corwin-of-amber/nw.js/releases/download",
|
|
223
|
+
manifestUrl: "https://raw.githubusercontent.com/nwutils/nw-builder/main/src/util/osx.arm.versions.json",
|
|
224
|
+
});
|
|
225
|
+
```
|
|
43
226
|
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
###
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
-
|
|
227
|
+
> Note: Community FFmpeg binaries may not be available for unofficial builds. You will have to rebuild them yourself.
|
|
228
|
+
|
|
229
|
+
### Get binaries via mirrors
|
|
230
|
+
|
|
231
|
+
China mirror:
|
|
232
|
+
|
|
233
|
+
```javascript
|
|
234
|
+
nwbuild({
|
|
235
|
+
mode: "get",
|
|
236
|
+
downloadUrl: "https://npm.taobao.org/mirrors/nwjs",
|
|
237
|
+
});
|
|
238
|
+
```
|
|
239
|
+
|
|
240
|
+
Singapore mirror:
|
|
241
|
+
|
|
242
|
+
```javascript
|
|
243
|
+
nwbuild({
|
|
244
|
+
mode: "get",
|
|
245
|
+
downloadUrl: "https://cnpmjs.org/mirrors/nwjs/",
|
|
246
|
+
});
|
|
247
|
+
```
|
|
248
|
+
|
|
249
|
+
### Let `nw-builder` manage your native addons
|
|
250
|
+
|
|
251
|
+
> Note: this behaviour is buggy and quite limited. This guide is to show what will be possible in the coming minor releases.
|
|
252
|
+
|
|
253
|
+
```javascript
|
|
254
|
+
nwbuild({
|
|
255
|
+
mode: "build",
|
|
256
|
+
managedManifest: true,
|
|
257
|
+
nativeAddon: "gyp",
|
|
258
|
+
});
|
|
259
|
+
```
|
|
260
|
+
|
|
261
|
+
## Contributing
|
|
262
|
+
|
|
263
|
+
### External contributor
|
|
264
|
+
|
|
265
|
+
- We use [Conventional Commits](https://www.conventionalcommits.org/en/v1.0.0/) style of commit messages.
|
|
266
|
+
- When making changes, try to follow [SOLID](https://en.wikipedia.org/wiki/SOLID) and [DRY](https://en.wikipedia.org/wiki/Don%27t_repeat_yourself) principles.
|
|
267
|
+
- Pull requests are squashed and merged onto the `main` branch.
|
|
268
|
+
- Lint your code before commiting your change.
|
|
269
|
+
- Add tests whenever possible.
|
|
270
|
+
|
|
271
|
+
### Maintainer guidelines
|
|
272
|
+
|
|
273
|
+
## Roadmap
|
|
274
|
+
|
|
275
|
+
### Bugs
|
|
276
|
+
|
|
277
|
+
- MacOS fails to unzip MacOS NW.js binaries consistently
|
|
278
|
+
- Add back error, info, warn and debug logs
|
|
279
|
+
|
|
280
|
+
### Features
|
|
281
|
+
|
|
282
|
+
- feat(get): support canary releases
|
|
283
|
+
- feat(bld): rename MacOS Helper apps
|
|
284
|
+
- feat(pkg): add `AppImage` installer
|
|
285
|
+
- feat(pkg): add `NSIS` installer
|
|
286
|
+
- feat(pkg): add `DMG` installer
|
|
287
|
+
- feat(get): add Linux ARM unofficial support
|
|
288
|
+
- feat(bld): add source code protection
|
|
289
|
+
- feat(pkg): add code signing
|
|
290
|
+
|
|
291
|
+
### Chores
|
|
292
|
+
|
|
293
|
+
- chore(cicd): use `google-github-actions/release-please-action` to automate publishing to npm, updating changelog and creating releases
|
|
294
|
+
- chore(cli): migrate from `yargs` to `commander`
|
|
295
|
+
- chore(get): verify sha checksum for downloads
|
|
296
|
+
- chore(util): factor out file paths as constant variables
|
|
297
|
+
- chore(bld): factor out core build step
|
|
298
|
+
- chore(bld): factor out linux config
|
|
299
|
+
- chore(bld): factor out macos config
|
|
300
|
+
- chore(bld): factor out windows config
|
|
301
|
+
- chore(bld): factor out native addon
|
|
302
|
+
- chore(bld): factor out compressing
|
|
303
|
+
- chore(bld): factor out managed manifest
|
|
304
|
+
- chore(bld): move `.desktop` entry file logic to `create-desktop-shortcuts` package
|
|
305
|
+
|
|
306
|
+
## FAQ
|
|
307
|
+
|
|
308
|
+
## License
|
|
309
|
+
|
|
310
|
+
MIT License.
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "nw-builder",
|
|
3
|
-
"version": "4.
|
|
3
|
+
"version": "4.6.0",
|
|
4
4
|
"description": "Build NW.js desktop applications for MacOS, Windows and Linux.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"NW.js",
|
|
@@ -33,7 +33,6 @@
|
|
|
33
33
|
"type": "module",
|
|
34
34
|
"files": [
|
|
35
35
|
"LICENSE",
|
|
36
|
-
"patches",
|
|
37
36
|
"src"
|
|
38
37
|
],
|
|
39
38
|
"homepage": "https://github.com/nwutils/nw-builder",
|
|
@@ -42,29 +41,39 @@
|
|
|
42
41
|
"url": "https://github.com/nwutils/nw-builder.git"
|
|
43
42
|
},
|
|
44
43
|
"scripts": {
|
|
45
|
-
"lint": "eslint src
|
|
46
|
-
"
|
|
47
|
-
"
|
|
44
|
+
"lint": "eslint ./src/**/*.js ./test/**/*.js",
|
|
45
|
+
"lint:fix": "eslint --fix ./**/*.{js,md} && markdownlint --fix ./README.md",
|
|
46
|
+
"docs": "jsdoc -d docs ./README.md ./src/index.js ./src/get.js ./src/run.js ./src/bld.js",
|
|
47
|
+
"test": "vitest",
|
|
48
48
|
"demo": "cd test/fixture && node demo.js"
|
|
49
49
|
},
|
|
50
50
|
"devDependencies": {
|
|
51
|
+
"@stylistic/eslint-plugin-js": "^1.5.4",
|
|
51
52
|
"eslint": "^8.56.0",
|
|
52
|
-
"eslint-
|
|
53
|
+
"eslint-config-tjw-jsdoc": "^1.0.5",
|
|
54
|
+
"eslint-plugin-jsdoc": "^48.0.2",
|
|
55
|
+
"eslint-plugin-markdown": "^3.0.1",
|
|
53
56
|
"jsdoc": "^4.0.2",
|
|
54
|
-
"
|
|
57
|
+
"markdownlint": "^0.33.0",
|
|
58
|
+
"markdownlint-cli": "^0.38.0",
|
|
59
|
+
"selenium-webdriver": "^4.16.0",
|
|
60
|
+
"vitest": "^1.2.1"
|
|
55
61
|
},
|
|
56
62
|
"dependencies": {
|
|
63
|
+
"axios": "^1.6.7",
|
|
57
64
|
"cli-progress": "^3.12.0",
|
|
58
65
|
"compressing": "^1.10.0",
|
|
66
|
+
"fs-extra": "^11.2.0",
|
|
59
67
|
"glob": "^10.3.10",
|
|
60
68
|
"node-gyp": "^10.0.1",
|
|
61
69
|
"plist": "^3.1.0",
|
|
62
70
|
"rcedit": "^4.0.1",
|
|
71
|
+
"semver": "^7.5.4",
|
|
63
72
|
"tar": "^6.2.0",
|
|
64
|
-
"
|
|
65
|
-
"
|
|
73
|
+
"yargs": "^17.7.2",
|
|
74
|
+
"yauzl-promise": "^4.0.0"
|
|
66
75
|
},
|
|
67
|
-
"packageManager": "npm@10.
|
|
76
|
+
"packageManager": "npm@10.3.0",
|
|
68
77
|
"engines": {
|
|
69
78
|
"node": ">=14"
|
|
70
79
|
},
|
|
@@ -79,11 +88,18 @@
|
|
|
79
88
|
},
|
|
80
89
|
"extends": [
|
|
81
90
|
"eslint:recommended",
|
|
82
|
-
"plugin:
|
|
91
|
+
"plugin:markdown/recommended",
|
|
92
|
+
"tjw-jsdoc"
|
|
93
|
+
],
|
|
94
|
+
"plugins": [
|
|
95
|
+
"@stylistic/js"
|
|
83
96
|
],
|
|
84
97
|
"rules": {
|
|
85
|
-
"
|
|
86
|
-
|
|
98
|
+
"@stylistic/js/indent": [
|
|
99
|
+
"error",
|
|
100
|
+
2
|
|
101
|
+
],
|
|
102
|
+
"jsdoc/require-file-overview": "off"
|
|
87
103
|
}
|
|
88
104
|
}
|
|
89
105
|
}
|
package/src/bld.js
CHANGED
|
@@ -83,72 +83,26 @@ import util from "./util.js"
|
|
|
83
83
|
|
|
84
84
|
/**
|
|
85
85
|
* @typedef {object} BuildOptions
|
|
86
|
-
* @property {string | "latest" | "stable" | "lts"} [options.version = "latest"]
|
|
87
|
-
* @property {"normal" | "sdk"} [options.flavor = "normal"]
|
|
88
|
-
* @property {"linux" | "osx" | "win"} [options.platform]
|
|
89
|
-
* @property {"ia32" | "x64" | "arm64"} [options.arch]
|
|
90
|
-
* @property {string} [options.manifestUrl = "https://nwjs.io/versions"]
|
|
91
|
-
* @property {string} [options.srcDir = "./src"]
|
|
92
|
-
* @property {string} [options.cacheDir = "./cache"]
|
|
93
|
-
* @property {string} [options.outDir = "./out"]
|
|
94
|
-
* @property {LinuxRc | WinRc | OsxRc} [options.app]
|
|
95
|
-
* @property {boolean} [options.glob = true]
|
|
96
|
-
* @property {boolean | string | object} [options.managedManifest = false]
|
|
97
|
-
* @property {false | "gyp"} [options.nativeAddon = false]
|
|
98
|
-
* @property {false | "zip" | "tar" | "tgz"} [options.zip = false]
|
|
86
|
+
* @property {string | "latest" | "stable" | "lts"} [options.version = "latest"] Runtime version
|
|
87
|
+
* @property {"normal" | "sdk"} [options.flavor = "normal"] Build flavor
|
|
88
|
+
* @property {"linux" | "osx" | "win"} [options.platform] Target platform
|
|
89
|
+
* @property {"ia32" | "x64" | "arm64"} [options.arch] Target arch
|
|
90
|
+
* @property {string} [options.manifestUrl = "https://nwjs.io/versions"] Manifest URL
|
|
91
|
+
* @property {string} [options.srcDir = "./src"] Source directory
|
|
92
|
+
* @property {string} [options.cacheDir = "./cache"] Cache directory
|
|
93
|
+
* @property {string} [options.outDir = "./out"] Out directory
|
|
94
|
+
* @property {LinuxRc | WinRc | OsxRc} [options.app] Platform specific rc
|
|
95
|
+
* @property {boolean} [options.glob = true] File globbing
|
|
96
|
+
* @property {boolean | string | object} [options.managedManifest = false] Manage manifest
|
|
97
|
+
* @property {false | "gyp"} [options.nativeAddon = false] Rebuild native modules
|
|
98
|
+
* @property {false | "zip" | "tar" | "tgz"} [options.zip = false] Compress built artifacts
|
|
99
99
|
*/
|
|
100
100
|
|
|
101
101
|
/**
|
|
102
102
|
* @async
|
|
103
103
|
* @function
|
|
104
|
-
* @param
|
|
104
|
+
* @param {BuildOptions} options - Build options
|
|
105
105
|
* @return {Promise<void>}
|
|
106
|
-
*
|
|
107
|
-
* @example
|
|
108
|
-
* // Minimal Usage (uses default values)
|
|
109
|
-
* nwbuild({
|
|
110
|
-
* mode: "build",
|
|
111
|
-
* });
|
|
112
|
-
*
|
|
113
|
-
* @example
|
|
114
|
-
* // Managed Manifest mode
|
|
115
|
-
* // Parse first Node manifest it encounters as NW manifest
|
|
116
|
-
* // Remove development dependencies
|
|
117
|
-
* // Auto detect and download dependencies via relevant package manager
|
|
118
|
-
* nwbuild({
|
|
119
|
-
* mode: "build",
|
|
120
|
-
* managedManifest: true
|
|
121
|
-
* });
|
|
122
|
-
*
|
|
123
|
-
* @example
|
|
124
|
-
* // Managed Manifest JSON
|
|
125
|
-
* // Use JSON object provided as NW manifest
|
|
126
|
-
* nwbuild({
|
|
127
|
-
* mode: "build",
|
|
128
|
-
* managedManifest: { name: "demo", "main": "index.html" }
|
|
129
|
-
* });
|
|
130
|
-
*
|
|
131
|
-
* @example
|
|
132
|
-
* // Managed Manifest File
|
|
133
|
-
* // Use file path provided as NW manifest
|
|
134
|
-
* nwbuild({
|
|
135
|
-
* mode: "build",
|
|
136
|
-
* managedManifest: "./manifest.json"
|
|
137
|
-
* });
|
|
138
|
-
*
|
|
139
|
-
* @example
|
|
140
|
-
* // Rebuild Node native modules
|
|
141
|
-
* // This behaviour is currently disabled.
|
|
142
|
-
* // Tracking issue: https://github.com/nwutils/nw-builder/pull/993
|
|
143
|
-
* nwbuild({
|
|
144
|
-
* mode: "build",
|
|
145
|
-
* nodeAddon: "gyp"
|
|
146
|
-
* });
|
|
147
|
-
*
|
|
148
|
-
* @example
|
|
149
|
-
* // For MacOS ARM unofficial builds (<= v0.75), remove quarantine flag post build.
|
|
150
|
-
* sudo xattr -r -d com.apple.quarantine /path/to/nwjs.app
|
|
151
|
-
*
|
|
152
106
|
*/
|
|
153
107
|
async function bld({
|
|
154
108
|
version = "latest",
|
|
@@ -218,7 +172,7 @@ async function bld({
|
|
|
218
172
|
typeof managedManifest === "object" ||
|
|
219
173
|
typeof managedManifest === "string"
|
|
220
174
|
) {
|
|
221
|
-
manageManifest({ manifest, managedManifest, outDir, platform });
|
|
175
|
+
await manageManifest({ manifest, managedManifest, outDir, platform });
|
|
222
176
|
}
|
|
223
177
|
|
|
224
178
|
if (platform === "linux") {
|
|
@@ -280,11 +234,11 @@ const manageManifest = async ({ nwPkg, managedManifest, outDir, platform }) => {
|
|
|
280
234
|
);
|
|
281
235
|
|
|
282
236
|
if (manifest.packageManager.startsWith("npm")) {
|
|
283
|
-
child_process.
|
|
237
|
+
child_process.execSync(`npm install`);
|
|
284
238
|
} else if (manifest.packageManager.startsWith("yarn")) {
|
|
285
|
-
child_process.
|
|
239
|
+
child_process.execSync(`yarn install`);
|
|
286
240
|
} else if (manifest.packageManager.startsWith("pnpm")) {
|
|
287
|
-
child_process.
|
|
241
|
+
child_process.execSync(`pnpm install`);
|
|
288
242
|
}
|
|
289
243
|
};
|
|
290
244
|
|
|
@@ -370,10 +324,12 @@ const setWinConfig = async ({ app, outDir }) => {
|
|
|
370
324
|
await fsm.rename(path.resolve(outDir, "nw.exe"), outDirAppExe);
|
|
371
325
|
await rcedit(outDirAppExe, rcEditOptions);
|
|
372
326
|
} catch (error) {
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
327
|
+
if (process.platform !== "win32") {
|
|
328
|
+
console.warn(
|
|
329
|
+
"Ensure WINE is installed or build your application on Windows platform",
|
|
330
|
+
);
|
|
331
|
+
}
|
|
332
|
+
throw error;
|
|
377
333
|
}
|
|
378
334
|
};
|
|
379
335
|
|
|
@@ -453,14 +409,7 @@ const buildNativeAddon = ({ cacheDir, version, platform, arch, outDir, nodeVersi
|
|
|
453
409
|
),
|
|
454
410
|
);
|
|
455
411
|
|
|
456
|
-
child_process.
|
|
457
|
-
`node-gyp rebuild --target=${nodeVersion} --nodedir=${nodePath}`,
|
|
458
|
-
(error) => {
|
|
459
|
-
if (error !== null) {
|
|
460
|
-
console.error(error);
|
|
461
|
-
}
|
|
462
|
-
},
|
|
463
|
-
);
|
|
412
|
+
child_process.execSync(`node-gyp rebuild --target=${nodeVersion} --nodedir=${nodePath}`);
|
|
464
413
|
};
|
|
465
414
|
|
|
466
415
|
const compress = async ({
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
import fs from "node:fs";
|
|
2
|
+
import path from "node:path";
|
|
3
|
+
import stream from "node:stream";
|
|
4
|
+
|
|
5
|
+
import tar from "tar";
|
|
6
|
+
import yauzl from "yauzl-promise";
|
|
7
|
+
import {ensureSymlink} from "fs-extra";
|
|
8
|
+
|
|
9
|
+
/**
|
|
10
|
+
* Decompresses a file at `filePath` to `cacheDir` directory.
|
|
11
|
+
*
|
|
12
|
+
* @param {string} filePath - file path to compressed binary
|
|
13
|
+
* @param {string} cacheDir - directory to decompress into
|
|
14
|
+
*/
|
|
15
|
+
export default async function decompress(filePath, cacheDir) {
|
|
16
|
+
if (filePath.endsWith(".zip")) {
|
|
17
|
+
await unzip(filePath, cacheDir);
|
|
18
|
+
} else {
|
|
19
|
+
await tar.extract({
|
|
20
|
+
file: filePath,
|
|
21
|
+
C: cacheDir
|
|
22
|
+
});
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
/**
|
|
27
|
+
* Wrapper for unzipping using `yauzl-promise`.
|
|
28
|
+
*
|
|
29
|
+
* @async
|
|
30
|
+
* @function
|
|
31
|
+
* @param {string} zippedFile - file path to .zip file
|
|
32
|
+
* @param {string} cacheDir - directory to unzip in
|
|
33
|
+
* @return {Promise<void>}
|
|
34
|
+
*/
|
|
35
|
+
export async function unzip(zippedFile, cacheDir) {
|
|
36
|
+
await unzipInternal(zippedFile, cacheDir, false).then(() => {
|
|
37
|
+
unzipInternal(zippedFile, cacheDir, true);
|
|
38
|
+
})
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
/**
|
|
42
|
+
* Method for unzip with symlink in theoretical
|
|
43
|
+
*
|
|
44
|
+
* @async
|
|
45
|
+
* @function
|
|
46
|
+
* @param unzipSymlink
|
|
47
|
+
* @param {string} zippedFile - file path to .zip file
|
|
48
|
+
* @param {string} cacheDir - directory to unzip in
|
|
49
|
+
* @param {boolean} unzipSymlink - Using or not symlink
|
|
50
|
+
* @return {Promise<void>}
|
|
51
|
+
*/
|
|
52
|
+
async function unzipInternal(zippedFile, cacheDir, unzipSymlink ) {
|
|
53
|
+
const zip = await yauzl.open(zippedFile);
|
|
54
|
+
|
|
55
|
+
let entry = await zip.readEntry();
|
|
56
|
+
|
|
57
|
+
while (entry !== null) {
|
|
58
|
+
// console.log(entry)
|
|
59
|
+
let entryPathAbs = path.join(cacheDir, entry.filename);
|
|
60
|
+
// Create the directory beforehand to prevent `ENOENT: no such file or directory` errors.
|
|
61
|
+
await fs.promises.mkdir(path.dirname(entryPathAbs), {recursive: true});
|
|
62
|
+
const readStream = await entry.openReadStream();
|
|
63
|
+
|
|
64
|
+
try {
|
|
65
|
+
if (!unzipSymlink) {
|
|
66
|
+
// Regular method and silent error at this point
|
|
67
|
+
const writeStream = fs.createWriteStream(entryPathAbs);
|
|
68
|
+
await stream.promises.pipeline(readStream, writeStream);
|
|
69
|
+
} else {
|
|
70
|
+
// Need check before if file is a symlink or not at this point
|
|
71
|
+
const pathContent = await fs.promises.lstat(entryPathAbs);
|
|
72
|
+
|
|
73
|
+
if (pathContent.isSymbolicLink()) {
|
|
74
|
+
const chunks = [];
|
|
75
|
+
readStream.on('data', (chunk) => chunks.push(chunk));
|
|
76
|
+
await stream.promises.finished(readStream);
|
|
77
|
+
// need fetch value of current symlink here
|
|
78
|
+
const linkTarget = Buffer.concat(chunks).toString('utf8').trim();
|
|
79
|
+
await ensureSymlink(entryPathAbs, path.join(path.dirname(entryPathAbs), linkTarget));
|
|
80
|
+
}else{
|
|
81
|
+
// Regular method and silent error at this point
|
|
82
|
+
const writeStream = fs.createWriteStream(entryPathAbs);
|
|
83
|
+
await stream.promises.pipeline(readStream, writeStream);
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
} catch (error) {
|
|
87
|
+
if (unzipSymlink) {
|
|
88
|
+
console.error(error);
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
entry = await zip.readEntry();
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
await zip.close();
|
|
96
|
+
}
|