主流跨平台方案

ionic-native/taro/uni api/

Babel 简单介绍

Uni API 基础介绍

Uni API 分端构建方案

Uni API 文档中《分端构建》介绍。

uni-api设计学习.drawio.png


  1. /* eslint-disable @typescript-eslint/no-var-requires */
  2. /* eslint-disable no-param-reassign */
  3. const { API_NAME_MAP, MAIN_PKG_MAP, PATH_NAME_MAP } = require('./config');
  4. const fs = require('fs-extra');
  5. const path = require('path');
  6. const root = process.cwd();
  7. module.exports = function(babel) {
  8. const { types: t } = babel;
  9. return {
  10. visitor: {
  11. ImportDeclaration: {
  12. enter(_path, state) {
  13. const { node } = _path;
  14. const importValue = node.source && node.source.value;
  15. // 替换匹配到的universal路径
  16. if (API_NAME_MAP[importValue]) {
  17. if (fs.pathExistsSync(path.resolve(root, 'node_modules', importValue, 'lib'))) {
  18. // 兼容旧版本构建
  19. if (API_NAME_MAP[importValue].hasChildApi) {
  20. const newImports = node.specifiers.map(item => {
  21. if (item.type === 'ImportSpecifier') {
  22. // import { a, b } from '@uni/xxx'; =>
  23. // import a from '@uni/xxx/lib/wechat-miniprogram/a';
  24. // import b from '@uni/xxx/lib/wechat-miniprogram/b';
  25. return t.importDeclaration([t.importDefaultSpecifier(item.local)], t.stringLiteral(`${importValue}/lib/${PATH_NAME_MAP[state.opts.target]}/${item.local.name}.js`));
  26. } else if (item.type === 'ImportDefaultSpecifier') {
  27. // import A from '@uni/xxx'; =>
  28. // import A from '@uni/xxx/lib/wechat-miniprogram';
  29. return t.importDeclaration([t.importDefaultSpecifier(item.local)], t.stringLiteral(`${importValue}/lib/${PATH_NAME_MAP[state.opts.target]}/index.js`));
  30. } else {
  31. return item;
  32. }
  33. });
  34. _path.replaceWithMultiple(newImports);
  35. } else {
  36. node.source.value = importValue + `/lib/${PATH_NAME_MAP[state.opts.target]}/index.js`;
  37. }
  38. } else {
  39. node.source.value = importValue + `/${PATH_NAME_MAP[state.opts.target]}/index.js`;
  40. }
  41. } else if (importValue === '@uni/apis') {
  42. if (fs.pathExistsSync(path.resolve(root, 'node_modules', importValue, 'lib'))) {
  43. const newImports = node.specifiers.map(item => {
  44. if (item.type === 'ImportSpecifier' && MAIN_PKG_MAP[item.local.name]) {
  45. // import { a, b } from '@uni/apis'; =>
  46. // import a from '@uni/apis/lib/packages/a/wechat-miniprogram';
  47. // import b from '@uni/apis/lib/packages/b/wechat-miniprogram';
  48. return t.importDeclaration([t.importDefaultSpecifier(item.local)], t.stringLiteral(`${importValue}/lib/packages/${MAIN_PKG_MAP[item.local.name]}/src/${PATH_NAME_MAP[state.opts.target]}/index.js`));
  49. } else if (item.type === 'ImportDefaultSpecifier') {
  50. return t.importDeclaration([t.importDefaultSpecifier(item.local)], t.stringLiteral(`${importValue}/lib/main/${PATH_NAME_MAP[state.opts.target]}/index.js`));
  51. } else {
  52. return item;
  53. }
  54. });
  55. _path.replaceWithMultiple(newImports);
  56. } else {
  57. node.source.value = importValue + `/${PATH_NAME_MAP[state.opts.target]}/index.js`;
  58. }
  59. }
  60. },
  61. },
  62. },
  63. };
  64. };
  1. const API_NAME_MAP = {
  2. '@uni/application': {
  3. hasChildApi: true,
  4. },
  5. '@uni/canvas': {
  6. hasChildApi: true,
  7. },
  8. '@uni/accelerometer': {
  9. hasChildApi: true,
  10. },
  11. '@uni/clipboard': {
  12. hasChildApi: true,
  13. },
  14. '@uni/system-info': {
  15. hasChildApi: true,
  16. },
  17. '@uni/file': {
  18. hasChildApi: true,
  19. },
  20. '@uni/action-sheet': {
  21. hasChildApi: false,
  22. },
  23. '@uni/alert': {
  24. hasChildApi: false,
  25. },
  26. '@uni/toast': {
  27. hasChildApi: true,
  28. },
  29. '@uni/loading': {
  30. hasChildApi: true,
  31. },
  32. '@uni/element': {
  33. hasChildApi: true,
  34. },
  35. '@uni/intersection-observer': {
  36. hasChildApi: true,
  37. },
  38. '@uni/confirm': {
  39. hasChildApi: false,
  40. },
  41. '@uni/location': {
  42. hasChildApi: true,
  43. },
  44. '@uni/image': {
  45. hasChildApi: true,
  46. },
  47. '@uni/navigate': {
  48. hasChildApi: true,
  49. },
  50. '@uni/request': {
  51. hasChildApi: false,
  52. },
  53. '@uni/storage': {
  54. hasChildApi: true,
  55. },
  56. '@uni/pull-down-refresh': {
  57. hasChildApi: true,
  58. },
  59. '@uni/recorder': {
  60. hasChildApi: false,
  61. },
  62. '@uni/video': {
  63. hasChildApi: true,
  64. },
  65. '@uni/scan': {
  66. hasChildApi: false,
  67. },
  68. '@uni/navigation-bar': {
  69. hasChildApi: true,
  70. },
  71. '@uni/animation': {
  72. hasChildApi: true,
  73. },
  74. '@uni/audio': {
  75. hasChildApi: true,
  76. },
  77. '@uni/share': {
  78. hasChildApi: true,
  79. },
  80. '@uni/subscribe-message': {
  81. hasChildApi: false,
  82. },
  83. '@uni/authorize': {
  84. hasChildApi: false,
  85. },
  86. '@uni/page-scroll-to': {
  87. hasChildApi: false,
  88. },
  89. '@uni/make-phone-call': {
  90. hasChildApi: false,
  91. },
  92. '@uni/tab-bar': {
  93. hasChildApi: true,
  94. },
  95. };
  96. const MAIN_PKG_MAP = {
  97. storage: 'storage',
  98. request: 'network/request',
  99. navigate: 'navigate',
  100. image: 'media/image',
  101. video: 'media/video',
  102. recorder: 'media/recorder',
  103. location: 'location',
  104. confirm: 'interactive/confirm',
  105. intersectionObserver: 'interactive/intersectionObserver',
  106. element: 'interactive/element',
  107. loading: 'interactive/loading',
  108. toast: 'interactive/toast',
  109. alert: 'interactive/alert',
  110. actionSheet: 'interactive/actionSheet',
  111. pullDownRefresh: 'interactive/pullDownRefresh',
  112. file: 'file',
  113. systemInfo: 'device/systemInfo',
  114. clipboard: 'device/clipboard',
  115. accelerometer: 'device/accelerometer',
  116. scan: 'device/scan',
  117. canvas: 'canvas',
  118. animation: 'interactive/animation',
  119. navigationBar: 'interactive/navigationBar',
  120. application: 'application',
  121. makePhoneCall: 'device/makePhoneCall',
  122. pageScrollTo: 'interactive/pageScrollTo',
  123. authorize: 'open/authorize',
  124. subscribeMessage: 'open/subscribeMessage',
  125. share: 'share',
  126. audio: 'media/audio',
  127. tabBar: 'interactive/tabBar'
  128. }
  129. const PATH_NAME_MAP = {
  130. 'web': 'web',
  131. 'wechat-miniprogram': 'wechat-miniprogram',
  132. 'miniapp': 'ali-miniapp',
  133. 'bytedance-microapp': 'bytedance-microapp',
  134. 'baidu-smartprogram': 'baidu-smartprogram',
  135. 'kuaishou-miniprogram': 'kuaishou-miniprogram'
  136. };
  137. exports.PATH_NAME_MAP = PATH_NAME_MAP;
  138. exports.MAIN_PKG_MAP = MAIN_PKG_MAP;
  139. exports.API_NAME_MAP = API_NAME_MAP;