react-native-update-cli 1.30.4 → 1.31.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/lib/bundle.js CHANGED
@@ -1,610 +1,586 @@
1
- 'use strict';
2
-
1
+ "use strict";
3
2
  Object.defineProperty(exports, "__esModule", {
4
- value: true
3
+ value: true
5
4
  });
6
- exports.commands = undefined;
7
-
8
- var _extends = Object.assign || function (target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) { if (Object.prototype.hasOwnProperty.call(source, key)) { target[key] = source[key]; } } } return target; };
9
-
10
- var _path = require('path');
11
-
12
- var _path2 = _interopRequireDefault(_path);
13
-
14
- var _utils = require('./utils');
15
-
16
- var _fsExtra = require('fs-extra');
17
-
18
- var fs = _interopRequireWildcard(_fsExtra);
19
-
20
- var _yazl = require('yazl');
21
-
22
- var _yauzl = require('yauzl');
23
-
24
- var _app = require('./app');
25
-
26
- var _child_process = require('child_process');
27
-
28
- var _os = require('os');
29
-
30
- var _os2 = _interopRequireDefault(_os);
31
-
32
- function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key]; } } newObj.default = obj; return newObj; } }
33
-
34
- function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
35
-
5
+ Object.defineProperty(exports, "commands", {
6
+ enumerable: true,
7
+ get: function() {
8
+ return commands;
9
+ }
10
+ });
11
+ const _path = /*#__PURE__*/ _interop_require_default(require("path"));
12
+ const _utils = require("./utils");
13
+ const _fsextra = /*#__PURE__*/ _interop_require_wildcard(require("fs-extra"));
14
+ const _yazl = require("yazl");
15
+ const _yauzl = require("yauzl");
16
+ const _app = require("./app");
17
+ const _child_process = require("child_process");
18
+ const _os = /*#__PURE__*/ _interop_require_default(require("os"));
19
+ function _interop_require_default(obj) {
20
+ return obj && obj.__esModule ? obj : {
21
+ default: obj
22
+ };
23
+ }
24
+ function _getRequireWildcardCache(nodeInterop) {
25
+ if (typeof WeakMap !== "function") return null;
26
+ var cacheBabelInterop = new WeakMap();
27
+ var cacheNodeInterop = new WeakMap();
28
+ return (_getRequireWildcardCache = function(nodeInterop) {
29
+ return nodeInterop ? cacheNodeInterop : cacheBabelInterop;
30
+ })(nodeInterop);
31
+ }
32
+ function _interop_require_wildcard(obj, nodeInterop) {
33
+ if (!nodeInterop && obj && obj.__esModule) {
34
+ return obj;
35
+ }
36
+ if (obj === null || typeof obj !== "object" && typeof obj !== "function") {
37
+ return {
38
+ default: obj
39
+ };
40
+ }
41
+ var cache = _getRequireWildcardCache(nodeInterop);
42
+ if (cache && cache.has(obj)) {
43
+ return cache.get(obj);
44
+ }
45
+ var newObj = {
46
+ __proto__: null
47
+ };
48
+ var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor;
49
+ for(var key in obj){
50
+ if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) {
51
+ var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null;
52
+ if (desc && (desc.get || desc.set)) {
53
+ Object.defineProperty(newObj, key, desc);
54
+ } else {
55
+ newObj[key] = obj[key];
56
+ }
57
+ }
58
+ }
59
+ newObj.default = obj;
60
+ if (cache) {
61
+ cache.set(obj, newObj);
62
+ }
63
+ return newObj;
64
+ }
36
65
  const g2js = require('gradle-to-js/lib/parser');
37
-
38
66
  const properties = require('properties');
39
-
40
67
  let bsdiff, hdiff, diff;
41
68
  try {
42
- bsdiff = require('node-bsdiff').diff;
69
+ bsdiff = require('node-bsdiff').diff;
43
70
  } catch (e) {}
44
-
45
71
  try {
46
- hdiff = require('node-hdiffpatch').diff;
72
+ hdiff = require('node-hdiffpatch').diff;
47
73
  } catch (e) {}
