electron-incremental-update 0.1.0 → 0.1.2
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 +1 -1
- package/dist/index.cjs +26 -14
- package/dist/index.d.ts +55 -5
- package/dist/index.mjs +26 -14
- package/dist/vite.cjs +7 -5
- package/dist/vite.d.ts +5 -0
- package/dist/vite.mjs +7 -5
- package/package.json +3 -2
package/README.md
CHANGED
package/dist/index.cjs
CHANGED
|
@@ -91,13 +91,20 @@ var import_node_https = __toESM(require("https"), 1);
|
|
|
91
91
|
var import_electron2 = require("electron");
|
|
92
92
|
function createUpdater({
|
|
93
93
|
SIGNATURE_PUB,
|
|
94
|
-
|
|
94
|
+
repository,
|
|
95
95
|
productName,
|
|
96
|
-
|
|
96
|
+
releaseAsarURL: _release,
|
|
97
|
+
updateJsonURL: _update,
|
|
98
|
+
userAgent,
|
|
99
|
+
extraHeader
|
|
97
100
|
}) {
|
|
98
101
|
const updater = new import_node_events.EventEmitter();
|
|
99
102
|
async function download(url, format) {
|
|
100
|
-
const ua = "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.183 Safari/537.36";
|
|
103
|
+
const ua = userAgent || "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.183 Safari/537.36";
|
|
104
|
+
const commonHeader = {
|
|
105
|
+
UserAgent: ua,
|
|
106
|
+
...extraHeader
|
|
107
|
+
};
|
|
101
108
|
return await new Promise((resolve2, reject) => {
|
|
102
109
|
import_node_https.default.get(url, (res) => {
|
|
103
110
|
if (format === "json") {
|
|
@@ -105,7 +112,7 @@ function createUpdater({
|
|
|
105
112
|
res.setEncoding("utf8");
|
|
106
113
|
res.headers = {
|
|
107
114
|
Accept: "application/json",
|
|
108
|
-
|
|
115
|
+
...commonHeader
|
|
109
116
|
};
|
|
110
117
|
res.on("data", (chunk) => data += chunk);
|
|
111
118
|
res.on("end", () => {
|
|
@@ -115,7 +122,7 @@ function createUpdater({
|
|
|
115
122
|
let data = [];
|
|
116
123
|
res.headers = {
|
|
117
124
|
Accept: "application/octet-stream",
|
|
118
|
-
|
|
125
|
+
...commonHeader
|
|
119
126
|
};
|
|
120
127
|
res.on("data", (chunk) => {
|
|
121
128
|
updater.emit("downloading", chunk.length);
|
|
@@ -162,16 +169,22 @@ function createUpdater({
|
|
|
162
169
|
};
|
|
163
170
|
return import_electron2.app.isPackaged && parseVersion(import_electron2.app.getVersion()) < parseVersion(version);
|
|
164
171
|
}
|
|
165
|
-
async function checkUpdate(
|
|
172
|
+
async function checkUpdate(option) {
|
|
173
|
+
let {
|
|
174
|
+
updateJsonURL = _update,
|
|
175
|
+
releaseAsarURL = _release
|
|
176
|
+
} = option || {};
|
|
177
|
+
if ((!updateJsonURL || !releaseAsarURL) && !repository) {
|
|
178
|
+
throw new Error("updateJsonURL or releaseAsarURL are not set");
|
|
179
|
+
}
|
|
180
|
+
updateJsonURL ??= `${repository}/version.json`;
|
|
181
|
+
releaseAsarURL ??= `${repository}/releases/download/latest/${productName}.asar.gz`;
|
|
166
182
|
const gzipPath = `../${productName}.asar.gz`;
|
|
167
183
|
const tmpFile = gzipPath.replace(".asar.gz", ".tmp.gz");
|
|
168
|
-
const base = repository.replace("https://github.com", "");
|
|
169
|
-
const updateJSONUrl = `https://cdn.jsdelivr.net/gh/${base}/version.json`;
|
|
170
|
-
const downloadUrl = `${releaseCdnPrefix2 ? `${releaseCdnPrefix2}/${base}` : repository}/releases/download/latest/${productName}.asar.gz`;
|
|
171
184
|
if ((0, import_node_fs2.existsSync)(tmpFile)) {
|
|
172
185
|
await (0, import_promises.rm)(tmpFile);
|
|
173
186
|
}
|
|
174
|
-
const json = await download(
|
|
187
|
+
const json = await download(updateJsonURL, "json");
|
|
175
188
|
if (!json) {
|
|
176
189
|
throw new Error("fetch update json failed");
|
|
177
190
|
}
|
|
@@ -180,12 +193,11 @@ function createUpdater({
|
|
|
180
193
|
version,
|
|
181
194
|
size
|
|
182
195
|
} = json;
|
|
183
|
-
console.log(version, size, signature);
|
|
184
196
|
if (!needUpdate(version)) {
|
|
185
197
|
return "unavailable";
|
|
186
198
|
}
|
|
187
199
|
updater.emit("downloadStart", size);
|
|
188
|
-
const buffer = await download(
|
|
200
|
+
const buffer = await download(releaseAsarURL, "buffer");
|
|
189
201
|
if (!verify(buffer, signature)) {
|
|
190
202
|
throw new Error("file broken, invalid signature!");
|
|
191
203
|
}
|
|
@@ -193,9 +205,9 @@ function createUpdater({
|
|
|
193
205
|
await extractFile(gzipPath);
|
|
194
206
|
return "success";
|
|
195
207
|
}
|
|
196
|
-
const onCheck = async () => {
|
|
208
|
+
const onCheck = async (option) => {
|
|
197
209
|
try {
|
|
198
|
-
const result = await checkUpdate(
|
|
210
|
+
const result = await checkUpdate(option);
|
|
199
211
|
updater.emit("checkResult", result);
|
|
200
212
|
} catch (error) {
|
|
201
213
|
updater.emit("checkResult", "fail", error);
|
package/dist/index.d.ts
CHANGED
|
@@ -8,6 +8,20 @@ type UpdateEvents = {
|
|
|
8
8
|
donwnloadError: [error: unknown];
|
|
9
9
|
};
|
|
10
10
|
type MaybeArray<T> = T extends undefined | null | never ? [] : T extends any[] ? T['length'] extends 1 ? [data: T[0]] : T : [data: T];
|
|
11
|
+
interface UpdateOption {
|
|
12
|
+
/**
|
|
13
|
+
* URL of version info json
|
|
14
|
+
* @default `${repository}/version.json`
|
|
15
|
+
* @throws if `updateJsonURL` and `repository` are all not set
|
|
16
|
+
*/
|
|
17
|
+
updateJsonURL?: string;
|
|
18
|
+
/**
|
|
19
|
+
* URL of release asar.gz
|
|
20
|
+
* @default `${repository}/releases/download/latest/${productName}.asar.gz`
|
|
21
|
+
* @throws if `releaseAsarURL` and `repository` are all not set
|
|
22
|
+
*/
|
|
23
|
+
releaseAsarURL?: string;
|
|
24
|
+
}
|
|
11
25
|
interface TypedUpdater<T extends Record<string | symbol, MaybeArray<any>>, Event extends Exclude<keyof T, number> = Exclude<keyof T, number>> {
|
|
12
26
|
removeAllListeners<E extends Event>(event?: E): this;
|
|
13
27
|
listeners<E extends Event>(eventName: E): Function[];
|
|
@@ -16,16 +30,52 @@ interface TypedUpdater<T extends Record<string | symbol, MaybeArray<any>>, Event
|
|
|
16
30
|
once<E extends Event>(eventName: E, listener: (...args: MaybeArray<T[E]>) => void): this;
|
|
17
31
|
emit<E extends Event>(eventName: E, ...args: MaybeArray<T[E]>): boolean;
|
|
18
32
|
off<E extends Event>(eventName: E, listener: (...args: MaybeArray<T[E]>) => void): this;
|
|
19
|
-
checkUpdate(
|
|
33
|
+
checkUpdate(options?: UpdateOption): Promise<void>;
|
|
20
34
|
}
|
|
21
35
|
type Updater = TypedUpdater<UpdateEvents>;
|
|
22
|
-
interface Options {
|
|
36
|
+
interface Options extends UpdateOption {
|
|
37
|
+
/**
|
|
38
|
+
* public key of signature
|
|
39
|
+
*
|
|
40
|
+
* it will be auto generated by plugin
|
|
41
|
+
* @example
|
|
42
|
+
* ```ts
|
|
43
|
+
* // auto filled by plugin
|
|
44
|
+
* const SIGNATURE_PUB = ''
|
|
45
|
+
*
|
|
46
|
+
* const updater = createUpdater({
|
|
47
|
+
* SIGNATURE_PUB,
|
|
48
|
+
* ...
|
|
49
|
+
* })
|
|
50
|
+
* ```
|
|
51
|
+
*/
|
|
23
52
|
SIGNATURE_PUB: string;
|
|
53
|
+
/**
|
|
54
|
+
* product name
|
|
55
|
+
*
|
|
56
|
+
* you can use the `name` in package.json
|
|
57
|
+
*/
|
|
24
58
|
productName: string;
|
|
25
|
-
|
|
26
|
-
|
|
59
|
+
/**
|
|
60
|
+
* repository url, e.g. `https://github.com/electron/electron`
|
|
61
|
+
*
|
|
62
|
+
* you can use the `repository` in package.json
|
|
63
|
+
*
|
|
64
|
+
* if `updateJsonURL` or `releaseAsarURL` are absent,
|
|
65
|
+
* `repository` will be used to determine the url
|
|
66
|
+
*/
|
|
67
|
+
repository?: string;
|
|
68
|
+
/**
|
|
69
|
+
* download user agent
|
|
70
|
+
* @default 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.183 Safari/537.36'
|
|
71
|
+
*/
|
|
72
|
+
userAgent?: string;
|
|
73
|
+
/**
|
|
74
|
+
* extra download header, `accept` and `user-agent` is set by default
|
|
75
|
+
*/
|
|
76
|
+
extraHeader?: Record<string, string>;
|
|
27
77
|
}
|
|
28
|
-
declare function createUpdater({ SIGNATURE_PUB,
|
|
78
|
+
declare function createUpdater({ SIGNATURE_PUB, repository, productName, releaseAsarURL: _release, updateJsonURL: _update, userAgent, extraHeader, }: Options): Updater;
|
|
29
79
|
|
|
30
80
|
declare function getAppAsarPath(name: string): string;
|
|
31
81
|
declare function getElectronVersion(): string;
|
package/dist/index.mjs
CHANGED
|
@@ -55,13 +55,20 @@ import https from "node:https";
|
|
|
55
55
|
import { app as app2 } from "electron";
|
|
56
56
|
function createUpdater({
|
|
57
57
|
SIGNATURE_PUB,
|
|
58
|
-
|
|
58
|
+
repository,
|
|
59
59
|
productName,
|
|
60
|
-
|
|
60
|
+
releaseAsarURL: _release,
|
|
61
|
+
updateJsonURL: _update,
|
|
62
|
+
userAgent,
|
|
63
|
+
extraHeader
|
|
61
64
|
}) {
|
|
62
65
|
const updater = new EventEmitter();
|
|
63
66
|
async function download(url, format) {
|
|
64
|
-
const ua = "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.183 Safari/537.36";
|
|
67
|
+
const ua = userAgent || "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.183 Safari/537.36";
|
|
68
|
+
const commonHeader = {
|
|
69
|
+
UserAgent: ua,
|
|
70
|
+
...extraHeader
|
|
71
|
+
};
|
|
65
72
|
return await new Promise((resolve2, reject) => {
|
|
66
73
|
https.get(url, (res) => {
|
|
67
74
|
if (format === "json") {
|
|
@@ -69,7 +76,7 @@ function createUpdater({
|
|
|
69
76
|
res.setEncoding("utf8");
|
|
70
77
|
res.headers = {
|
|
71
78
|
Accept: "application/json",
|
|
72
|
-
|
|
79
|
+
...commonHeader
|
|
73
80
|
};
|
|
74
81
|
res.on("data", (chunk) => data += chunk);
|
|
75
82
|
res.on("end", () => {
|
|
@@ -79,7 +86,7 @@ function createUpdater({
|
|
|
79
86
|
let data = [];
|
|
80
87
|
res.headers = {
|
|
81
88
|
Accept: "application/octet-stream",
|
|
82
|
-
|
|
89
|
+
...commonHeader
|
|
83
90
|
};
|
|
84
91
|
res.on("data", (chunk) => {
|
|
85
92
|
updater.emit("downloading", chunk.length);
|
|
@@ -126,16 +133,22 @@ function createUpdater({
|
|
|
126
133
|
};
|
|
127
134
|
return app2.isPackaged && parseVersion(app2.getVersion()) < parseVersion(version);
|
|
128
135
|
}
|
|
129
|
-
async function checkUpdate(
|
|
136
|
+
async function checkUpdate(option) {
|
|
137
|
+
let {
|
|
138
|
+
updateJsonURL = _update,
|
|
139
|
+
releaseAsarURL = _release
|
|
140
|
+
} = option || {};
|
|
141
|
+
if ((!updateJsonURL || !releaseAsarURL) && !repository) {
|
|
142
|
+
throw new Error("updateJsonURL or releaseAsarURL are not set");
|
|
143
|
+
}
|
|
144
|
+
updateJsonURL ??= `${repository}/version.json`;
|
|
145
|
+
releaseAsarURL ??= `${repository}/releases/download/latest/${productName}.asar.gz`;
|
|
130
146
|
const gzipPath = `../${productName}.asar.gz`;
|
|
131
147
|
const tmpFile = gzipPath.replace(".asar.gz", ".tmp.gz");
|
|
132
|
-
const base = repository.replace("https://github.com", "");
|
|
133
|
-
const updateJSONUrl = `https://cdn.jsdelivr.net/gh/${base}/version.json`;
|
|
134
|
-
const downloadUrl = `${releaseCdnPrefix2 ? `${releaseCdnPrefix2}/${base}` : repository}/releases/download/latest/${productName}.asar.gz`;
|
|
135
148
|
if (existsSync(tmpFile)) {
|
|
136
149
|
await rm(tmpFile);
|
|
137
150
|
}
|
|
138
|
-
const json = await download(
|
|
151
|
+
const json = await download(updateJsonURL, "json");
|
|
139
152
|
if (!json) {
|
|
140
153
|
throw new Error("fetch update json failed");
|
|
141
154
|
}
|
|
@@ -144,12 +157,11 @@ function createUpdater({
|
|
|
144
157
|
version,
|
|
145
158
|
size
|
|
146
159
|
} = json;
|
|
147
|
-
console.log(version, size, signature);
|
|
148
160
|
if (!needUpdate(version)) {
|
|
149
161
|
return "unavailable";
|
|
150
162
|
}
|
|
151
163
|
updater.emit("downloadStart", size);
|
|
152
|
-
const buffer = await download(
|
|
164
|
+
const buffer = await download(releaseAsarURL, "buffer");
|
|
153
165
|
if (!verify(buffer, signature)) {
|
|
154
166
|
throw new Error("file broken, invalid signature!");
|
|
155
167
|
}
|
|
@@ -157,9 +169,9 @@ function createUpdater({
|
|
|
157
169
|
await extractFile(gzipPath);
|
|
158
170
|
return "success";
|
|
159
171
|
}
|
|
160
|
-
const onCheck = async () => {
|
|
172
|
+
const onCheck = async (option) => {
|
|
161
173
|
try {
|
|
162
|
-
const result = await checkUpdate(
|
|
174
|
+
const result = await checkUpdate(option);
|
|
163
175
|
updater.emit("checkResult", result);
|
|
164
176
|
} catch (error) {
|
|
165
177
|
updater.emit("checkResult", "fail", error);
|
package/dist/vite.cjs
CHANGED
|
@@ -140,7 +140,8 @@ async function buildAsar({
|
|
|
140
140
|
asarOutputPath,
|
|
141
141
|
privateKeyPath,
|
|
142
142
|
electronDistPath,
|
|
143
|
-
rendererDistPath
|
|
143
|
+
rendererDistPath,
|
|
144
|
+
versionPath
|
|
144
145
|
}) {
|
|
145
146
|
await (0, import_promises2.rename)(rendererDistPath, `${electronDistPath}/renderer`);
|
|
146
147
|
await (0, import_promises2.writeFile)(`${electronDistPath}/version`, version);
|
|
@@ -151,7 +152,7 @@ async function buildAsar({
|
|
|
151
152
|
await gzipFile(asarOutputPath);
|
|
152
153
|
const buffer = await (0, import_promises2.readFile)(`${asarOutputPath}.gz`);
|
|
153
154
|
const signature = generateSignature(buffer, await (0, import_promises2.readFile)(privateKeyPath, "utf-8"));
|
|
154
|
-
await (0, import_promises2.writeFile)(
|
|
155
|
+
await (0, import_promises2.writeFile)(versionPath, JSON.stringify({
|
|
155
156
|
signature,
|
|
156
157
|
version,
|
|
157
158
|
size: buffer.length
|
|
@@ -166,7 +167,8 @@ function parseOptions(options) {
|
|
|
166
167
|
entryOutputPath = "app.js",
|
|
167
168
|
asarOutputPath = `release/${productName}.asar`,
|
|
168
169
|
electronDistPath = "dist-electron",
|
|
169
|
-
rendererDistPath = "dist"
|
|
170
|
+
rendererDistPath = "dist",
|
|
171
|
+
versionPath = "version.json"
|
|
170
172
|
} = paths;
|
|
171
173
|
const {
|
|
172
174
|
privateKeyPath = "public/private.pem",
|
|
@@ -175,11 +177,11 @@ function parseOptions(options) {
|
|
|
175
177
|
} = keys;
|
|
176
178
|
const buildAsarOption = {
|
|
177
179
|
version,
|
|
178
|
-
productName,
|
|
179
180
|
asarOutputPath,
|
|
180
181
|
privateKeyPath,
|
|
181
182
|
electronDistPath,
|
|
182
|
-
rendererDistPath
|
|
183
|
+
rendererDistPath,
|
|
184
|
+
versionPath
|
|
183
185
|
};
|
|
184
186
|
const buildEntryOption = {
|
|
185
187
|
privateKeyPath,
|
package/dist/vite.d.ts
CHANGED
package/dist/vite.mjs
CHANGED
|
@@ -108,7 +108,8 @@ async function buildAsar({
|
|
|
108
108
|
asarOutputPath,
|
|
109
109
|
privateKeyPath,
|
|
110
110
|
electronDistPath,
|
|
111
|
-
rendererDistPath
|
|
111
|
+
rendererDistPath,
|
|
112
|
+
versionPath
|
|
112
113
|
}) {
|
|
113
114
|
await rename(rendererDistPath, `${electronDistPath}/renderer`);
|
|
114
115
|
await writeFile2(`${electronDistPath}/version`, version);
|
|
@@ -119,7 +120,7 @@ async function buildAsar({
|
|
|
119
120
|
await gzipFile(asarOutputPath);
|
|
120
121
|
const buffer = await readFile2(`${asarOutputPath}.gz`);
|
|
121
122
|
const signature = generateSignature(buffer, await readFile2(privateKeyPath, "utf-8"));
|
|
122
|
-
await writeFile2(
|
|
123
|
+
await writeFile2(versionPath, JSON.stringify({
|
|
123
124
|
signature,
|
|
124
125
|
version,
|
|
125
126
|
size: buffer.length
|
|
@@ -134,7 +135,8 @@ function parseOptions(options) {
|
|
|
134
135
|
entryOutputPath = "app.js",
|
|
135
136
|
asarOutputPath = `release/${productName}.asar`,
|
|
136
137
|
electronDistPath = "dist-electron",
|
|
137
|
-
rendererDistPath = "dist"
|
|
138
|
+
rendererDistPath = "dist",
|
|
139
|
+
versionPath = "version.json"
|
|
138
140
|
} = paths;
|
|
139
141
|
const {
|
|
140
142
|
privateKeyPath = "public/private.pem",
|
|
@@ -143,11 +145,11 @@ function parseOptions(options) {
|
|
|
143
145
|
} = keys;
|
|
144
146
|
const buildAsarOption = {
|
|
145
147
|
version,
|
|
146
|
-
productName,
|
|
147
148
|
asarOutputPath,
|
|
148
149
|
privateKeyPath,
|
|
149
150
|
electronDistPath,
|
|
150
|
-
rendererDistPath
|
|
151
|
+
rendererDistPath,
|
|
152
|
+
versionPath
|
|
151
153
|
};
|
|
152
154
|
const buildEntryOption = {
|
|
153
155
|
privateKeyPath,
|
package/package.json
CHANGED
|
@@ -1,11 +1,12 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "electron-incremental-update",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.2",
|
|
4
4
|
"description": "electron incremental update tools, powered by vite",
|
|
5
5
|
"scripts": {
|
|
6
6
|
"build": "tsup",
|
|
7
|
-
"release": "bumpp"
|
|
7
|
+
"release": "tsup && bumpp"
|
|
8
8
|
},
|
|
9
|
+
"repository": "https://github.com/subframe7536/electron-incremental-update",
|
|
9
10
|
"type": "module",
|
|
10
11
|
"license": "MIT",
|
|
11
12
|
"files": [
|