@mpxjs/webpack-plugin 2.6.103 → 2.7.0-alpha.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.
Files changed (58) hide show
  1. package/lib/dependencies/AppEntryDependency.js +56 -0
  2. package/lib/dependencies/CommonJsVariableDependency.js +74 -0
  3. package/lib/dependencies/DynamicEntryDependency.js +127 -0
  4. package/lib/dependencies/FlagPluginDependency.js +23 -0
  5. package/lib/dependencies/InjectDependency.js +43 -0
  6. package/lib/dependencies/RecordGlobalComponentsDependency.js +50 -0
  7. package/lib/dependencies/RecordStaticResourceDependency.js +47 -0
  8. package/lib/{dependency → dependencies}/ReplaceDependency.js +19 -2
  9. package/lib/dependencies/ResolveDependency.js +83 -0
  10. package/lib/extractor.js +72 -179
  11. package/lib/file-loader.js +7 -19
  12. package/lib/helpers.js +41 -331
  13. package/lib/index.js +475 -365
  14. package/lib/json-compiler/helper.js +152 -0
  15. package/lib/json-compiler/index.js +148 -407
  16. package/lib/json-compiler/plugin.js +134 -0
  17. package/lib/json-compiler/{theme-loader.js → theme.js} +5 -3
  18. package/lib/loader.js +78 -177
  19. package/lib/native-loader.js +40 -70
  20. package/lib/record-loader.js +11 -0
  21. package/lib/{path-loader.js → resolve-loader.js} +0 -0
  22. package/lib/runtime/i18n.wxs +3 -3
  23. package/lib/selector.js +8 -7
  24. package/lib/style-compiler/index.js +14 -15
  25. package/lib/template-compiler/compiler.js +16 -153
  26. package/lib/template-compiler/index.js +46 -132
  27. package/lib/url-loader.js +11 -29
  28. package/lib/utils/add-query.js +1 -1
  29. package/lib/utils/const.js +5 -0
  30. package/lib/utils/emit-file.js +10 -0
  31. package/lib/utils/get-entry-name.js +13 -0
  32. package/lib/utils/is-url-request.js +10 -1
  33. package/lib/utils/normalize.js +0 -13
  34. package/lib/utils/parse-request.js +3 -3
  35. package/lib/utils/set.js +47 -0
  36. package/lib/utils/stringify-loaders-resource.js +25 -0
  37. package/lib/utils/stringify-query.js +4 -0
  38. package/lib/web/processScript.js +3 -3
  39. package/lib/web/processTemplate.js +2 -0
  40. package/lib/wxml/{wxml-loader.js → loader.js} +24 -60
  41. package/lib/wxs/WxsModuleIdsPlugin.js +32 -0
  42. package/lib/wxs/WxsParserPlugin.js +2 -2
  43. package/lib/wxs/WxsPlugin.js +4 -8
  44. package/lib/wxs/WxsTemplatePlugin.js +46 -92
  45. package/lib/wxs/{wxs-i18n-loader.js → i18n-loader.js} +0 -0
  46. package/lib/wxs/{wxs-loader.js → loader.js} +33 -38
  47. package/lib/wxs/{wxs-pre-loader.js → pre-loader.js} +0 -0
  48. package/lib/wxss/loader.js +31 -43
  49. package/lib/wxss/localsLoader.js +1 -5
  50. package/package.json +4 -8
  51. package/lib/content-loader.js +0 -13
  52. package/lib/dependency/ChildCompileDependency.js +0 -24
  53. package/lib/dependency/InjectDependency.js +0 -26
  54. package/lib/dependency/RemovedModuleDependency.js +0 -23
  55. package/lib/dependency/ResolveDependency.js +0 -49
  56. package/lib/plugin-loader.js +0 -287
  57. package/lib/utils/try-require.js +0 -16
  58. package/lib/wxss/getImportPrefix.js +0 -30
@@ -1,51 +1,28 @@
1
1
  const async = require('async')
2
2
  const JSON5 = require('json5')
3
3
  const path = require('path')
4
- const SingleEntryPlugin = require('webpack/lib/SingleEntryPlugin')
5
- const loaderUtils = require('loader-utils')
6
4
  const parseComponent = require('../parser')
7
5
  const config = require('../config')
8
- const normalize = require('../utils/normalize')
9
- const nativeLoaderPath = normalize.lib('native-loader')
10
- const themeLoaderPath = normalize.lib('json-compiler/theme-loader')
11
- const extractorPath = normalize.lib('extractor')
12
6
  const parseRequest = require('../utils/parse-request')
13
7
  const mpxJSON = require('../utils/mpx-json')