48
-
49
74
  async function runReactNativeBundleCommand(bundleName, development, entryFile, outputFolder, platform, sourcemapOutput, config) {
50
- let gradleConfig = {};
51
- if (platform === 'android') {
52
- gradleConfig = await checkGradleConfig();
53
- if (gradleConfig.crunchPngs !== false) {
54
- console.warn('android的crunchPngs选项似乎尚未禁用(如已禁用则请忽略此提示),这可能导致热更包体积异常增大,具体请参考 https://pushy.reactnative.cn/docs/getting-started.html#%E7%A6%81%E7%94%A8-android-%E7%9A%84-crunch-%E4%BC%98%E5%8C%96 \n');
75
+ let gradleConfig = {};
76
+ if (platform === 'android') {
77
+ gradleConfig = await checkGradleConfig();
78
+ if (gradleConfig.crunchPngs !== false) {
79
+ console.warn('android的crunchPngs选项似乎尚未禁用(如已禁用则请忽略此提示),这可能导致热更包体积异常增大,具体请参考 https://pushy.reactnative.cn/docs/getting-started.html#%E7%A6%81%E7%94%A8-android-%E7%9A%84-crunch-%E4%BC%98%E5%8C%96 \n');
80
+ }
55
81
  }
56
- }
57
-
58
- let reactNativeBundleArgs = [];
59
-
60
- let envArgs = process.env.PUSHY_ENV_ARGS;
61
-
62
- if (envArgs) {
63
- Array.prototype.push.apply(reactNativeBundleArgs, envArgs.trim().split(/\s+/));
64
- }
65
-
66
- fs.emptyDirSync(outputFolder);
67
-
68
- let cliPath;
69
-
70
- try {
71
- // rn >= 0.75
72
- cliPath = require.resolve('@react-native-community/cli/build/bin.js', {
73
- paths: [process.cwd()]
74
- });
75
- } catch (e) {
76
- // rn < 0.75
77
- cliPath = require.resolve('react-native/local-cli/cli.js', {
78
- paths: [process.cwd()]
79
- });
80
- }
81
-
82
- let usingExpo = false;
83
- try {
84
- require.resolve('expo-router', {
85
- paths: [process.cwd()]
86
- });
87
-
88
- console.log(`expo-router detected, will use @expo/cli to bundle.\n`);
89
- // if using expo-router, use expo-cli
90
- cliPath = require.resolve('@expo/cli', {
91
- paths: [process.cwd()]
92
- });
93
- usingExpo = true;
94
- } catch (e) {}
95
- const bundleCommand = usingExpo ? 'export:embed' : 'bundle';
96
-
97
- Array.prototype.push.apply(reactNativeBundleArgs, [cliPath, bundleCommand, '--assets-dest', outputFolder, '--bundle-output', _path2.default.join(outputFolder, bundleName), '--dev', development, '--entry-file', entryFile, '--platform', platform, '--reset-cache']);
98
-
99
- if (sourcemapOutput) {
100
- reactNativeBundleArgs.push('--sourcemap-output', sourcemapOutput);
101
- }
102
-
103
- if (config) {
104
- reactNativeBundleArgs.push('--config', config);
105
- }
106
-
107
- const reactNativeBundleProcess = (0, _child_process.spawn)('node', reactNativeBundleArgs);
108
- console.log(`Running bundle command: node ${reactNativeBundleArgs.join(' ')}`);
109
-
110
- return new Promise((resolve, reject) => {
111
- reactNativeBundleProcess.stdout.on('data', data => {
112
- console.log(data.toString().trim());
113
- });
114
-
115
- reactNativeBundleProcess.stderr.on('data', data => {
116
- console.error(data.toString().trim());
117
- });
118
-
119
- reactNativeBundleProcess.on('close', async exitCode => {
120
- if (exitCode) {
121
- reject(new Error(`"react-native bundle" command exited with code ${exitCode}.`));
122
- } else {
123
- let hermesEnabled = false;
124
-
125
- if (platform === 'android') {
126
- const gradlePropeties = await new Promise(resolve => {
127
- properties.parse('./android/gradle.properties', { path: true }, function (error, props) {
128
- if (error) {
129
- console.error(error);
82
+ let reactNativeBundleArgs = [];
83
+ let envArgs = process.env.PUSHY_ENV_ARGS;
84
+ if (envArgs) {
85
+ Array.prototype.push.apply(reactNativeBundleArgs, envArgs.trim().split(/\s+/));
86
+ }
87
+ _fsextra.emptyDirSync(outputFolder);
88
+ let cliPath;
89
+ try {
90
+ // rn >= 0.75
91
+ cliPath = require.resolve('@react-native-community/cli/build/bin.js', {
92
+ paths: [
93
+ process.cwd()
94
+ ]
95
+ });
96
+ } catch (e) {
97
+ // rn < 0.75
98
+ cliPath = require.resolve('react-native/local-cli/cli.js', {
99
+ paths: [
100
+ process.cwd()
101
+ ]
102
+ });
103
+ }
104
+ let usingExpo = false;
105
+ try {
106
+ require.resolve('expo-router', {
107
+ paths: [
108
+ process.cwd()
109
+ ]
110
+ });
111
+ console.log(`expo-router detected, will use @expo/cli to bundle.\n`);
112
+ // if using expo-router, use expo-cli
113
+ cliPath = require.resolve('@expo/cli', {
114
+ paths: [
115
+ process.cwd()
116
+ ]
117
+ });
118
+ usingExpo = true;
119
+ } catch (e) {}
120
+ const bundleCommand = usingExpo ? 'export:embed' : 'bundle';
121
+ Array.prototype.push.apply(reactNativeBundleArgs, [
122
+ cliPath,
123
+ bundleCommand,
124
+ '--assets-dest',
125
+ outputFolder,
126
+ '--bundle-output',
127
+ _path.default.join(outputFolder, bundleName),
128
+ '--dev',
129
+ development,
130
+ '--entry-file',
131
+ entryFile,
132
+ '--platform',
133
+ platform,
134
+ '--reset-cache'
135
+ ]);
136
+ if (sourcemapOutput) {
137
+ reactNativeBundleArgs.push('--sourcemap-output', sourcemapOutput);
138
+ }
139
+ if (config) {
140
+ reactNativeBundleArgs.push('--config', config);
141
+ }
142
+ const reactNativeBundleProcess = (0, _child_process.spawn)('node', reactNativeBundleArgs);
143
+ console.log(`Running bundle command: node ${reactNativeBundleArgs.join(' ')}`);
144
+ return new Promise((resolve, reject)=>{
145
+ reactNativeBundleProcess.stdout.on('data', (data)=>{
146
+ console.log(data.toString().trim());
147
+ });
148
+ reactNativeBundleProcess.stderr.on('data', (data)=>{
149
+ console.error(data.toString().trim());
150
+ });
151
+ reactNativeBundleProcess.on('close', async (exitCode)=>{
152
+ if (exitCode) {
153
+ reject(new Error(`"react-native bundle" command exited with code ${exitCode}.`));
154
+ } else {
155
+ let hermesEnabled = false;
156
+ if (platform === 'android') {
157
+ const gradlePropeties = await new Promise((resolve)=>{
158
+ properties.parse('./android/gradle.properties', {
159
+ path: true
160
+ }, function(error, props) {
161
+ if (error) {
162
+ console.error(error);
163
+ resolve(null);
164
+ }
165
+ resolve(props);
166
+ });
167
+ });
168
+ hermesEnabled = gradlePropeties.hermesEnabled;
169
+ if (typeof hermesEnabled !== 'boolean') hermesEnabled = gradleConfig.enableHermes;
170
+ } else if (platform === 'ios' && _fsextra.existsSync('ios/Pods/hermes-engine')) {
171
+ hermesEnabled = true;
172
+ }
173
+ if (hermesEnabled) {
174
+ await compileHermesByteCode(bundleName, outputFolder, sourcemapOutput);
175
+ }
130
176
  resolve(null);
131
- }
132
-
133
- resolve(props);
134
- });
135
- });
136
- hermesEnabled = gradlePropeties.hermesEnabled;
137
-
138
- if (typeof hermesEnabled !== 'boolean') hermesEnabled = gradleConfig.enableHermes;
139
- } else if (platform === 'ios' && fs.existsSync('ios/Pods/hermes-engine')) {
140
- hermesEnabled = true;
141
- }
142
- if (hermesEnabled) {
143
- await compileHermesByteCode(bundleName, outputFolder, sourcemapOutput);
144
- }
145
- resolve(null);
146
- }
177
+ }
178
+ });
147
179
  });
148
- });
149
180
  }
150
-
151
181
  function getHermesOSBin() {
152
- if (_os2.default.platform() === 'win32') return 'win64-bin';
153
- if (_os2.default.platform() === 'darwin') return 'osx-bin';
154
- if (_os2.default.platform() === 'linux') return 'linux64-bin';
182
+ if (_os.default.platform() === 'win32') return 'win64-bin';
183
+ if (_os.default.platform() === 'darwin') return 'osx-bin';
184
+ if (_os.default.platform() === 'linux') return 'linux64-bin';
155
185
  }
156
-
157
186
  async function checkGradleConfig() {
158
- let enableHermes = false;
159
- let crunchPngs;
160
- try {
161
- const gradleConfig = await g2js.parseFile('android/app/build.gradle');
162
- const projectConfig = gradleConfig['project.ext.react'];
163
- for (const packagerConfig of projectConfig) {
164
- if (packagerConfig.includes('enableHermes') && packagerConfig.includes('true')) {
165
- enableHermes = true;
166
- break;
167
- }
168
- }
169
- crunchPngs = gradleConfig.android.buildTypes.release.crunchPngs;
170
- } catch (e) {}
171
- return {
172
- enableHermes,
173
- crunchPngs
174
- };
187
+ let enableHermes = false;
188
+ let crunchPngs;
189
+ try {
190
+ const gradleConfig = await g2js.parseFile('android/app/build.gradle');
191
+ crunchPngs = gradleConfig.android.buildTypes.release.crunchPngs;
192
+ const projectConfig = gradleConfig['project.ext.react'];
193
+ if (projectConfig) {
194
+ for (const packagerConfig of projectConfig){
195
+ if (packagerConfig.includes('enableHermes') && packagerConfig.includes('true')) {
196
+ enableHermes = true;
197
+ break;
198
+ }
199
+ }
200
+ }
201
+ } catch (e) {}
202
+ return {
203
+ enableHermes,
204
+ crunchPngs
205
+ };
175
206
  }
176
-
177
207
  async function compileHermesByteCode(bundleName, outputFolder, sourcemapOutput) {
178
- console.log(`Hermes enabled, now compiling to hermes bytecode:\n`);
179
- // >= rn 0.69
180
- const rnDir = _path2.default.dirname(require.resolve('react-native', {
181
- paths: [process.cwd()]
182
- }));
183
- let hermesPath = _path2.default.join(rnDir, `/sdks/hermesc/${getHermesOSBin()}`);
184
-
185
- // < rn 0.69
186
- if (!fs.existsSync(hermesPath)) {
187
- hermesPath = `node_modules/hermes-engine/${getHermesOSBin()}`;
188
- }
189
-
190
- const hermesCommand = `${hermesPath}/hermesc`;
191
-
192
- const args = ['-emit-binary', '-out', _path2.default.join(outputFolder, bundleName), _path2.default.join(outputFolder, bundleName), '-O'];
193
- if (sourcemapOutput) {
194
- args.push('-output-source-map');
195
- }
196
- console.log('Running hermesc: ' + hermesCommand + ' ' + args.join(' ') + '\n');
197
- (0, _child_process.spawnSync)(hermesCommand, args, {
198
- stdio: 'ignore'
199
- });
208
+ console.log(`Hermes enabled, now compiling to hermes bytecode:\n`);
209
+ // >= rn 0.69
210
+ const rnDir = _path.default.dirname(require.resolve('react-native', {
211
+ paths: [
212
+ process.cwd()
213
+ ]
214
+ }));
215
+ let hermesPath = _path.default.join(rnDir, `/sdks/hermesc/${getHermesOSBin()}`);
216
+ // < rn 0.69
217
+ if (!_fsextra.existsSync(hermesPath)) {
218
+ hermesPath = `node_modules/hermes-engine/${getHermesOSBin()}`;
219
+ }
220
+ const hermesCommand = `${hermesPath}/hermesc`;
221
+ const args = [
222
+ '-emit-binary',
223
+ '-out',
224
+ _path.default.join(outputFolder, bundleName),
225
+ _path.default.join(outputFolder, bundleName),
226
+ '-O'
227
+ ];
228
+ if (sourcemapOutput) {
229
+ args.push('-output-source-map');
230
+ }
231
+ console.log('Running hermesc: ' + hermesCommand + ' ' + args.join(' ') + '\n');
232
+ (0, _child_process.spawnSync)(hermesCommand, args, {
233
+ stdio: 'ignore'
234
+ });
200
235
  }
201
-
202
236
  async function pack(dir, output) {
203
- console.log('Packing');
204
- fs.ensureDirSync(_path2.default.dirname(output));
205
- await new Promise((resolve, reject) => {
206
- const zipfile = new _yazl.ZipFile();
207
-
208
- function addDirectory(root, rel) {
209
- if (rel) {
210
- zipfile.addEmptyDirectory(rel);
211
- }
212
- const childs = fs.readdirSync(root);
213
- for (const name of childs) {
214
- if (name === '.' || name === '..' || name === 'index.bundlejs.map') {
215
- continue;
216
- }
217
- const fullPath = _path2.default.join(root, name);
218
- const stat = fs.statSync(fullPath);
219
- if (stat.isFile()) {
220
- //console.log('adding: ' + rel+name);
221
- zipfile.addFile(fullPath, rel + name);
222
- } else if (stat.isDirectory()) {
223
- //console.log('adding: ' + rel+name+'/');
224
- addDirectory(fullPath, rel + name + '/');
237
+ console.log('Packing');
238
+ _fsextra.ensureDirSync(_path.default.dirname(output));
239
+ await new Promise((resolve, reject)=>{
240
+ const zipfile = new _yazl.ZipFile();
241
+ function addDirectory(root, rel) {
242
+ if (rel) {
243
+ zipfile.addEmptyDirectory(rel);
244
+ }
245
+ const childs = _fsextra.readdirSync(root);
246
+ for (const name of childs){
247
+ if (name === '.' || name === '..' || name === 'index.bundlejs.map') {
248
+ continue;
249
+ }
250
+ const fullPath = _path.default.join(root, name);
251
+ const stat = _fsextra.statSync(fullPath);
252
+ if (stat.isFile()) {
253
+ //console.log('adding: ' + rel+name);
254
+ zipfile.addFile(fullPath, rel + name);
255
+ } else if (stat.isDirectory()) {
256
+ //console.log('adding: ' + rel+name+'/');
257
+ addDirectory(fullPath, rel + name + '/');
258
+ }
259
+ }
225
260
  }
226
- }
227
- }
228
-
229
- addDirectory(dir, '');
230
-
231
- zipfile.outputStream.on('error', err => reject(err));
232
- zipfile.outputStream.pipe(fs.createWriteStream(output)).on('close', function () {
233
- resolve();
261
+ addDirectory(dir, '');
262
+ zipfile.outputStream.on('error', (err)=>reject(err));
263
+ zipfile.outputStream.pipe(_fsextra.createWriteStream(output)).on('close', function() {
264
+ resolve();
265
+ });
266
+ zipfile.end();
234
267
  });
235
- zipfile.end();
236
- });
237
- console.log('ppk热更包已生成并保存到: ' + output);
268
+ console.log('ppk热更包已生成并保存到: ' + output);
238
269
  }
239
-
240
270
  function readEntire(entry, zipFile) {
241
- const buffers = [];
242
- return new Promise((resolve, reject) => {
243
- zipFile.openReadStream(entry, (err, stream) => {
244
- stream.pipe({
245
- write(chunk) {
246
- buffers.push(chunk);
247
- },
248
- end() {
249
- resolve(Buffer.concat(buffers));
250
- },
251
- prependListener() {},
252
- on() {},
253
- once() {},
254
- emit() {}
255
- });
271
+ const buffers = [];
272
+ return new Promise((resolve, reject)=>{
273
+ zipFile.openReadStream(entry, (err, stream)=>{
274
+ stream.pipe({
275
+ write (chunk) {
276
+ buffers.push(chunk);
277
+ },
278
+ end () {
279
+ resolve(Buffer.concat(buffers));
280
+ },
281
+ prependListener () {},
282
+ on () {},
283
+ once () {},
284
+ emit () {}
285
+ });
286
+ });
256
287
  });
257
- });
258
288
  }
259
-
260
289
  function basename(fn) {
261
- const m = /^(.+\/)[^\/]+\/?$/.exec(fn);
262
- return m && m[1];
290
+ const m = /^(.+\/)[^\/]+\/?$/.exec(fn);
291
+ return m && m[1];
263
292
  }
264
-
265
293
  async function diffFromPPK(origin, next, output) {
266
- fs.ensureDirSync(_path2.default.dirname(output));
267
-
268
- const originEntries = {};
269
- const originMap = {};
270
-
271
- let originSource;
272
-
273
- await enumZipEntries(origin, (entry, zipFile) => {
274
- originEntries[entry.fileName] = entry;
275
- if (!/\/$/.test(entry.fileName)) {
276
- // isFile
277
- originMap[entry.crc32] = entry.fileName;
278
-
279
- if (entry.fileName === 'index.bundlejs') {
280
- // This is source.
281
- return readEntire(entry, zipFile).then(v => originSource = v);
282
- }
283
- }
284
- });
285
-
286
- if (!originSource) {
287
- throw new Error(`Bundle file not found! Please use default bundle file name and path.`);
288
- }
289
-
290
- const copies = {};
291
-
292
- const zipfile = new _yazl.ZipFile();
293
-
294
- const writePromise = new Promise((resolve, reject) => {
295
- zipfile.outputStream.on('error', err => {
296
- throw err;
297
- });
298
- zipfile.outputStream.pipe(fs.createWriteStream(output)).on('close', function () {
299
- resolve();
294
+ _fsextra.ensureDirSync(_path.default.dirname(output));
295
+ const originEntries = {};
296
+ const originMap = {};
297
+ let originSource;
298
+ await enumZipEntries(origin, (entry, zipFile)=>{
299
+ originEntries[entry.fileName] = entry;
300
+ if (!/\/$/.test(entry.fileName)) {
301
+ // isFile
302
+ originMap[entry.crc32] = entry.fileName;
303
+ if (entry.fileName === 'index.bundlejs') {
304
+ // This is source.
305
+ return readEntire(entry, zipFile).then((v)=>originSource = v);
306
+ }
307
+ }
300
308
  });
301
- });
302
-
303
- const addedEntry = {};
304
-
305
- function addEntry(fn) {
306
- //console.log(fn);
307
- if (!fn || addedEntry[fn]) {
308
- return;
309
+ if (!originSource) {
310
+ throw new Error(`Bundle file not found! Please use default bundle file name and path.`);
309
311
  }
310
- const base = basename(fn);
311
- if (base) {
312
- addEntry(base);
313
- }
314
- zipfile.addEmptyDirectory(fn);
315
- }
316
-
317
- const newEntries = {};
318
-
319
- await enumZipEntries(next, (entry, nextZipfile) => {
320
- newEntries[entry.fileName] = entry;
321
-
322
- if (/\/$/.test(entry.fileName)) {
323
- // Directory
324
- if (!originEntries[entry.fileName]) {
325
- addEntry(entry.fileName);
326
- }
327
- } else if (entry.fileName === 'index.bundlejs') {
328
- //console.log('Found bundle');
329
- return readEntire(entry, nextZipfile).then(newSource => {
330
- //console.log('Begin diff');
331
- zipfile.addBuffer(diff(originSource, newSource), 'index.bundlejs.patch');
332
- //console.log('End diff');
333
- });
334
- } else {
335
- // If same file.
336
- const originEntry = originEntries[entry.fileName];
337
- if (originEntry && originEntry.crc32 === entry.crc32) {
338
- // ignore
339
- return;
340
- }
341
-
342
- // If moved from other place
343
- if (originMap[entry.crc32]) {
344
- const base = basename(entry.fileName);
345
- if (!originEntries[base]) {
346
- addEntry(base);
347
- }
348
- copies[entry.fileName] = originMap[entry.crc32];
349
- return;
350
- }
351
-
352
- // New file.
353
- addEntry(basename(entry.fileName));
354
-
355
- return new Promise((resolve, reject) => {
356
- nextZipfile.openReadStream(entry, function (err, readStream) {
357
- if (err) {
358
- return reject(err);
359
- }
360
- zipfile.addReadStream(readStream, entry.fileName);
361
- readStream.on('end', () => {
362
- //console.log('add finished');
312
+ const copies = {};
313
+ const zipfile = new _yazl.ZipFile();
314
+ const writePromise = new Promise((resolve, reject)=>{
315
+ zipfile.outputStream.on('error', (err)=>{
316
+ throw err;
317
+ });
318
+ zipfile.outputStream.pipe(_fsextra.createWriteStream(output)).on('close', function() {
363
319
  resolve();
364
- });
365
320
  });
366
- });
321
+ });
322
+ const addedEntry = {};
323
+ function addEntry(fn) {
324
+ //console.log(fn);
325
+ if (!fn || addedEntry[fn]) {
326
+ return;
327
+ }
328
+ const base = basename(fn);
329
+ if (base) {
330
+ addEntry(base);
331
+ }
332
+ zipfile.addEmptyDirectory(fn);
367
333
  }
368
- });
369
-
370
- const deletes = {};
371
-
372
- for (let k in originEntries) {
373
- if (!newEntries[k]) {
374
- console.log('Delete ' + k);
375
- deletes[k] = 1;
334
+ const newEntries = {};
335
+ await enumZipEntries(next, (entry, nextZipfile)=>{
336
+ newEntries[entry.fileName] = entry;
337
+ if (/\/$/.test(entry.fileName)) {
338
+ // Directory
339
+ if (!originEntries[entry.fileName]) {
340
+ addEntry(entry.fileName);
341
+ }
342
+ } else if (entry.fileName === 'index.bundlejs') {
343
+ //console.log('Found bundle');
344
+ return readEntire(entry, nextZipfile).then((newSource)=>{
345
+ //console.log('Begin diff');
346
+ zipfile.addBuffer(diff(originSource, newSource), 'index.bundlejs.patch');
347
+ //console.log('End diff');
348
+ });
349
+ } else {
350
+ // If same file.
351
+ const originEntry = originEntries[entry.fileName];
352
+ if (originEntry && originEntry.crc32 === entry.crc32) {
353
+ // ignore
354
+ return;
355
+ }
356
+ // If moved from other place
357
+ if (originMap[entry.crc32]) {
358
+ const base = basename(entry.fileName);
359
+ if (!originEntries[base]) {
360
+ addEntry(base);
361
+ }
362
+ copies[entry.fileName] = originMap[entry.crc32];
363
+ return;
364
+ }
365
+ // New file.
366
+ addEntry(basename(entry.fileName));
367
+ return new Promise((resolve, reject)=>{
368
+ nextZipfile.openReadStream(entry, function(err, readStream) {
369
+ if (err) {
370
+ return reject(err);
371
+ }
372
+ zipfile.addReadStream(readStream, entry.fileName);
373
+ readStream.on('end', ()=>{
374
+ //console.log('add finished');
375
+ resolve();
376
+ });
377
+ });
378
+ });
379
+ }
380
+ });
381
+ const deletes = {};
382
+ for(let k in originEntries){
383
+ if (!newEntries[k]) {
384
+ console.log('Delete ' + k);
385
+ deletes[k] = 1;
386
+ }
376
387
  }
377
- }
378
-
379
- //console.log({copies, deletes});
380
- zipfile.addBuffer(Buffer.from(JSON.stringify({ copies, deletes })), '__diff.json');
381
- zipfile.end();
382
- await writePromise;
388
+ //console.log({copies, deletes});
389
+ zipfile.addBuffer(Buffer.from(JSON.stringify({
390
+ copies,
391
+ deletes
392
+ })), '__diff.json');
393
+ zipfile.end();
394
+ await writePromise;
383
395
  }
384
-
385
- async function diffFromPackage(origin, next, output, originBundleName, transformPackagePath = v => v) {
386
- fs.ensureDirSync(_path2.default.dirname(output));
387
-
388
- const originEntries = {};
389
- const originMap = {};
390
-
391
- let originSource;
392
-
393
- await enumZipEntries(origin, (entry, zipFile) => {
394
- if (!/\/$/.test(entry.fileName)) {
395
- const fn = transformPackagePath(entry.fileName);
396
- if (!fn) {
397
- return;
398
- }
399
-
400
- //console.log(fn);
401
- // isFile
402
- originEntries[fn] = entry.crc32;
403
- originMap[entry.crc32] = fn;
404
-
405
- if (fn === originBundleName) {
406
- // This is source.
407
- return readEntire(entry, zipFile).then(v => originSource = v);
408
- }
409
- }
410
- });
411
-
412
- if (!originSource) {
413
- throw new Error(`Bundle file not found! Please use default bundle file name and path.`);
414
- }
415
-
416
- const copies = {};
417
-
418
- const zipfile = new _yazl.ZipFile();
419
-
420
- const writePromise = new Promise((resolve, reject) => {
421
- zipfile.outputStream.on('error', err => {
422
- throw err;
423
- });
424
- zipfile.outputStream.pipe(fs.createWriteStream(output)).on('close', function () {
425
- resolve();
396
+ async function diffFromPackage(origin, next, output, originBundleName, transformPackagePath = (v)=>v) {
397
+ _fsextra.ensureDirSync(_path.default.dirname(output));
398
+ const originEntries = {};
399
+ const originMap = {};
400
+ let originSource;
401
+ await enumZipEntries(origin, (entry, zipFile)=>{
402
+ if (!/\/$/.test(entry.fileName)) {
403
+ const fn = transformPackagePath(entry.fileName);
404
+ if (!fn) {
405
+ return;
406
+ }
407
+ //console.log(fn);
408
+ // isFile
409
+ originEntries[fn] = entry.crc32;
410
+ originMap[entry.crc32] = fn;
411
+ if (fn === originBundleName) {
412
+ // This is source.
413
+ return readEntire(entry, zipFile).then((v)=>originSource = v);
414
+ }
415
+ }
426
416
  });
427
- });
428
-
429
- await enumZipEntries(next, (entry, nextZipfile) => {
430
- if (/\/$/.test(entry.fileName)) {
431
- // Directory
432
- zipfile.addEmptyDirectory(entry.fileName);
433
- } else if (entry.fileName === 'index.bundlejs') {
434
- //console.log('Found bundle');
435
- return readEntire(entry, nextZipfile).then(newSource => {
436
- //console.log('Begin diff');
437
- zipfile.addBuffer(diff(originSource, newSource), 'index.bundlejs.patch');
438
- //console.log('End diff');
439
- });
440
- } else {
441
- // If same file.
442
- if (originEntries[entry.fileName] === entry.crc32) {
443
- copies[entry.fileName] = '';
444
- return;
445
- }
446
- // If moved from other place
447
- if (originMap[entry.crc32]) {
448
- copies[entry.fileName] = originMap[entry.crc32];
449
- return;
450
- }
451
-
452
- return new Promise((resolve, reject) => {
453
- nextZipfile.openReadStream(entry, function (err, readStream) {
454
- if (err) {
455
- return reject(err);
456
- }
457
- zipfile.addReadStream(readStream, entry.fileName);
458
- readStream.on('end', () => {
459
- //console.log('add finished');
417
+ if (!originSource) {
418
+ throw new Error(`Bundle file not found! Please use default bundle file name and path.`);
419
+ }
420
+ const copies = {};
421
+ const zipfile = new _yazl.ZipFile();
422
+ const writePromise = new Promise((resolve, reject)=>{
423
+ zipfile.outputStream.on('error', (err)=>{
424
+ throw err;
425
+ });
426
+ zipfile.outputStream.pipe(_fsextra.createWriteStream(output)).on('close', function() {
460
427
  resolve();
461
- });
462
428
  });
463
- });
464
- }
465
- });
466
-
467
- zipfile.addBuffer(Buffer.from(JSON.stringify({ copies })), '__diff.json');
468
- zipfile.end();
469
- await writePromise;
470
- }
471
-
472
- function enumZipEntries(zipFn, callback) {
473
- return new Promise((resolve, reject) => {
474
- (0, _yauzl.open)(zipFn, { lazyEntries: true }, (err, zipfile) => {
475
- if (err) {
476
- return reject(err);
477
- }
478
- zipfile.on('end', resolve);
479
- zipfile.on('error', reject);
480
- zipfile.on('entry', entry => {
481
- const result = callback(entry, zipfile);
482
- if (result && typeof result.then === 'function') {
483
- result.then(() => zipfile.readEntry());
429
+ });
430
+ await enumZipEntries(next, (entry, nextZipfile)=>{
431
+ if (/\/$/.test(entry.fileName)) {
432
+ // Directory
433
+ zipfile.addEmptyDirectory(entry.fileName);
434
+ } else if (entry.fileName === 'index.bundlejs') {
435
+ //console.log('Found bundle');
436
+ return readEntire(entry, nextZipfile).then((newSource)=>{
437
+ //console.log('Begin diff');
438
+ zipfile.addBuffer(diff(originSource, newSource), 'index.bundlejs.patch');
439
+ //console.log('End diff');
440
+ });
484
441
  } else {
485
- zipfile.readEntry();
442
+ // If same file.
443
+ if (originEntries[entry.fileName] === entry.crc32) {
444
+ copies[entry.fileName] = '';
445
+ return;
446
+ }
447
+ // If moved from other place
448
+ if (originMap[entry.crc32]) {
449
+ copies[entry.fileName] = originMap[entry.crc32];
450
+ return;
451
+ }
452
+ return new Promise((resolve, reject)=>{
453
+ nextZipfile.openReadStream(entry, function(err, readStream) {
454
+ if (err) {
455
+ return reject(err);
456
+ }
457
+ zipfile.addReadStream(readStream, entry.fileName);
458
+ readStream.on('end', ()=>{
459
+ //console.log('add finished');
460
+ resolve();
461
+ });
462
+ });
463
+ });
486
464
  }
487
- });
488
- zipfile.readEntry();
489
465
  });
490
- });
466
+ zipfile.addBuffer(Buffer.from(JSON.stringify({
467
+ copies
468
+ })), '__diff.json');
469
+ zipfile.end();
470
+ await writePromise;
471
+ }
472
+ function enumZipEntries(zipFn, callback) {
473
+ return new Promise((resolve, reject)=>{
474
+ (0, _yauzl.open)(zipFn, {
475
+ lazyEntries: true
476
+ }, (err, zipfile)=>{
477
+ if (err) {
478
+ return reject(err);
479
+ }
480
+ zipfile.on('end', resolve);
481
+ zipfile.on('error', reject);
482
+ zipfile.on('entry', (entry)=>{
483
+ const result = callback(entry, zipfile);
484
+ if (result && typeof result.then === 'function') {
485
+ result.then(()=>zipfile.readEntry());
486
+ } else {
487
+ zipfile.readEntry();
488
+ }
489
+ });
490
+ zipfile.readEntry();
491
+ });
492
+ });
491
493
  }
492
-
493
494
  function diffArgsCheck(args, options, diffFn) {
494
- const [origin, next] = args;
495
-
496
- if (!origin || !next) {
497
- console.error(`Usage: pushy ${diffFn} <origin> <next>`);
498
- process.exit(1);
499
- }
500
-
501
- if (diffFn.startsWith('hdiff')) {
502
- if (!hdiff) {
503
- console.error(`This function needs "node-hdiffpatch".
504
- Please run "npm i node-hdiffpatch" to install`);
505
- process.exit(1);
495
+ const [origin, next] = args;
496
+ if (!origin || !next) {
497
+ console.error(`Usage: pushy ${diffFn} <origin> <next>`);
498
+ process.exit(1);
506
499
  }
507
- diff = hdiff;
508
- } else {
509
- if (!bsdiff) {
510
- console.error(`This function needs "node-bsdiff".
500
+ if (diffFn.startsWith('hdiff')) {
501
+ if (!hdiff) {
502
+ console.error(`This function needs "node-hdiffpatch".
503
+ Please run "npm i node-hdiffpatch" to install`);
504
+ process.exit(1);
505
+ }
506
+ diff = hdiff;
507
+ } else {
508
+ if (!bsdiff) {
509
+ console.error(`This function needs "node-bsdiff".
511
510
  Please run "npm i node-bsdiff" to install`);
512
- process.exit(1);
511
+ process.exit(1);
512
+ }
513
+ diff = bsdiff;
513
514
  }
514
- diff = bsdiff;
515
- }
516
- const { output } = options;
517
-
518
- return {
519
- origin,
520
- next,
521
- realOutput: output.replace(/\$\{time\}/g, '' + Date.now())
522
- };
515
+ const { output } = options;
516
+ return {
517
+ origin,
518
+ next,
519
+ realOutput: output.replace(/\$\{time\}/g, '' + Date.now())
520
+ };
523
521
  }
524
-
525
- const commands = exports.commands = {
526
- bundle: async function ({ options }) {
527
- const platform = (0, _app.checkPlatform)(options.platform || (await (0, _utils.question)('平台(ios/android):')));
528
-
529
- let { bundleName, entryFile, intermediaDir, output, dev, sourcemap } = (0, _utils.translateOptions)(_extends({}, options, {
530
- platform
531
- }));
532
-
533
- const sourcemapOutput = _path2.default.join(intermediaDir, bundleName + '.map');
534
-
535
- const realOutput = output.replace(/\$\{time\}/g, '' + Date.now());
536
-
537
- if (!platform) {
538
- throw new Error('Platform must be specified.');
539
- }
540
-
541
- const { version, major, minor } = (0, _utils.getRNVersion)();
542
-
543
- console.log('Bundling with react-native: ', version);
544
- (0, _utils.printVersionCommand)();
545
-
546
- await runReactNativeBundleCommand(bundleName, dev, entryFile, intermediaDir, platform, sourcemap ? sourcemapOutput : '');
547
-
548
- await pack(_path2.default.resolve(intermediaDir), realOutput);
549
-
550
- const v = await (0, _utils.question)('是否现在上传此热更包?(Y/N)');
551
- if (v.toLowerCase() === 'y') {
552
- await this.publish({
553
- args: [realOutput],
554
- options: {
555
- platform
522
+ const commands = {
523
+ bundle: async function({ options }) {
524
+ const platform = (0, _app.checkPlatform)(options.platform || await (0, _utils.question)('平台(ios/android):'));
525
+ let { bundleName, entryFile, intermediaDir, output, dev, sourcemap } = (0, _utils.translateOptions)({
526
+ ...options,
527
+ platform
528
+ });
529
+ const sourcemapOutput = _path.default.join(intermediaDir, bundleName + '.map');
530
+ const realOutput = output.replace(/\$\{time\}/g, '' + Date.now());
531
+ if (!platform) {
532
+ throw new Error('Platform must be specified.');
556
533
  }
557
- });
534
+ const { version, major, minor } = (0, _utils.getRNVersion)();
535
+ console.log('Bundling with react-native: ', version);
536
+ await runReactNativeBundleCommand(bundleName, dev, entryFile, intermediaDir, platform, sourcemap ? sourcemapOutput : '');
537
+ await pack(_path.default.resolve(intermediaDir), realOutput);
538
+ const v = await (0, _utils.question)('是否现在上传此热更包?(Y/N)');
539
+ if (v.toLowerCase() === 'y') {
540
+ await this.publish({
541
+ args: [
542
+ realOutput
543
+ ],
544
+ options: {
545
+ platform
546
+ }
547
+ });
548
+ }
549
+ },
550
+ async diff ({ args, options }) {
551
+ const { origin, next, realOutput } = diffArgsCheck(args, options, 'diff');
552
+ await diffFromPPK(origin, next, realOutput, 'index.bundlejs');
553
+ console.log(`${realOutput} generated.`);
554
+ },
555
+ async hdiff ({ args, options }) {
556
+ const { origin, next, realOutput } = diffArgsCheck(args, options, 'hdiff');
557
+ await diffFromPPK(origin, next, realOutput, 'index.bundlejs');
558
+ console.log(`${realOutput} generated.`);
559
+ },
560
+ async diffFromApk ({ args, options }) {
561
+ const { origin, next, realOutput } = diffArgsCheck(args, options, 'diffFromApk');
562
+ await diffFromPackage(origin, next, realOutput, 'assets/index.android.bundle');
563
+ console.log(`${realOutput} generated.`);
564
+ },
565
+ async hdiffFromApk ({ args, options }) {
566
+ const { origin, next, realOutput } = diffArgsCheck(args, options, 'hdiffFromApk');
567
+ await diffFromPackage(origin, next, realOutput, 'assets/index.android.bundle');
568
+ console.log(`${realOutput} generated.`);
569
+ },
570
+ async diffFromIpa ({ args, options }) {
571
+ const { origin, next, realOutput } = diffArgsCheck(args, options, 'diffFromIpa');
572
+ await diffFromPackage(origin, next, realOutput, 'main.jsbundle', (v)=>{
573
+ const m = /^Payload\/[^/]+\/(.+)$/.exec(v);
574
+ return m && m[1];
575
+ });
576
+ console.log(`${realOutput} generated.`);
577
+ },
578
+ async hdiffFromIpa ({ args, options }) {
579
+ const { origin, next, realOutput } = diffArgsCheck(args, options, 'hdiffFromIpa');
580
+ await diffFromPackage(origin, next, realOutput, 'main.jsbundle', (v)=>{
581
+ const m = /^Payload\/[^/]+\/(.+)$/.exec(v);
582
+ return m && m[1];
583
+ });
584
+ console.log(`${realOutput} generated.`);
558
585
  }
559
- },
560
-
561
- async diff({ args, options }) {
562
- const { origin, next, realOutput } = diffArgsCheck(args, options, 'diff');
563
-
564
- await diffFromPPK(origin, next, realOutput, 'index.bundlejs');
565
- console.log(`${realOutput} generated.`);
566
- },
567
-
568
- async hdiff({ args, options }) {
569
- const { origin, next, realOutput } = diffArgsCheck(args, options, 'hdiff');
570
-
571
- await diffFromPPK(origin, next, realOutput, 'index.bundlejs');
572
- console.log(`${realOutput} generated.`);
573
- },
574
-
575
- async diffFromApk({ args, options }) {
576
- const { origin, next, realOutput } = diffArgsCheck(args, options, 'diffFromApk');
577
-
578
- await diffFromPackage(origin, next, realOutput, 'assets/index.android.bundle');
579
- console.log(`${realOutput} generated.`);
580
- },
581
-
582
- async hdiffFromApk({ args, options }) {
583
- const { origin, next, realOutput } = diffArgsCheck(args, options, 'hdiffFromApk');
584
-
585
- await diffFromPackage(origin, next, realOutput, 'assets/index.android.bundle');
586
- console.log(`${realOutput} generated.`);
587
- },
588
-
589
- async diffFromIpa({ args, options }) {
590
- const { origin, next, realOutput } = diffArgsCheck(args, options, 'diffFromIpa');
591
-
592
- await diffFromPackage(origin, next, realOutput, 'main.jsbundle', v => {
593
- const m = /^Payload\/[^/]+\/(.+)$/.exec(v);
594
- return m && m[1];
595
- });
596
-
597
- console.log(`${realOutput} generated.`);
598
- },
599
-
600
- async hdiffFromIpa({ args, options }) {
601
- const { origin, next, realOutput } = diffArgsCheck(args, options, 'hdiffFromIpa');
602
-
603
- await diffFromPackage(origin, next, realOutput, 'main.jsbundle', v => {
604
- const m = /^Payload\/[^/]+\/(.+)$/.exec(v);
605
- return m && m[1];
606
- });
607
-
608
- console.log(`${realOutput} generated.`);
609
- }
610
- };
586
+ };