[
  {
    "path": ".editorconfig",
    "content": "root = true\n\n[*]\ncharset = utf-8\nindent_style = space\nindent_size = 2\nend_of_line = lf\ninsert_final_newline = true\ntrim_trailing_whitespace = true\n"
  },
  {
    "path": ".github/workflows/ci.yml",
    "content": "name: GitHub Actions Build and Deploy Demo\non:\n  push:\n    branches:\n      - master\njobs:\n  build-and-deploy:\n    runs-on: ubuntu-latest\n    steps:\n    - name: Checkout\n      uses: actions/checkout@v1\n\n    - name: Install and Build\n      run: |\n        cd examples\n        yarn\n        yarn install:all\n        yarn build:all\n\n    - name: Deploy\n      uses: JamesIves/github-pages-deploy-action@releases/v3\n      with:\n        ACCESS_TOKEN: ${{ secrets.ACCESS_TOKEN }}\n        BRANCH: gh-pages\n        FOLDER: examples/master/dist\n        CLEAN: true\n"
  },
  {
    "path": ".gitignore",
    "content": "# Logs\nlogs\n*.log\nnpm-debug.log*\nyarn-debug.log*\nyarn-error.log*\nlerna-debug.log*\n\n# Diagnostic reports (https://nodejs.org/api/report.html)\nreport.[0-9]*.[0-9]*.[0-9]*.[0-9]*.json\n\n# Runtime data\npids\n*.pid\n*.seed\n*.pid.lock\n\n# Directory for instrumented libs generated by jscoverage/JSCover\nlib-cov\n\n# Coverage directory used by tools like istanbul\ncoverage\n*.lcov\n\n# nyc test coverage\n.nyc_output\n\n# Grunt intermediate storage (https://gruntjs.com/creating-plugins#storing-task-files)\n.grunt\n\n# Bower dependency directory (https://bower.io/)\nbower_components\n\n# node-waf configuration\n.lock-wscript\n\n# Compiled binary addons (https://nodejs.org/api/addons.html)\nbuild/Release\n\n# Dependency directories\nnode_modules/\njspm_packages/\n\n# TypeScript v1 declaration files\ntypings/\n\n# TypeScript cache\n*.tsbuildinfo\n\n# Optional npm cache directory\n.npm\n\n# Optional eslint cache\n.eslintcache\n\n# Microbundle cache\n.rpt2_cache/\n.rts2_cache_cjs/\n.rts2_cache_es/\n.rts2_cache_umd/\n\n# Optional REPL history\n.node_repl_history\n\n# Output of 'npm pack'\n*.tgz\n\n# Yarn Integrity file\n.yarn-integrity\n\n# dotenv environment variables file\n.env\n.env.test\n\n# parcel-bundler cache (https://parceljs.org/)\n.cache\n\n# Next.js build output\n.next\n\n# Nuxt.js build / generate output\n.nuxt\ndist\n\n# Gatsby files\n.cache/\n# Comment in the public line in if your project uses Gatsby and *not* Next.js\n# https://nextjs.org/blog/next-9-1#public-directory-support\n# public\n\n# vuepress build output\n.vuepress/dist\n\n# Serverless directories\n.serverless/\n\n# FuseBox cache\n.fusebox/\n\n# DynamoDB Local files\n.dynamodb/\n\n# TernJS port file\n.tern-port\n\n# Lock file\nyarn.lock\npackage-lock.json\n"
  },
  {
    "path": "LICENSE",
    "content": "MIT License\n\nCopyright (c) 2020 徒言\n\nPermission is hereby granted, free of charge, to any person obtaining a copy\nof this software and associated documentation files (the \"Software\"), to deal\nin the Software without restriction, including without limitation the rights\nto use, copy, modify, merge, publish, distribute, sublicense, and/or sell\ncopies of the Software, and to permit persons to whom the Software is\nfurnished to do so, subject to the following conditions:\n\nThe above copyright notice and this permission notice shall be included in all\ncopies or substantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\nIMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\nFITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\nAUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\nLIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\nOUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\nSOFTWARE.\n"
  },
  {
    "path": "README.md",
    "content": "## vue-cli-plugin-qiankun\n\n> qiankun plugin for vue-cli\n\n[![npm version](https://img.shields.io/npm/v/vue-cli-plugin-qiankun.svg?style=flat-square)](https://www.npmjs.com/package/vue-cli-plugin-qiankun) [![npm downloads](https://img.shields.io/npm/dt/vue-cli-plugin-qiankun.svg?style=flat-square)](https://www.npmjs.com/package/vue-cli-plugin-qiankun)\n\n### 使用步骤 (Use setup)\n\n1. 创建主应用 (Create master project)\n\n``` sh\n$ vue create master\n$ cd master\n$ vue add vue-cli-plugin-qiankun --type master\n```\n\n2. 创建子应用 (Create slave project)\n\n``` sh\n$ vue create foo-app\n$ cd foo-app\n$ vue add vue-cli-plugin-qiankun --type slave --port 8081\n```\n\n3. 配置主应用 (Config master project)\n\n> master/src/App.vue\n\n``` vue\n<script>\nexport default {\n  name: 'master',\n  data () {\n    return {\n      // ...\n      apps: [\n        { name: 'foo-app', entry: '//localhost:8081', container: '#appContainer', activeRule: '/foo-app' }\n      ]\n    }\n  },\n  // ...\n  methods: {\n    // ...\n    initQiankun () {\n      // ...\n      setDefaultMountApp('/foo-app')\n      // ...\n    }\n  }\n}\n</script>\n```\n\n4. 运行各项目 (Run each project)\n\n``` sh\n$ cd master\n$ yarn serve\n```\n\n``` sh\n$ cd foo-app\n$ yarn serve\n```\n\n### 示例 (Examples)\n\n> [DEMO](https://f-loat.github.io/vue-cli-plugin-qiankun)\n\n``` sh\n$ cd examples\n$ yarn\n$ yarn install:all\n$ yarn serve:all\n```\n\n### 功能 (Features)\n\n- 修改项目文件引入 qiankun 框架\n\n- 注入 qiankun 框架要求的构建配置\n\n- 自动配置 `publicPath` 处理资源路径\n\n### 致谢 (Acknowledgements)\n\n- [vue-cli](https://github.com/vuejs/vue-cli) Standard Tooling for Vue.js Development.\n\n- [qiankun](https://github.com/umijs/qiankun) Blazing fast, simple and completed solution for micro frontends.\n\n- [single-spa](https://github.com/CanopyTax/single-spa) What an awesome meta-framework for micro-frontends!\n"
  },
  {
    "path": "examples/README.md",
    "content": "## Examples\n\n``` sh\n$ yarn\n$ yarn install:all\n$ yarn serve:all\n```\n"
  },
  {
    "path": "examples/bar-app/.browserslistrc",
    "content": "> 1%\nlast 2 versions\n"
  },
  {
    "path": "examples/bar-app/.editorconfig",
    "content": "[*.{js,jsx,ts,tsx,vue}]\nindent_style = space\nindent_size = 2\ntrim_trailing_whitespace = true\ninsert_final_newline = true\n"
  },
  {
    "path": "examples/bar-app/.eslintrc.js",
    "content": "module.exports = {\n  root: true,\n  env: {\n    node: true\n  },\n  'extends': [\n    'plugin:vue/essential',\n    '@vue/standard'\n  ],\n  rules: {\n    'no-console': process.env.NODE_ENV === 'production' ? 'error' : 'off',\n    'no-debugger': process.env.NODE_ENV === 'production' ? 'error' : 'off'\n  },\n  parserOptions: {\n    parser: 'babel-eslint'\n  }\n}\n"
  },
  {
    "path": "examples/bar-app/.gitignore",
    "content": ".DS_Store\nnode_modules\n/dist\n\n# local env files\n.env.local\n.env.*.local\n\n# Log files\nnpm-debug.log*\nyarn-debug.log*\nyarn-error.log*\n\n# Editor directories and files\n.idea\n.vscode\n*.suo\n*.ntvs*\n*.njsproj\n*.sln\n*.sw?\n"
  },
  {
    "path": "examples/bar-app/README.md",
    "content": "# bar-app\n\n## Project setup\n```\nyarn install\n```\n\n### Compiles and hot-reloads for development\n```\nyarn run serve\n```\n\n### Compiles and minifies for production\n```\nyarn run build\n```\n\n### Run your tests\n```\nyarn run test\n```\n\n### Lints and fixes files\n```\nyarn run lint\n```\n\n### Customize configuration\nSee [Configuration Reference](https://cli.vuejs.org/config/).\n"
  },
  {
    "path": "examples/bar-app/babel.config.js",
    "content": "module.exports = {\n  presets: [\n    '@vue/cli-plugin-babel/preset'\n  ]\n}\n"
  },
  {
    "path": "examples/bar-app/package.json",
    "content": "{\n  \"name\": \"bar-app\",\n  \"version\": \"0.1.0\",\n  \"private\": true,\n  \"scripts\": {\n    \"serve\": \"vue-cli-service serve --port 8082\",\n    \"build\": \"vue-cli-service build\",\n    \"postbuild\": \"cp-cli dist ../master/dist/bar-app\",\n    \"lint\": \"vue-cli-service lint\"\n  },\n  \"dependencies\": {\n    \"core-js\": \"^3.4.4\",\n    \"vue\": \"^2.6.10\"\n  },\n  \"devDependencies\": {\n    \"@vue/cli-plugin-babel\": \"^4.1.0\",\n    \"@vue/cli-plugin-eslint\": \"^4.1.0\",\n    \"@vue/cli-service\": \"^4.1.0\",\n    \"@vue/eslint-config-standard\": \"^4.0.0\",\n    \"babel-eslint\": \"^10.0.3\",\n    \"cp-cli\": \"^2.0.0\",\n    \"eslint\": \"^5.16.0\",\n    \"eslint-plugin-vue\": \"^5.0.0\",\n    \"vue-cli-plugin-qiankun\": \"../../\",\n    \"vue-template-compiler\": \"^2.6.10\"\n  }\n}\n"
  },
  {
    "path": "examples/bar-app/public/index.html",
    "content": "<!DOCTYPE html>\n<html lang=\"en\">\n  <head>\n    <meta charset=\"utf-8\">\n    <meta http-equiv=\"X-UA-Compatible\" content=\"IE=edge\">\n    <meta name=\"viewport\" content=\"width=device-width,initial-scale=1.0\">\n    <link rel=\"icon\" href=\"<%= BASE_URL %>favicon.ico\">\n    <title>bar-app</title>\n  </head>\n  <body>\n    <noscript>\n      <strong>We're sorry but bar-app doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>\n    </noscript>\n    <div id=\"app\"></div>\n    <!-- built files will be auto injected -->\n  </body>\n</html>\n"
  },
  {
    "path": "examples/bar-app/src/App.vue",
    "content": "<template>\n  <div id=\"app\">\n    <img alt=\"Vue logo\" src=\"./assets/logo.png\">\n    <HelloWorld msg=\"Welcome to Your Bar Vue.js App\"/>\n  </div>\n</template>\n\n<script>\nimport HelloWorld from './components/HelloWorld.vue'\n\nexport default {\n  name: 'app',\n  components: {\n    HelloWorld\n  }\n}\n</script>\n\n<style>\n#app {\n  font-family: 'Avenir', Helvetica, Arial, sans-serif;\n  -webkit-font-smoothing: antialiased;\n  -moz-osx-font-smoothing: grayscale;\n  text-align: center;\n  color: #2c3e50;\n  margin-top: 60px;\n}\n</style>\n"
  },
  {
    "path": "examples/bar-app/src/components/HelloWorld.vue",
    "content": "<template>\n  <div class=\"hello\">\n    <h1>{{ msg }}</h1>\n    <p>\n      For a guide and recipes on how to configure / customize this project,<br>\n      check out the\n      <a href=\"https://cli.vuejs.org\" target=\"_blank\" rel=\"noopener\">vue-cli documentation</a>.\n    </p>\n    <h3>Installed CLI Plugins</h3>\n    <ul>\n      <li><a href=\"https://github.com/vuejs/vue-cli/tree/dev/packages/%40vue/cli-plugin-babel\" target=\"_blank\" rel=\"noopener\">babel</a></li>\n      <li><a href=\"https://github.com/vuejs/vue-cli/tree/dev/packages/%40vue/cli-plugin-eslint\" target=\"_blank\" rel=\"noopener\">eslint</a></li>\n    </ul>\n    <h3>Essential Links</h3>\n    <ul>\n      <li><a href=\"https://vuejs.org\" target=\"_blank\" rel=\"noopener\">Core Docs</a></li>\n      <li><a href=\"https://forum.vuejs.org\" target=\"_blank\" rel=\"noopener\">Forum</a></li>\n      <li><a href=\"https://chat.vuejs.org\" target=\"_blank\" rel=\"noopener\">Community Chat</a></li>\n      <li><a href=\"https://twitter.com/vuejs\" target=\"_blank\" rel=\"noopener\">Twitter</a></li>\n      <li><a href=\"https://news.vuejs.org\" target=\"_blank\" rel=\"noopener\">News</a></li>\n    </ul>\n    <h3>Ecosystem</h3>\n    <ul>\n      <li><a href=\"https://router.vuejs.org\" target=\"_blank\" rel=\"noopener\">vue-router</a></li>\n      <li><a href=\"https://vuex.vuejs.org\" target=\"_blank\" rel=\"noopener\">vuex</a></li>\n      <li><a href=\"https://github.com/vuejs/vue-devtools#vue-devtools\" target=\"_blank\" rel=\"noopener\">vue-devtools</a></li>\n      <li><a href=\"https://vue-loader.vuejs.org\" target=\"_blank\" rel=\"noopener\">vue-loader</a></li>\n      <li><a href=\"https://github.com/vuejs/awesome-vue\" target=\"_blank\" rel=\"noopener\">awesome-vue</a></li>\n    </ul>\n  </div>\n</template>\n\n<script>\nexport default {\n  name: 'HelloWorld',\n  props: {\n    msg: String\n  }\n}\n</script>\n\n<!-- Add \"scoped\" attribute to limit CSS to this component only -->\n<style scoped>\nh3 {\n  margin: 40px 0 0;\n}\nul {\n  list-style-type: none;\n  padding: 0;\n}\nli {\n  display: inline-block;\n  margin: 0 10px;\n}\na {\n  color: #42b983;\n}\n</style>\n"
  },
  {
    "path": "examples/bar-app/src/main.js",
    "content": "import Vue from 'vue'\nimport App from './App.vue'\n\nVue.config.productionTip = false\n\nlet instance = null\n\nfunction render () {\n  instance = new Vue({\n    render: h => h(App)\n  }).$mount('#app')\n}\n\nif (!window.__POWERED_BY_QIANKUN__) {\n  render()\n}\n\nexport async function bootstrap () {\n  // eslint-disable-next-line no-console\n  console.log('vue app bootstraped')\n}\n\nexport async function mount (props) {\n  // eslint-disable-next-line no-console\n  console.log('props from main framework', props)\n  render()\n}\n\nexport async function unmount () {\n  instance.$destroy()\n  instance = null\n}\n"
  },
  {
    "path": "examples/bar-app/vue.config.js",
    "content": "module.exports = {\n  productionSourceMap: false,\n  indexPath: process.env.NODE_ENV === 'production'\n    ? 'source.html'\n    : 'index.html',\n  publicPath: process.env.VUE_APP_BASE_PATH\n}\n"
  },
  {
    "path": "examples/foo-app/.browserslistrc",
    "content": "> 1%\nlast 2 versions\n"
  },
  {
    "path": "examples/foo-app/.editorconfig",
    "content": "[*.{js,jsx,ts,tsx,vue}]\nindent_style = space\nindent_size = 2\ntrim_trailing_whitespace = true\ninsert_final_newline = true\n"
  },
  {
    "path": "examples/foo-app/.eslintrc.js",
    "content": "module.exports = {\n  root: true,\n  env: {\n    node: true\n  },\n  'extends': [\n    'plugin:vue/essential',\n    '@vue/standard'\n  ],\n  rules: {\n    'no-console': process.env.NODE_ENV === 'production' ? 'error' : 'off',\n    'no-debugger': process.env.NODE_ENV === 'production' ? 'error' : 'off'\n  },\n  parserOptions: {\n    parser: 'babel-eslint'\n  }\n}\n"
  },
  {
    "path": "examples/foo-app/.gitignore",
    "content": ".DS_Store\nnode_modules\n/dist\n\n# local env files\n.env.local\n.env.*.local\n\n# Log files\nnpm-debug.log*\nyarn-debug.log*\nyarn-error.log*\n\n# Editor directories and files\n.idea\n.vscode\n*.suo\n*.ntvs*\n*.njsproj\n*.sln\n*.sw?\n"
  },
  {
    "path": "examples/foo-app/README.md",
    "content": "# foo-app\n\n## Project setup\n```\nyarn install\n```\n\n### Compiles and hot-reloads for development\n```\nyarn run serve\n```\n\n### Compiles and minifies for production\n```\nyarn run build\n```\n\n### Run your tests\n```\nyarn run test\n```\n\n### Lints and fixes files\n```\nyarn run lint\n```\n\n### Customize configuration\nSee [Configuration Reference](https://cli.vuejs.org/config/).\n"
  },
  {
    "path": "examples/foo-app/babel.config.js",
    "content": "module.exports = {\n  presets: [\n    '@vue/cli-plugin-babel/preset'\n  ]\n}\n"
  },
  {
    "path": "examples/foo-app/package.json",
    "content": "{\n  \"name\": \"foo-app\",\n  \"version\": \"0.1.0\",\n  \"private\": true,\n  \"scripts\": {\n    \"serve\": \"vue-cli-service serve --port 8081\",\n    \"build\": \"vue-cli-service build\",\n    \"postbuild\": \"cp-cli dist ../master/dist/foo-app\",\n    \"lint\": \"vue-cli-service lint\"\n  },\n  \"dependencies\": {\n    \"core-js\": \"^3.4.4\",\n    \"vue\": \"^2.6.10\",\n    \"vue-router\": \"^3.1.3\"\n  },\n  \"devDependencies\": {\n    \"@vue/cli-plugin-babel\": \"^4.1.0\",\n    \"@vue/cli-plugin-eslint\": \"^4.1.0\",\n    \"@vue/cli-service\": \"^4.1.0\",\n    \"@vue/eslint-config-standard\": \"^4.0.0\",\n    \"babel-eslint\": \"^10.0.3\",\n    \"cp-cli\": \"^2.0.0\",\n    \"eslint\": \"^5.16.0\",\n    \"eslint-plugin-vue\": \"^5.0.0\",\n    \"vue-cli-plugin-qiankun\": \"../../\",\n    \"vue-template-compiler\": \"^2.6.10\"\n  }\n}\n"
  },
  {
    "path": "examples/foo-app/public/index.html",
    "content": "<!DOCTYPE html>\n<html lang=\"en\">\n  <head>\n    <meta charset=\"utf-8\">\n    <meta http-equiv=\"X-UA-Compatible\" content=\"IE=edge\">\n    <meta name=\"viewport\" content=\"width=device-width,initial-scale=1.0\">\n    <link rel=\"icon\" href=\"<%= BASE_URL %>favicon.ico\">\n    <title>foo-app</title>\n  </head>\n  <body>\n    <noscript>\n      <strong>We're sorry but foo-app doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>\n    </noscript>\n    <div id=\"app\"></div>\n    <!-- built files will be auto injected -->\n  </body>\n</html>\n"
  },
  {
    "path": "examples/foo-app/src/App.vue",
    "content": "<template>\n  <div id=\"app\">\n    <div id=\"nav\">\n      <router-link to=\"/\">Home</router-link> |\n      <router-link to=\"/about\">About</router-link>\n    </div>\n    <router-view/>\n  </div>\n</template>\n\n<style>\n#app {\n  font-family: 'Avenir', Helvetica, Arial, sans-serif;\n  -webkit-font-smoothing: antialiased;\n  -moz-osx-font-smoothing: grayscale;\n  text-align: center;\n  color: #2c3e50;\n}\n\n#nav {\n  padding: 30px;\n}\n\n#nav a {\n  font-weight: bold;\n  color: #2c3e50;\n}\n\n#nav a.router-link-exact-active {\n  color: #42b983;\n}\n</style>\n"
  },
  {
    "path": "examples/foo-app/src/components/HelloWorld.vue",
    "content": "<template>\n  <div class=\"hello\">\n    <h1>{{ msg }}</h1>\n    <p>\n      For a guide and recipes on how to configure / customize this project,<br>\n      check out the\n      <a href=\"https://cli.vuejs.org\" target=\"_blank\" rel=\"noopener\">vue-cli documentation</a>.\n    </p>\n    <h3>Installed CLI Plugins</h3>\n    <ul>\n      <li><a href=\"https://github.com/vuejs/vue-cli/tree/dev/packages/%40vue/cli-plugin-babel\" target=\"_blank\" rel=\"noopener\">babel</a></li>\n      <li><a href=\"https://github.com/vuejs/vue-cli/tree/dev/packages/%40vue/cli-plugin-eslint\" target=\"_blank\" rel=\"noopener\">eslint</a></li>\n    </ul>\n    <h3>Essential Links</h3>\n    <ul>\n      <li><a href=\"https://vuejs.org\" target=\"_blank\" rel=\"noopener\">Core Docs</a></li>\n      <li><a href=\"https://forum.vuejs.org\" target=\"_blank\" rel=\"noopener\">Forum</a></li>\n      <li><a href=\"https://chat.vuejs.org\" target=\"_blank\" rel=\"noopener\">Community Chat</a></li>\n      <li><a href=\"https://twitter.com/vuejs\" target=\"_blank\" rel=\"noopener\">Twitter</a></li>\n      <li><a href=\"https://news.vuejs.org\" target=\"_blank\" rel=\"noopener\">News</a></li>\n    </ul>\n    <h3>Ecosystem</h3>\n    <ul>\n      <li><a href=\"https://router.vuejs.org\" target=\"_blank\" rel=\"noopener\">vue-router</a></li>\n      <li><a href=\"https://vuex.vuejs.org\" target=\"_blank\" rel=\"noopener\">vuex</a></li>\n      <li><a href=\"https://github.com/vuejs/vue-devtools#vue-devtools\" target=\"_blank\" rel=\"noopener\">vue-devtools</a></li>\n      <li><a href=\"https://vue-loader.vuejs.org\" target=\"_blank\" rel=\"noopener\">vue-loader</a></li>\n      <li><a href=\"https://github.com/vuejs/awesome-vue\" target=\"_blank\" rel=\"noopener\">awesome-vue</a></li>\n    </ul>\n  </div>\n</template>\n\n<script>\nexport default {\n  name: 'HelloWorld',\n  props: {\n    msg: String\n  }\n}\n</script>\n\n<!-- Add \"scoped\" attribute to limit CSS to this component only -->\n<style scoped>\nh3 {\n  margin: 40px 0 0;\n}\nul {\n  list-style-type: none;\n  padding: 0;\n}\nli {\n  display: inline-block;\n  margin: 0 10px;\n}\na {\n  color: #42b983;\n}\n</style>\n"
  },
  {
    "path": "examples/foo-app/src/main.js",
    "content": "import Vue from 'vue'\nimport App from './App.vue'\nimport router from './router'\n\nVue.config.productionTip = false\n\nlet instance = null\n\nfunction render () {\n  instance = new Vue({\n    router,\n    render: h => h(App)\n  }).$mount('#app')\n}\n\nif (!window.__POWERED_BY_QIANKUN__) {\n  render()\n}\n\nexport async function bootstrap () {\n  // eslint-disable-next-line no-console\n  console.log('vue app bootstraped')\n}\n\nexport async function mount (props) {\n  // eslint-disable-next-line no-console\n  console.log('props from main framework', props)\n  render()\n}\n\nexport async function unmount () {\n  instance.$destroy()\n  instance = null\n}\n"
  },
  {
    "path": "examples/foo-app/src/router/index.js",
    "content": "import Vue from 'vue'\nimport VueRouter from 'vue-router'\nimport Home from '../views/Home.vue'\n\nVue.use(VueRouter)\n\nconst routes = [\n  {\n    path: '/',\n    name: 'home',\n    component: Home\n  },\n  {\n    path: '/about',\n    name: 'about',\n    // route level code-splitting\n    // this generates a separate chunk (about.[hash].js) for this route\n    // which is lazy-loaded when the route is visited.\n    component: () => import(/* webpackChunkName: \"about\" */ '../views/About.vue')\n  }\n]\n\nconst router = new VueRouter({\n  mode: 'history',\n  base: window.__POWERED_BY_QIANKUN__\n    ? process.env.VUE_APP_BASE_PATH || '/foo-app/'\n    : '/',\n  routes\n})\n\nexport default router\n"
  },
  {
    "path": "examples/foo-app/src/views/About.vue",
    "content": "<template>\n  <div class=\"about\">\n    <h1>This is an about page</h1>\n  </div>\n</template>\n"
  },
  {
    "path": "examples/foo-app/src/views/Home.vue",
    "content": "<template>\n  <div class=\"home\">\n    <img alt=\"Vue logo\" src=\"../assets/logo.png\">\n    <HelloWorld msg=\"Welcome to Your Foo Vue.js App\"/>\n  </div>\n</template>\n\n<script>\n// @ is an alias to /src\nimport HelloWorld from '@/components/HelloWorld.vue'\n\nexport default {\n  name: 'home',\n  components: {\n    HelloWorld\n  }\n}\n</script>\n"
  },
  {
    "path": "examples/foo-app/vue.config.js",
    "content": "module.exports = {\n  productionSourceMap: false,\n  indexPath: process.env.NODE_ENV === 'production'\n    ? 'source.html'\n    : 'index.html',\n  publicPath: process.env.VUE_APP_BASE_PATH\n}\n"
  },
  {
    "path": "examples/master/.browserslistrc",
    "content": "> 1%\nlast 2 versions\n"
  },
  {
    "path": "examples/master/.editorconfig",
    "content": "[*.{js,jsx,ts,tsx,vue}]\nindent_style = space\nindent_size = 2\ntrim_trailing_whitespace = true\ninsert_final_newline = true\n"
  },
  {
    "path": "examples/master/.eslintrc.js",
    "content": "module.exports = {\n  root: true,\n  env: {\n    node: true\n  },\n  'extends': [\n    'plugin:vue/essential',\n    '@vue/standard'\n  ],\n  rules: {\n    'no-console': process.env.NODE_ENV === 'production' ? 'error' : 'off',\n    'no-debugger': process.env.NODE_ENV === 'production' ? 'error' : 'off'\n  },\n  parserOptions: {\n    parser: 'babel-eslint'\n  }\n}\n"
  },
  {
    "path": "examples/master/.gitignore",
    "content": ".DS_Store\nnode_modules\n/dist\n\n# local env files\n.env.local\n.env.*.local\n\n# Log files\nnpm-debug.log*\nyarn-debug.log*\nyarn-error.log*\n\n# Editor directories and files\n.idea\n.vscode\n*.suo\n*.ntvs*\n*.njsproj\n*.sln\n*.sw?\n"
  },
  {
    "path": "examples/master/README.md",
    "content": "# master\n\n## Project setup\n```\nyarn install\n```\n\n### Compiles and hot-reloads for development\n```\nyarn run serve\n```\n\n### Compiles and minifies for production\n```\nyarn run build\n```\n\n### Run your tests\n```\nyarn run test\n```\n\n### Lints and fixes files\n```\nyarn run lint\n```\n\n### Customize configuration\nSee [Configuration Reference](https://cli.vuejs.org/config/).\n"
  },
  {
    "path": "examples/master/babel.config.js",
    "content": "module.exports = {\n  presets: [\n    '@vue/cli-plugin-babel/preset'\n  ]\n}\n"
  },
  {
    "path": "examples/master/package.json",
    "content": "{\n  \"name\": \"master\",\n  \"version\": \"0.1.0\",\n  \"private\": true,\n  \"scripts\": {\n    \"serve\": \"vue-cli-service serve\",\n    \"build\": \"vue-cli-service build\",\n    \"postbuild\": \"cp-cli dist/index.html dist/404.html\",\n    \"lint\": \"vue-cli-service lint\"\n  },\n  \"dependencies\": {\n    \"core-js\": \"^3.4.4\",\n    \"qiankun\": \"^2.0.0\",\n    \"vue\": \"^2.6.10\"\n  },\n  \"devDependencies\": {\n    \"@vue/cli-plugin-babel\": \"^4.1.0\",\n    \"@vue/cli-plugin-eslint\": \"^4.1.0\",\n    \"@vue/cli-service\": \"^4.1.0\",\n    \"@vue/eslint-config-standard\": \"^4.0.0\",\n    \"babel-eslint\": \"^10.0.3\",\n    \"cp-cli\": \"^2.0.0\",\n    \"eslint\": \"^5.16.0\",\n    \"eslint-plugin-vue\": \"^5.0.0\",\n    \"vue-cli-plugin-qiankun\": \"../../\",\n    \"vue-template-compiler\": \"^2.6.10\"\n  }\n}\n"
  },
  {
    "path": "examples/master/public/index.html",
    "content": "<!DOCTYPE html>\n<html lang=\"en\">\n  <head>\n    <meta charset=\"utf-8\">\n    <meta http-equiv=\"X-UA-Compatible\" content=\"IE=edge\">\n    <meta name=\"viewport\" content=\"width=device-width,initial-scale=1.0\">\n    <link rel=\"icon\" href=\"<%= BASE_URL %>favicon.ico\">\n    <title>master</title>\n  </head>\n  <body>\n    <noscript>\n      <strong>We're sorry but master doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>\n    </noscript>\n    <div id=\"app\"></div>\n    <!-- built files will be auto injected -->\n  </body>\n</html>\n"
  },
  {
    "path": "examples/master/src/App.vue",
    "content": "<template>\n  <div id=\"container\">\n    <header>\n      <nav>\n        <ol>\n          <li v-for=\"app of apps\" :key=\"app.name\">\n            <a @click=\"goto(app.name, app.activeRule)\">{{app.name}}</a>\n          </li>\n        </ol>\n      </nav>\n    </header>\n    <div id=\"appContainer\" />\n  </div>\n</template>\n\n<script>\nimport { registerMicroApps, runAfterFirstMounted, setDefaultMountApp, start } from 'qiankun'\n\nconst apps = process.env.NODE_ENV === 'production'\n  ? [\n    { name: 'foo-app', entry: '/vue-cli-plugin-qiankun/foo-app/source.html', container: '#appContainer', activeRule: '/vue-cli-plugin-qiankun/foo-app' },\n    { name: 'bar-app', entry: '/vue-cli-plugin-qiankun/bar-app/source.html', container: '#appContainer', activeRule: '/vue-cli-plugin-qiankun/bar-app' }\n  ]\n  : [\n    { name: 'foo-app', entry: '//localhost:8081', container: '#appContainer', activeRule: '/foo-app' },\n    { name: 'bar-app', entry: '//localhost:8082', container: '#appContainer', activeRule: '/bar-app' }\n  ]\n\nexport default {\n  name: 'master',\n  data () {\n    return {\n      apps\n    }\n  },\n  created () {\n    if (!window.__INJECTED_PUBLIC_PATH_BY_QIANKUN__) {\n      this.initQiankun()\n    } else {\n      location.reload()\n    }\n  },\n  methods: {\n    goto (title, href) {\n      window.history.pushState({}, title, href)\n    },\n    initQiankun () {\n      registerMicroApps(\n        apps,\n        {\n          beforeLoad: [\n            app => {\n              // eslint-disable-next-line no-console\n              console.log('before load', app)\n            }\n          ],\n          beforeMount: [\n            app => {\n              // eslint-disable-next-line no-console\n              console.log('before mount', app)\n            }\n          ],\n          afterUnmount: [\n            app => {\n              // eslint-disable-next-line no-console\n              console.log('after unload', app)\n            }\n          ]\n        }\n      )\n\n      const defaultApp = apps[0] || {}\n      setDefaultMountApp(defaultApp.activeRule)\n\n      runAfterFirstMounted(() => {\n        // eslint-disable-next-line no-console\n        console.info('first app mounted')\n      })\n\n      start({ prefetch: true })\n    }\n  }\n}\n</script>\n\n<style scoped>\na {\n  color: #42b983;\n  cursor: pointer;\n}\n.appContainer {\n  margin-top: 50px;\n}\n</style>\n"
  },
  {
    "path": "examples/master/src/main.js",
    "content": "import Vue from 'vue'\nimport App from './App.vue'\n\nVue.config.productionTip = false\n\nnew Vue({\n  render: h => h(App)\n}).$mount('#app')\n"
  },
  {
    "path": "examples/master/vue.config.js",
    "content": "module.exports = {\n  productionSourceMap: false,\n  publicPath: process.env.NODE_ENV === 'production'\n    ? '/vue-cli-plugin-qiankun/'\n    : '/'\n}\n"
  },
  {
    "path": "examples/package.json",
    "content": "{\n  \"name\": \"examples\",\n  \"license\": \"MIT\",\n  \"scripts\": {\n    \"install:all\": \"yarn install:master && yarn install:foo && yarn install:bar\",\n    \"install:master\": \"cd master && yarn\",\n    \"install:foo\": \"cd foo-app && yarn\",\n    \"install:bar\": \"cd bar-app && yarn\",\n    \"serve:all\": \"concurrently \\\"yarn serve:master\\\" \\\"yarn serve:foo\\\" \\\"yarn serve:bar\\\"\",\n    \"serve:master\": \"cd master && yarn serve\",\n    \"serve:foo\": \"cd foo-app && yarn serve\",\n    \"serve:bar\": \"cd bar-app && yarn serve\",\n    \"build:all\": \"concurrently \\\"yarn build:master\\\" \\\"yarn build:foo\\\" \\\"yarn build:bar\\\"\",\n    \"build:master\": \"cd master && yarn build\",\n    \"build:foo\": \"cd foo-app && yarn build\",\n    \"build:bar\": \"cd bar-app && yarn build\"\n  },\n  \"devDependencies\": {\n    \"concurrently\": \"^5.0.2\"\n  }\n}\n"
  },
  {
    "path": "generator/index.js",
    "content": "module.exports = (api, { type }) => {\n  require(`./${type}`)(api)\n\n  if (api.hasPlugin('eslint')) {\n    api.onCreateComplete(() => {\n      require('@vue/cli-plugin-eslint/lint')({}, api)\n    })\n  }\n}\n"
  },
  {
    "path": "generator/master.js",
    "content": "module.exports = (api) => {\n  api.extendPackage({\n    dependencies: {\n      \"qiankun\": \"^2.0.0\"\n    }\n  })\n\n  api.render('./template/master')\n}\n"
  },
  {
    "path": "generator/slave.js",
    "content": "const slaveMain = require('./template/slave/main')\n\nmodule.exports = (api) => {\n  const { port } = api.options\n  const { projectName } = api.rootOptions\n\n  api.extendPackage({\n    scripts: {\n      serve: `vue-cli-service serve --port ${port}`\n    }\n  })\n\n  api.postProcessFiles((files) => {\n    const routerConfigPath = 'src/router/index.js'\n\n    if (files[routerConfigPath]) {\n      files[routerConfigPath] = files[routerConfigPath].replace(\n        /base: process.env.BASE_URL,/,\n        `base: window.__POWERED_BY_QIANKUN__ ? '/${projectName}' : '/',`\n      )\n    }\n\n    if (!files[api.entryFile].match(/\\nnew Vue\\(/)) {\n      files['src/slave-main.js'] = slaveMain.standard.replace(\n        /(new Vue\\([\\s\\S]*)/,\n        slaveMain.replacement\n      )\n      console.info('\\n暂无法自动转换该项目的 main.js 文件，请参考 src/slave-main.js 手动修改\\n')\n    } else {\n      files[api.entryFile] = files[api.entryFile].replace(\n        /(new Vue\\([\\s\\S]*)/,\n        slaveMain.replacement\n      )\n    }\n  })\n}\n"
  },
  {
    "path": "generator/template/master/src/App.vue",
    "content": "<template>\n  <div id=\"container\">\n    <header>\n      <nav>\n        <ol>\n          <li v-for=\"app of apps\" :key=\"app.name\">\n            <a @click=\"goto(app.name, `${app.activeRule}`)\">{{app.name}}</a>\n          </li>\n        </ol>\n      </nav>\n    </header>\n    <div id=\"appContainer\" />\n  </div>\n</template>\n\n<script>\n  import { registerMicroApps, runAfterFirstMounted, setDefaultMountApp, start } from 'qiankun'\n\n\texport default {\n    name: 'master',\n\t\tdata () {\n      return {\n        apps: [\n          { name: 'slave', entry: '//localhost:8081', container: '#appContainer', activeRule: '/slave' }\n        ]\n      }\n    },\n    created () {\n      if (!window.__INJECTED_PUBLIC_PATH_BY_QIANKUN__) {\n        this.initQiankun()\n      } else {\n        // fix hot-reload\n        location.reload()\n      }\n    },\n\t\tmethods: {\n\t\t\tgoto (title, href) {\n\t\t\t\twindow.history.pushState({}, title, href)\n      },\n      initQiankun () {\n        registerMicroApps(\n          this.apps,\n          {\n            beforeLoad: [\n              app => {\n                // eslint-disable-next-line no-console\n                console.log('before load', app)\n              }\n            ],\n            beforeMount: [\n              app => {\n                // eslint-disable-next-line no-console\n                console.log('before mount', app)\n              }\n            ],\n            afterUnmount: [\n              app => {\n                // eslint-disable-next-line no-console\n                console.log('after unload', app)\n              }\n            ]\n          }\n        )\n\n        setDefaultMountApp('/slave')\n\n        runAfterFirstMounted(() => {\n          // eslint-disable-next-line no-console\n          console.info('first app mounted')\n        })\n\n        start({ prefetch: true })\n      }\n\t\t}\n\t}\n</script>\n\n<style scoped>\n  a {\n    color: #42b983;\n    cursor: pointer;\n  }\n  .appContainer {\n    margin-top: 50px;\n  }\n</style>\n"
  },
  {
    "path": "generator/template/slave/main.js",
    "content": "exports.standard = `import Vue from 'vue'\n  import App from './App.vue'\n\n  Vue.config.productionTip = false\n\n  new Vue({\n    render: h => h(App)\n  }).$mount('#app')\n`\n\nexports.replacement = `let instance = null\n\n  function render () {\n    instance = $1\n  }\n\n  if (!window.__POWERED_BY_QIANKUN__) {\n    render()\n  }\n\n  export async function bootstrap () {\n    // eslint-disable-next-line no-console\n    console.log('vue app bootstraped')\n  }\n\n  export async function mount (props) {\n    // eslint-disable-next-line no-console\n    console.log('props from main framework', props)\n    render()\n  }\n\n  export async function unmount () {\n    instance.$destroy()\n    instance = null\n  }\n`\n"
  },
  {
    "path": "index.js",
    "content": "const path = require('path')\n\nmodule.exports = (api) => {\n  const { name, dependencies = {} } = api.service.pkg\n  const isMaster = !!dependencies.qiankun\n\n  if (isMaster) return\n\n  api.chainWebpack((config) => {\n    config.devServer\n      .headers({\n        'Access-Control-Allow-Origin': '*'\n      })\n\n    config.merge({\n      entry: {\n        main: [\n          path.resolve(__dirname, './public-path.js'),\n          path.resolve(api.service.context, 'src/main.js')\n        ]\n      }\n    })\n\n    config.output\n      .library(`${name}-[name]`)\n      .libraryTarget('umd')\n      .jsonpFunction(`webpackJsonp_${name}`)\n  })\n}\n"
  },
  {
    "path": "package.json",
    "content": "{\n  \"name\": \"vue-cli-plugin-qiankun\",\n  \"version\": \"1.0.1\",\n  \"description\": \"qiankun plugin for vue-cli\",\n  \"main\": \"index.js\",\n  \"files\": [\n    \"generator\",\n    \"index.js\",\n    \"public-path.js\",\n    \"prompts.js\"\n  ],\n  \"repository\": \"https://github.com/F-loat/vue-cli-plugin-qiankun\",\n  \"keywords\": [\n    \"vue-cli\",\n    \"plugin\",\n    \"qiankun\",\n    \"micro-frontend\"\n  ],\n  \"author\": \"F-loat <chaimaoyuan@foxmail.com>\",\n  \"license\": \"MIT\",\n  \"private\": false\n}\n"
  },
  {
    "path": "prompts.js",
    "content": "module.exports = [\n  {\n    name: 'type',\n    type: 'list',\n    message: 'Pick a project type:',\n    choices: [\n      {\n        name: 'master',\n        value: 'master'\n      },\n      {\n        name: 'slave',\n        value: 'slave'\n      }\n    ]\n  },\n  {\n    name: 'port',\n    type: 'input',\n    default: 8080,\n    message: 'Input a slave project port:',\n    when: answers => answers.type === 'slave'\n  }\n]\n"
  },
  {
    "path": "public-path.js",
    "content": "if (window.__POWERED_BY_QIANKUN__) {\n  // eslint-disable-next-line\n  __webpack_public_path__ = window.__INJECTED_PUBLIC_PATH_BY_QIANKUN__\n}\n"
  }
]