14
- const toPosix = require('../utils/to-posix')
15
8
  const fixUsingComponent = require('../utils/fix-using-component')
16
9
  const getRulesRunner = require('../platform/index')
17
- const isUrlRequestRaw = require('../utils/is-url-request')
18
10
  const addQuery = require('../utils/add-query')
19
11
  const readJsonForSrc = require('../utils/read-json-for-src')
20
- const getMainCompilation = require('../utils/get-main-compilation')
12
+ const createHelpers = require('../helpers')
13
+ const createJSONHelper = require('./helper')
14
+ const RecordGlobalComponentsDependency = require('../dependencies/RecordGlobalComponentsDependency')
15
+ const { MPX_DISABLE_EXTRACTOR_CACHE } = require('../utils/const')
21
16
 
22
- module.exports = function (raw = '{}') {
23
- // 该loader中会在每次编译中动态添加entry,不能缓存,否则watch不好使
24
- this.cacheable(false)
17
+ module.exports = function (content) {
25
18
  const nativeCallback = this.async()
26
- const options = loaderUtils.getOptions(this) || {}
27
- const mainCompilation = getMainCompilation(this._compilation)
28
- const mpx = mainCompilation.__mpx__
29
-
30
- const emitWarning = (msg) => {
31
- this.emitWarning(
32
- new Error('[json compiler][' + this.resource + ']: ' + msg)
33
- )
34
- }
35
-
36
- const emitError = (msg) => {
37
- this.emitError(
38
- new Error('[json compiler][' + this.resource + ']: ' + msg)
39
- )
40
- }
41
-
42
- const stringifyRequest = r => loaderUtils.stringifyRequest(this, r)
43
- const isUrlRequest = r => isUrlRequestRaw(r, options.root)
44
- const urlToRequest = r => loaderUtils.urlToRequest(r)
19
+ const mpx = this.getMpx()
45
20
 
46
21
  if (!mpx) {
47
- return nativeCallback(null, raw)
22
+ return nativeCallback(null, content)
48
23
  }
24
+ // json模块必须每次都创建(但并不是每次都需要build),用于动态添加编译入口,传递信息以禁用父级extractor的缓存
25
+ this.emitFile(MPX_DISABLE_EXTRACTOR_CACHE, '', undefined, { skipEmit: true })
49
26
 
50
27
  // 微信插件下要求组件使用相对路径
51
28
  const useRelativePath = mpx.isPluginMode || mpx.useRelativePath
@@ -53,35 +30,60 @@ module.exports = function (raw = '{}') {
53
30
  const packageName = queryObj.packageRoot || mpx.currentPackageRoot || 'main'
54
31
  const pagesMap = mpx.pagesMap
55
32
  const componentsMap = mpx.componentsMap[packageName]
56
- const getEntryNode = mpx.getEntryNode
33
+ const appInfo = mpx.appInfo
57
34
  const mode = mpx.mode
58
35
  const env = mpx.env
59
36
  const defs = mpx.defs
60
37
  const globalSrcMode = mpx.srcMode
61
38
  const localSrcMode = queryObj.mode
62
39
  const srcMode = localSrcMode || globalSrcMode
63
- const resolveMode = mpx.resolveMode
64
- const externals = mpx.externals
65
- const pathHash = mpx.pathHash
40
+
66
41
  const isApp = !(pagesMap[resourcePath] || componentsMap[resourcePath])
67
42
  const publicPath = this._compilation.outputOptions.publicPath || ''
68
43
  const fs = this._compiler.inputFileSystem
69
- const rootName = mainCompilation._preparedEntrypoints[0].name
70
- const currentName = componentsMap[resourcePath] || pagesMap[resourcePath] || rootName
71
- const currentPath = publicPath + currentName
72
44
 
73
- // json模块都是由.mpx或.js的入口模块引入,且引入关系为一对一,其issuer必为入口module
74
- const entryModule = this._module.issuer
75
- // 通过rawRequest关联entryNode和entryModule
76
- const entryRequest = entryModule.rawRequest
77
- const entryType = isApp ? 'App' : pagesMap[resourcePath] ? 'Page' : 'Component'
45
+ const emitWarning = (msg) => {
46
+ this.emitWarning(
47
+ new Error('[json compiler][' + this.resource + ']: ' + msg)
48
+ )
49
+ }
50
+
51
+ const emitError = (msg) => {
52
+ this.emitError(
53
+ new Error('[json compiler][' + this.resource + ']: ' + msg)
54
+ )
55
+ }
56
+
57
+ const {
58
+ resolve,
59
+ isUrlRequest,
60
+ urlToRequest,
61
+ processPage,
62
+ processDynamicEntry,
63
+ processComponent,
64
+ processJsExport
65
+ } = createJSONHelper({
66
+ loaderContext: this,
67
+ emitWarning,
68
+ emitError
69
+ })
70
+
71
+ const { getRequestString } = createHelpers(this)
72
+
73
+ let currentName
74
+
75
+ if (isApp) {
76
+ currentName = appInfo.name
77
+ } else {
78
+ currentName = componentsMap[resourcePath] || pagesMap[resourcePath]
79
+ }
78
80
 
79
- const currentEntry = getEntryNode(entryRequest, entryType, entryModule)
81
+ const relativePath = useRelativePath ? publicPath + path.dirname(currentName) : ''
80
82
 
81
83
  const copydir = (dir, context, callback) => {
82
84
  fs.readdir(dir, (err, files) => {
83
85
  if (err) return callback(err)
84
- async.forEach(files, (file, callback) => {
86
+ async.each(files, (file, callback) => {
85
87
  file = path.join(dir, file)
86
88
  async.waterfall([
87
89
  (callback) => {
@@ -111,48 +113,12 @@ module.exports = function (raw = '{}') {
111
113
  })
112
114
  }
113
115
 
114
- let entryDeps = new Set()
115
-
116
- let cacheCallback
117
-
118
- const checkEntryDeps = (callback) => {
119
- callback = callback || cacheCallback
120
- if (callback && entryDeps.size === 0) {
121
- callback()
122
- } else {
123
- cacheCallback = callback
124
- }
125
- }
126
-
127
- const addEntrySafely = (resource, name, callback) => {
128
- // 如果loader已经回调,就不再添加entry
129
- if (callbacked) return callback()
130
- const dep = SingleEntryPlugin.createDependency(resource, name)
131
- entryDeps.add(dep)
132
- this._compilation.addEntry(this._compiler.context, dep, name, (err, module) => {
133
- entryDeps.delete(dep)
134
- checkEntryDeps()
135
- callback(err, module)
136
- })
137
- }
138
-
139
- // const deleteEntry = (name) => {
140
- // const index = this._compilation._preparedEntrypoints.findIndex(slot => slot.name === name)
141
- // if (index >= 0) {
142
- // this._compilation._preparedEntrypoints.splice(index, 1)
143
- // }
144
- // }
145
-
146
- let callbacked = false
147
116
  const callback = (err, processOutput) => {
148
- checkEntryDeps(() => {
149
- callbacked = true
150
- if (err) return nativeCallback(err)
151
- let output = `var json = ${JSON.stringify(json, null, 2)};\n`
152
- if (processOutput) output = processOutput(output)
153
- output += `module.exports = JSON.stringify(json, null, 2);\n`
154
- nativeCallback(null, output)
155
- })
117
+ if (err) return nativeCallback(err)
118
+ let output = `var json = ${JSON.stringify(json, null, 2)};\n`
119
+ if (processOutput) output = processOutput(output)
120
+ output += `module.exports = JSON.stringify(json, null, 2);\n`
121
+ nativeCallback(null, output)
156
122
  }
157
123
 
158
124
  let json = {}
@@ -160,9 +126,9 @@ module.exports = function (raw = '{}') {
160
126
  // 使用了MPXJSON的话先编译
161
127
  // 此处需要使用真实的resourcePath
162
128
  if (this.resourcePath.endsWith('.json.js')) {
163
- json = JSON.parse(mpxJSON.compileMPXJSONText({ source: raw, defs, filePath: this.resourcePath }))
129
+ json = JSON.parse(mpxJSON.compileMPXJSONText({ source: content, defs, filePath: this.resourcePath }))
164
130
  } else {
165
- json = JSON5.parse(raw)
131
+ json = JSON5.parse(content || '{}')
166
132
  }
167
133
  } catch (err) {
168
134
  return callback(err)
@@ -220,13 +186,7 @@ module.exports = function (raw = '{}') {
220
186
  } else {
221
187
  // 保存全局注册组件
222
188
  if (json.usingComponents) {
223
- mpx.usingComponents = {}
224
- Object.keys(json.usingComponents).forEach((key) => {
225
- const request = json.usingComponents[key]
226
- mpx.usingComponents[key] = addQuery(request, {
227
- context: this.context
228
- })
229
- })
189
+ this._module.addPresentationalDependency(new RecordGlobalComponentsDependency(json.usingComponents, this.context))
230
190
  }
231
191
  }
232
192
 
@@ -236,120 +196,24 @@ module.exports = function (raw = '{}') {
236
196
  rulesRunner(json)
237
197
  }
238
198
 
239
- const resolve = (context, request, callback) => {
240
- const { queryObj } = parseRequest(request)
241
- context = queryObj.context || context
242
- return this.resolve(context, request, callback)
243
- }
244
-
245
199
  const processComponents = (components, context, callback) => {
246
200
  if (components) {
247
- async.forEachOf(components, (component, name, callback) => {
248
- processComponent(component, context, (componentPath) => {
249
- if (useRelativePath === true) {
250
- componentPath = toPosix(path.relative(path.dirname(currentPath), componentPath))
251
- }
252
- components[name] = componentPath
253
- }, undefined, callback)
201
+ async.eachOf(components, (component, name, callback) => {
202
+ processComponent(component, context, { relativePath }, (err, entry) => {
203
+ if (err) return callback(err)
204
+ components[name] = entry
205
+ callback()
206
+ })
254
207
  }, callback)
255
208
  } else {
256
209
  callback()
257
210
  }
258
211
  }
259
212
 
260
- const processComponent = (component, context, rewritePath, outputPath, callback) => {
261
- if (!isUrlRequest(component)) return callback()
262
- if (resolveMode === 'native') {
263
- component = urlToRequest(component)
264
- }
265
-
266
- if (externals.some((external) => {
267
- if (typeof external === 'string') {
268
- return external === component
269
- } else if (external instanceof RegExp) {
270
- return external.test(component)
271
- }
272
- return false
273
- })) {
274
- return callback()
275
- }
276
-
277
- resolve(context, component, (err, resource, info) => {
278
- if (err) return callback(err)
279
- const resourcePath = parseRequest(resource).resourcePath
280
- const parsed = path.parse(resourcePath)
281
- const ext = parsed.ext
282
- const resourceName = path.join(parsed.dir, parsed.name)
283
-
284
- if (!outputPath) {
285
- if (ext === '.js' && resourceName.includes('node_modules')) {
286
- let root = info.descriptionFileRoot
287
- let name = 'nativeComponent'
288
- if (info.descriptionFileData) {
289
- if (info.descriptionFileData.miniprogram) {
290
- root = path.join(root, info.descriptionFileData.miniprogram)
291
- }
292
- if (info.descriptionFileData.name) {
293
- // 去掉name里面的@符号,因为支付宝不支持文件路径上有@
294
- name = info.descriptionFileData.name.split('@').join('')
295
- }
296
- }
297
- let relativePath = path.relative(root, resourceName)
298
- outputPath = path.join('components', name + pathHash(root), relativePath)
299
- } else {
300
- let componentName = parsed.name
301
- outputPath = path.join('components', componentName + pathHash(resourcePath), componentName)
302
- }
303
- }
304
- const { packageRoot, outputPath: componentPath, alreadyOutputed } = mpx.getPackageInfo({
305
- resource,
306
- outputPath,
307
- resourceType: 'components',
308
- warn: (err) => {
309
- this.emitWarning(err)
310
- }
311
- })
312
- if (packageRoot) {
313
- resource = addQuery(resource, {
314
- packageRoot
315
- })
316
- }
317
- rewritePath && rewritePath(publicPath + componentPath)
318
- if (ext === '.js') {
319
- resource = '!!' + nativeLoaderPath + '!' + resource
320
- }
321
- currentEntry.addChild(getEntryNode(resource, 'Component'))
322
- // 如果之前已经创建了入口,直接return
323
- if (alreadyOutputed) {
324
- return callback()
325
- }
326
- addEntrySafely(resource, componentPath, callback)
327
- })
328
- }
329
-
330
- // 由于json模块都是由mpx/js文件引入的,需要向上找两层issuer获取真实的引用源
331
- const getJsonIssuer = (module) => {
332
- if (module.issuer) {
333
- return module.issuer.issuer
334
- }
335
- }
336
-
337
213
  if (isApp) {
338
- if (!mpx.hasApp) {
339
- mpx.hasApp = true
340
- } else {
341
- const issuer = getJsonIssuer(this._module)
342
- if (issuer) {
343
- emitError(`[json compiler]:Mpx单次构建中只能存在一个App,当前组件/页面[${this.resource}]通过[${issuer.resource}]非法引入,引用的资源将被忽略,请确保组件/页面资源通过usingComponents/pages配置引入!`)
344
- } else {
345
- emitError(`[json compiler]:Mpx单次构建中只能存在一个App,请检查当前entry中的资源[${this.resource}]是否为组件/页面,通过添加?component/page查询字符串显式声明该资源是组件/页面!`)
346
- }
347
- return callback()
348
- }
349
214
  // app.json
350
- const subPackagesCfg = {}
351
215
  const localPages = []
352
- const processSubPackagesQueue = []
216
+ const subPackagesCfg = {}
353
217
  // 添加首页标识
354
218
  if (json.pages && json.pages[0]) {
355
219
  if (typeof json.pages[0] !== 'string') {
@@ -359,9 +223,33 @@ module.exports = function (raw = '{}') {
359
223
  }
360
224
  }
361
225
 
226
+ const processPages = (pages, context, tarRoot = '', callback) => {
227
+ if (pages) {
228
+ async.each(pages, (page, callback) => {
229
+ const { queryObj } = parseRequest(page)
230
+ processPage(page, context, tarRoot, (err, entry) => {
231
+ if (err) return callback(err)
232
+ if (tarRoot && subPackagesCfg) {
233
+ subPackagesCfg[tarRoot].pages.push(entry)
234
+ } else {
235
+ // 确保首页
236
+ if (queryObj.isFirst) {
237
+ localPages.unshift(entry)
238
+ } else {
239
+ localPages.push(entry)
240
+ }
241
+ }
242
+ callback()
243
+ })
244
+ }, callback)
245
+ } else {
246
+ callback()
247
+ }
248
+ }
249
+
362
250
  const processPackages = (packages, context, callback) => {
363
251
  if (packages) {
364
- async.forEach(packages, (packagePath, callback) => {
252
+ async.each(packages, (packagePath, callback) => {
365
253
  const { queryObj } = parseRequest(packagePath)
366
254
  async.waterfall([
367
255
  (callback) => {
@@ -422,12 +310,12 @@ module.exports = function (raw = '{}') {
422
310
  subPackage.plugins = content.plugins
423
311
  }
424
312
 
425
- processSubPackagesQueue.push((callback) => {
313
+ processSelfQueue.push((callback) => {
426
314
  processSubPackage(subPackage, context, callback)
427
315
  })
428
316
  } else {
429
317
  processSelfQueue.push((callback) => {
430
- processPages(content.pages, '', '', context, callback)
318
+ processPages(content.pages, context, '', callback)
431
319
  })
432
320
  }
433
321
  }
@@ -449,7 +337,7 @@ module.exports = function (raw = '{}') {
449
337
  }
450
338
  }
451
339
 
452
- const getOtherConfig = (raw) => {
340
+ const getOtherConfig = (config) => {
453
341
  let result = {}
454
342
  let blackListMap = {
455
343
  tarRoot: true,
@@ -457,9 +345,9 @@ module.exports = function (raw = '{}') {
457
345
  root: true,
458
346
  pages: true
459
347
  }
460
- for (let key in raw) {
348
+ for (let key in config) {
461
349
  if (!blackListMap[key]) {
462
- result[key] = raw[key]
350
+ result[key] = config[key]
463
351
  }
464
352
  }
465
353
  return result
@@ -487,16 +375,13 @@ module.exports = function (raw = '{}') {
487
375
  pages: [],
488
376
  ...otherConfig
489
377
  }
490
- mpx.currentPackageRoot = tarRoot
491
- mpx.componentsMap[tarRoot] = {}
492
- mpx.staticResourcesMap[tarRoot] = {}
493
- mpx.subpackageModulesMap[tarRoot] = {}
378
+ context = path.join(context, srcRoot)
494
379
  async.parallel([
495
380
  (callback) => {
496
- processPages(subPackage.pages, srcRoot, tarRoot, context, callback)
381
+ processPages(subPackage.pages, context, tarRoot, callback)
497
382
  },
498
383
  (callback) => {
499
- processPlugins(subPackage.plugins, srcRoot, tarRoot, context, callback)
384
+ processPlugins(subPackage.plugins, context, tarRoot, callback)
500
385
  }
501
386
  ], callback)
502
387
  } else {
@@ -506,92 +391,8 @@ module.exports = function (raw = '{}') {
506
391
 
507
392
  const processSubPackages = (subPackages, context, callback) => {
508
393
  if (subPackages) {
509
- subPackages.forEach((subPackage) => {
510
- processSubPackagesQueue.push((callback) => {
511
- processSubPackage(subPackage, context, callback)
512
- })
513
- })
514
- }
515
- callback()
516
- }
517
-
518
- const getPageName = (resourcePath, ext) => {
519
- const baseName = path.basename(resourcePath, ext)
520
- return path.join('pages', baseName + pathHash(resourcePath), baseName)
521
- }
522
-
523
- const processPages = (pages, srcRoot = '', tarRoot = '', context, callback) => {
524
- if (pages) {
525
- context = path.join(context, srcRoot)
526
- async.forEach(pages, (page, callback) => {
527
- let aliasPath = ''
528
- if (typeof page !== 'string') {
529
- aliasPath = page.path
530
- page = page.src
531
- }
532
- if (!isUrlRequest(page)) return callback()
533
- if (resolveMode === 'native') {
534
- page = urlToRequest(page)
535
- }
536
- resolve(context, page, (err, resource) => {
537
- if (err) return callback(err)
538
- const { resourcePath, queryObj } = parseRequest(resource)
539
- const ext = path.extname(resourcePath)
540
- // 获取pageName
541
- let pageName
542
- if (aliasPath) {
543
- pageName = toPosix(path.join(tarRoot, aliasPath))
544
- // 判断 key 存在重复情况直接报错
545
- for (let key in pagesMap) {
546
- if (pagesMap[key] === pageName && key !== resourcePath) {
547
- emitError(`Current page [${resourcePath}] registers a conflict page path [${pageName}] with existed page [${key}], which is not allowed, please rename it!`)
548
- return callback()
549
- }
550
- }
551
- } else {
552
- const relative = path.relative(context, resourcePath)
553
- if (/^\./.test(relative)) {
554
- // 如果当前page不存在于context中,对其进行重命名
555
- pageName = toPosix(path.join(tarRoot, getPageName(resourcePath, ext)))
556
- emitWarning(`Current page [${resourcePath}] is not in current pages directory [${context}], the page path will be replaced with [${pageName}], use ?resolve to get the page path and navigate to it!`)
557
- } else {
558
- pageName = toPosix(path.join(tarRoot, /^(.*?)(\.[^.]*)?$/.exec(relative)[1]))
559
- // 如果当前page与已有page存在命名冲突,也进行重命名
560
- for (let key in pagesMap) {
561
- if (pagesMap[key] === pageName && key !== resourcePath) {
562
- const pageNameRaw = pageName
563
- pageName = toPosix(path.join(tarRoot, getPageName(resourcePath, ext)))
564
- emitWarning(`Current page [${resourcePath}] is registered with a conflict page path [${pageNameRaw}] which is already existed in system, the page path will be replaced with [${pageName}], use ?resolve to get the page path and navigate to it!`)
565
- break
566
- }
567
- }
568
- }
569
- }
570
- if (ext === '.js') {
571
- resource = '!!' + nativeLoaderPath + '!' + resource
572
- }
573
- // 如果之前已经创建了页面入口,直接return,目前暂时不支持多个分包复用同一个页面
574
- if (pagesMap[resourcePath]) {
575
- emitWarning(`Current page [${resourcePath}] which is imported from [${this.resourcePath}] has been registered in pagesMap already, it will be ignored, please check it and remove the redundant page declaration!`)
576
- return callback()
577
- }
578
- currentEntry.addChild(getEntryNode(resource, 'Page'))
579
- pagesMap[resourcePath] = pageName
580
- if (tarRoot && subPackagesCfg[tarRoot]) {
581
- resource = addQuery(resource, {
582
- packageRoot: tarRoot
583
- })
584
- subPackagesCfg[tarRoot].pages.push(toPosix(path.relative(tarRoot, pageName)))
585
- } else {
586
- // 确保首页
587
- if (queryObj.isFirst) {
588
- localPages.unshift(pageName)
589
- } else {
590
- localPages.push(pageName)
591
- }
592
- }
593
- addEntrySafely(resource, pageName, callback)
594
- })
394
+ async.each(subPackages, (subPackage, callback) => {
395
+ processSubPackage(subPackage, context, callback)
595
396
  }, callback)
596
397
  } else {
597
398
  callback()
@@ -630,15 +431,11 @@ module.exports = function (raw = '{}') {
630
431
 
631
432
  const processThemeLocation = (output) => {
632
433
  if (json.themeLocation && isUrlRequest(json.themeLocation)) {
633
- const themeRequest = '!!' + extractorPath + '?' +
634
- JSON.stringify({
635
- type: 'json',
636
- index: -1
637
- }) + '!' +
638
- themeLoaderPath + '?root = ' + options.root + '!' +
639
- addQuery(urlToRequest(json.themeLocation), { __component: true, isStatic: true })
640
-
641
- output += `json.themeLocation = require(${stringifyRequest(themeRequest)});\n`
434
+ const requestString = getRequestString('json', { src: urlToRequest(json.themeLocation) }, {
435
+ isTheme: true,
436
+ isStatic: true
437
+ })
438
+ output += `json.themeLocation = require(${requestString});\n`
642
439
  }
643
440
  return output
644
441
  }
@@ -655,75 +452,48 @@ module.exports = function (raw = '{}') {
655
452
 
656
453
  const processCustomTabBar = (tabBar, context, callback) => {
657
454
  if (tabBar && tabBar.custom) {
658
- processComponent('./custom-tab-bar/index', context, undefined, 'custom-tab-bar/index', callback)
455
+ processComponent('./custom-tab-bar/index', context, { outputPath: 'custom-tab-bar/index' }, callback)
659
456
  } else {
660
457
  callback()
661
458
  }
662
459
  }
663
460
 
664
- const addMiniToPluginModules = module => {
665
- if (mpx.miniToPluginModules) {
666
- mpx.miniToPluginModules.add(module)
667
- } else {
668
- mpx.miniToPluginModules = new Set([module])
669
- }
670
- }
671
-
672
- const processPluginGenericsImplementation = (genericsImplementation, tarRoot, context, callback) => {
673
- async.forEachOf(genericsImplementation, (genericComponents, name, callback) => {
674
- async.forEachOf(genericComponents, (genericComponentPath, name, callback) => {
675
- processComponent(genericComponentPath, context, (componentPath) => {
676
- if (useRelativePath === true) {
677
- componentPath = toPosix(path.relative(publicPath + tarRoot, componentPath))
678
- }
679
- genericComponents[name] = componentPath
680
- }, undefined, callback)
461
+ const processPluginGenericsImplementation = (genericsImplementation, context, tarRoot, callback) => {
462
+ const relativePath = useRelativePath ? publicPath + tarRoot : ''
463
+ async.eachOf(genericsImplementation, (genericComponents, name, callback) => {
464
+ async.eachOf(genericComponents, (genericComponentPath, name, callback) => {
465
+ processComponent(genericComponentPath, context, { tarRoot, relativePath }, (err, entry) => {
466
+ if (err) return callback(err)
467
+ genericComponents[name] = entry
468
+ })
681
469
  }, callback)
682
470
  }, callback)
683
471
  }
684
472
 
685
- const processPluginExport = (plugin, tarRoot, context, callback) => {
473
+ const processPluginExport = (plugin, context, tarRoot, callback) => {
686
474
  if (!plugin.export) {
687
475
  return callback()
688
476
  }
689
- let pluginExport = plugin.export
690
- if (resolveMode === 'native') {
691
- pluginExport = urlToRequest(pluginExport)
692
- }
693
- resolve(context, pluginExport, (err, resource, info) => {
477
+ processJsExport(plugin.export, context, tarRoot, (err, entry) => {
694
478
  if (err) return callback(err)
695
- const { resourcePath } = parseRequest(resource)
696
- // 获取 export 的模块名
697
- const relative = path.relative(context, resourcePath)
698
- const name = toPosix(/^(.*?)(\.[^.]*)?$/.exec(relative)[1])
699
- if (/^\./.test(name)) {
700
- return callback(new Error(`The miniprogram plugins' export path ${plugin.export} must be in the context ${context}!`))
701
- }
702
- plugin.export = name + '.js'
703
- addEntrySafely(resource, toPosix(tarRoot ? `${tarRoot}/${name}` : name), (err, module) => {
704
- if (err) return callback(err)
705
- addMiniToPluginModules(module)
706
- currentEntry.addChild(getEntryNode(resource, 'PluginExport', module))
707
- callback(err, module)
708
- })
479
+ plugin.export = entry
480
+ callback()
709
481
  })
710
482
  }
711
483
 
712
- /* 导出到插件 */
713
- const processPlugins = (plugins, srcRoot = '', tarRoot = '', context, callback) => {
714
- if (mpx.mode !== 'wx' || !plugins) return callback() // 目前只有微信支持导出到插件
715
- context = path.join(context, srcRoot)
716
- async.forEachOf(plugins, (plugin, name, callback) => {
484
+ const processPlugins = (plugins, context, tarRoot = '', callback) => {
485
+ if (mode !== 'wx' || !plugins) return callback() // 目前只有微信支持导出到插件
486
+ async.eachOf(plugins, (plugin, name, callback) => {
717
487
  async.parallel([
718
488
  (callback) => {
719
489
  if (plugin.genericsImplementation) {
720
- processPluginGenericsImplementation(plugin.genericsImplementation, tarRoot, context, callback)
490
+ processPluginGenericsImplementation(plugin.genericsImplementation, context, tarRoot, callback)
721
491
  } else {
722
492
  callback()
723
493
  }
724
494
  },
725
495
  (callback) => {
726
- processPluginExport(plugin, tarRoot, context, callback)
496
+ processPluginExport(plugin, context, tarRoot, callback)
727
497
  }
728
498
  ], (err) => {
729
499
  callback(err)
@@ -731,59 +501,30 @@ module.exports = function (raw = '{}') {
731
501
  }, callback)
732
502
  }
733
503
 
734
- // 串行处理,先处理主包代码,再处理分包代码,为了正确识别出分包中定义的组件属于主包还是分包
735
- let errors = []
736
- // 外部收集errors,确保整个series流程能够执行完
737
- async.series([
504
+ async.parallel([
738
505
  (callback) => {
739
- async.parallel([
740
- (callback) => {
741
- processPlugins(json.plugins, '', '', this.context, callback)
742
- },
743
- (callback) => {
744
- processPages(json.pages, '', '', this.context, callback)
745
- },
746
- (callback) => {
747
- processComponents(json.usingComponents, this.context, callback)
748
- },
749
- (callback) => {
750
- processWorkers(json.workers, this.context, callback)
751
- },
752
- (callback) => {
753
- processPackages(json.packages, this.context, callback)
754
- },
755
- (callback) => {
756
- processCustomTabBar(json.tabBar, this.context, callback)
757
- },
758
- (callback) => {
759
- processSubPackages(json.subPackages || json.subpackages, this.context, callback)
760
- }
761
- ], (err) => {
762
- if (err) {
763
- errors.push(err)
764
- }
765
- callback()
766
- })
506
+ processPlugins(json.plugins, this.context, '', callback)
767
507
  },
768
508
  (callback) => {
769
- if (mpx.appScriptPromise) {
770
- mpx.appScriptPromise.then(callback)
771
- } else {
772
- callback()
773
- }
509
+ processPages(json.pages, this.context, '', callback)
774
510
  },
775
511
  (callback) => {
776
- async.series(processSubPackagesQueue, (err) => {
777
- if (err) {
778
- errors.push(err)
779
- }
780
- // 处理完分包后重置currentPackageRoot以确保app中的资源输出到主包
781
- mpx.currentPackageRoot = ''
782
- callback()
783
- })
512
+ processComponents(json.usingComponents, this.context, callback)
513
+ },
514
+ (callback) => {
515
+ processWorkers(json.workers, this.context, callback)
516
+ },
517
+ (callback) => {
518
+ processPackages(json.packages, this.context, callback)
519
+ },
520
+ (callback) => {
521
+ processCustomTabBar(json.tabBar, this.context, callback)
522
+ },
523
+ (callback) => {
524
+ processSubPackages(json.subPackages || json.subpackages, this.context, callback)
784
525
  }
785
- ], () => {
786
- if (errors.length) return callback(errors[0])
526
+ ], (err) => {
527
+ if (err) return callback(err)
787
528
  delete json.packages
788
529
  delete json.subpackages
789
530
  delete json.subPackages
@@ -795,6 +536,7 @@ module.exports = function (raw = '{}') {
795
536
  json.subPackages.push(subPackagesCfg[root])
796
537
  }
797
538
  const processOutput = (output) => {
539
+ output = processDynamicEntry(output)
798
540
  output = processTabBar(output)
799
541
  output = processOptionMenu(output)
800
542
  output = processThemeLocation(output)
@@ -803,16 +545,16 @@ module.exports = function (raw = '{}') {
803
545
  callback(null, processOutput)
804
546
  })
805
547
  } else {
548
+ // page.json或component.json
806
549
  const processGenerics = (generics, context, callback) => {
807
550
  if (generics) {
808
- async.forEachOf(generics, (generic, name, callback) => {
551
+ async.eachOf(generics, (generic, name, callback) => {
809
552
  if (generic.default) {
810
- processComponent(generic.default, context, (componentPath) => {
811
- if (useRelativePath === true) {
812
- componentPath = toPosix(path.relative(path.dirname(currentPath), componentPath))
813
- }
814
- generic.default = componentPath
815
- }, undefined, callback)
553
+ processComponent(generic.default, context, { relativePath }, (err, entry) => {
554
+ if (err) return callback(err)
555
+ generic.default = entry
556
+ callback()
557
+ })
816
558
  } else {
817
559
  callback()
818
560
  }
@@ -821,7 +563,6 @@ module.exports = function (raw = '{}') {
821
563
  callback()
822
564
  }
823
565
  }
824
- // page.json或component.json
825
566
  async.parallel([
826
567
  (callback) => {
827
568
  processComponents(json.usingComponents, this.context, callback)
@@ -830,7 +571,7 @@ module.exports = function (raw = '{}') {
830
571
  processGenerics(json.componentGenerics, this.context, callback)
831
572
  }
832
573
  ], (err) => {
833
- callback(err)
574
+ callback(err, processDynamicEntry)
834
575
  })
835
576
  }
836
577
  }