From a6af50dadb9f5d1c061e87a1d4183f18c6f84bdc Mon Sep 17 00:00:00 2001 From: kagol Date: Mon, 6 Sep 2021 20:02:58 +0800 Subject: [PATCH 1/3] =?UTF-8?q?fix:=20=E4=BF=AE=E5=A4=8Dsh=E4=B8=8D?= =?UTF-8?q?=E5=AD=98=E5=9C=A8=E7=9A=84=E9=97=AE=E9=A2=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- sites/index.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/sites/index.md b/sites/index.md index 403f7e8f..0e850304 100644 --- a/sites/index.md +++ b/sites/index.md @@ -10,7 +10,7 @@ 推荐使用@vite/cli创建你的项目 -```sh +```shell yarn create vite my-vue-app --template vue-ts ``` @@ -18,7 +18,7 @@ yarn create vite my-vue-app --template vue-ts 进入你的项目文件夹,使用yarn安装DevUI -```sh +```shell yarn add vue-devui # 可选,字体图标库, 部分Demo依赖此字体库 @@ -38,6 +38,6 @@ createApp(App).use(DevUI).mount('#app') ### 4. 启动开发调试 -```sh +```shell yarn dev ``` \ No newline at end of file -- Gitee From 5ff476b9165d543b57f6408ea05fd5d5fd03290a Mon Sep 17 00:00:00 2001 From: kagol Date: Mon, 6 Sep 2021 21:01:10 +0800 Subject: [PATCH 2/3] =?UTF-8?q?build:=20=E5=A2=9E=E5=8A=A0=E6=8C=89?= =?UTF-8?q?=E9=9C=80=E6=89=93=E5=8C=85=E7=9A=84=E8=84=9A=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .gitignore | 1 + scripts/build-components.js | 71 +++++++++++++++++++++++++++++++++++++ 2 files changed, 72 insertions(+) create mode 100644 scripts/build-components.js diff --git a/.gitignore b/.gitignore index 5aa59fce..e9dd2d13 100644 --- a/.gitignore +++ b/.gitignore @@ -2,6 +2,7 @@ node_modules .DS_Store dist dist-ssr +build *.local package-lock.json pnpm-lock.yaml diff --git a/scripts/build-components.js b/scripts/build-components.js new file mode 100644 index 00000000..3406270f --- /dev/null +++ b/scripts/build-components.js @@ -0,0 +1,71 @@ +const path = require('path') +const fs = require('fs') +const { defineConfig, build } = require('vite') +const vue = require('@vitejs/plugin-vue') +const vueJsx = require('@vitejs/plugin-vue-jsx') + +const entryDir = path.resolve(__dirname, '../devui') +const outputDir = path.resolve(__dirname, '../build') + +const baseConfig = defineConfig({ + configFile: false, + publicDir: false, + plugins: [ vue(), vueJsx() ] +}) + +const rollupOptions = { + external: ['vue', 'vue-router'], + output: { + globals: { + vue: 'Vue' + } + } +} + +const buildSingle = async (name) => { + await build(defineConfig({ + ...baseConfig, + build: { + rollupOptions, + lib: { + entry: path.resolve(entryDir, name), + name: 'index', + fileName: 'index', + formats: ['es', 'umd'] + }, + outDir: path.resolve(outputDir, name) + } + })) +} + +const buildAll = async () => { + await build(defineConfig({ + ...baseConfig, + build: { + rollupOptions, + lib: { + entry: path.resolve(entryDir, 'vue-devui.ts'), + name: 'vue-devui', + fileName: 'vue-devui', + formats: ['es', 'umd'] + }, + outDir: outputDir + } + })) +} + +const runBuild = async () => { + const components = fs.readdirSync(entryDir).filter(name => { + const componentDir = path.resolve(entryDir, name) + const isDir = fs.lstatSync(componentDir).isDirectory() + return isDir && fs.readdirSync(componentDir).includes('index.ts') + }) + + for(const name of components) { + await buildSingle(name) + } + + await buildAll() +} + +runBuild() -- Gitee From e9ec661f80001a08042035f011de339c7250cba2 Mon Sep 17 00:00:00 2001 From: kagol Date: Mon, 6 Sep 2021 21:23:08 +0800 Subject: [PATCH 3/3] =?UTF-8?q?refactor:=20=E8=BF=81=E7=A7=BBbuild?= =?UTF-8?q?=E8=84=9A=E6=9C=AC=E5=88=B0devui-cli=E4=B8=AD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../commands/build.js | 8 +-- devui-cli/index.js | 6 ++ package.json | 5 +- scripts/add-api.js | 65 ----------------- scripts/const.js | 69 ------------------ scripts/convert-component-route.js | 72 ------------------- scripts/delete-old-api.js | 28 -------- scripts/generate-devui.js | 47 ------------ 8 files changed, 11 insertions(+), 289 deletions(-) rename scripts/build-components.js => devui-cli/commands/build.js (97%) delete mode 100644 scripts/add-api.js delete mode 100644 scripts/const.js delete mode 100644 scripts/convert-component-route.js delete mode 100644 scripts/delete-old-api.js delete mode 100644 scripts/generate-devui.js diff --git a/scripts/build-components.js b/devui-cli/commands/build.js similarity index 97% rename from scripts/build-components.js rename to devui-cli/commands/build.js index 3406270f..1d2090d8 100644 --- a/scripts/build-components.js +++ b/devui-cli/commands/build.js @@ -54,7 +54,9 @@ const buildAll = async () => { })) } -const runBuild = async () => { +exports.build = async () => { + await buildAll() + const components = fs.readdirSync(entryDir).filter(name => { const componentDir = path.resolve(entryDir, name) const isDir = fs.lstatSync(componentDir).isDirectory() @@ -64,8 +66,4 @@ const runBuild = async () => { for(const name of components) { await buildSingle(name) } - - await buildAll() } - -runBuild() diff --git a/devui-cli/index.js b/devui-cli/index.js index db57d98c..24f11c31 100755 --- a/devui-cli/index.js +++ b/devui-cli/index.js @@ -1,6 +1,7 @@ #!/usr/bin/env node const { Command } = require('commander') const { create, validateCreateType } = require('./commands/create') +const { build } = require('./commands/build') const { VERSION, CREATE_SUPPORT_TYPES } = require('./shared/constant') const program = new Command() @@ -13,4 +14,9 @@ program .option('--cover', '覆盖原文件', false) .action(create) +program + .command('build') + .description('打包组件库') + .action(build) + program.parse().version(VERSION) diff --git a/package.json b/package.json index e1c54ce8..fe1f86db 100644 --- a/package.json +++ b/package.json @@ -27,14 +27,13 @@ "serve": "vitepress serve sites", "app:dev": "vite", "app:build": "vite build", - "build:lib": "yarn predev && vite build --config vite.config.build.ts && cp package.json dist && cp README.md dist", + "build:lib": "yarn predev && yarn build:components && cp package.json build && cp README.md build", "test": "jest --config jest.config.js", "ls-lint": "ls-lint", "lint": "eslint \"{src,devui}/**/*.{vue,js,ts,jsx,tsx}\"", "lint:fix": "eslint --fix \"{src,devui}/**/*.{vue,js,ts,jsx,tsx}\"", "stylelint": "stylelint --fix \"{devui,src}/**/*.{scss,css}\"", - "convert:route": "node ./scripts/convert-component-route.js", - "generate:devui": "node scripts/generate-devui.js", + "build:components": "node ./devui-cli/index.js build", "clean:cli": "npm uninstall -g devui-cli & npm uninstall -g vue-devui", "cli:create": "node ./devui-cli/index.js create", "predev": "node ./devui-cli/index.js create -t vue-devui --ignore-parse-error" diff --git a/scripts/add-api.js b/scripts/add-api.js deleted file mode 100644 index 5ffdbf8d..00000000 --- a/scripts/add-api.js +++ /dev/null @@ -1,65 +0,0 @@ -const fs = require('fs') -const path = require('path') -const shelljs = require('shelljs') -const program = require('commander') -const { COMPONENTS } = require('./const') - -const DEFAULT_SOURCE_PATH = path.resolve(__dirname, '../../../code/ng-devui/devui') -const DEFAULT_TARGET_PATH = path.resolve(__dirname, '../devui') - -// 从命令行参数中取源文件和目标文件路径 -program - .option('-s, --source ', 'Original file path', DEFAULT_SOURCE_PATH) - .option('-t, --target ', 'Target file path', DEFAULT_TARGET_PATH) -program.parse(process.argv); - -const { source, target } = program.opts(); - -const sourcePath = source; -const targetPath = target; - -function addApi(sourcePath, targetPath) { - fs.readdir(sourcePath, function(sourcePathError, sourceComponentFolder) { - if (sourcePathError) { - console.error(sourcePathError) - return - } - - sourceComponentFolder - .filter(doc => COMPONENTS.includes(doc)) - .forEach((componentName) => { - const targetDocPath = path.resolve(targetPath, componentName, 'doc') - - // 在组件目录下创建 doc 目录 - if (!fs.existsSync(targetDocPath)) { - fs.mkdirSync(targetDocPath) - } - - // 拷贝中英文 API 文档 - const sourceDocPath = path.resolve(sourcePath, componentName, 'doc') - fs.readdir(sourceDocPath, (sourceDocPathError, sourceDocs) => { - if (sourceDocPathError) { - console.error(sourceDocPathError) - return - } - - sourceDocs.forEach(sourceDoc => { - shelljs.cp(path.resolve(sourceDocPath, sourceDoc), targetDocPath) - }) - }) - - // 修改路由 - const componentRoutePath = path.resolve(targetPath, componentName, 'demo', componentName + '.route.ts') - shelljs.sed('-i', /'..\/doc\/api-cn.md'/, 'ApiCn', componentRoutePath) - shelljs.sed('-i', /'..\/doc\/api-en.md'/, 'ApiEn', componentRoutePath) - shelljs.sed( - '-i', - /const routes = \[/, - 'import ApiCn from \'../doc/api-cn.md\'\nimport ApiEn from \'../doc/api-en.md\'\nconst routes = [', - componentRoutePath - ) - }) - }) -} - -addApi(sourcePath, targetPath) diff --git a/scripts/const.js b/scripts/const.js deleted file mode 100644 index 4f867767..00000000 --- a/scripts/const.js +++ /dev/null @@ -1,69 +0,0 @@ -const COMPONENTS = [ - 'accordion', - 'alert', - 'anchor', - 'auto-complete', - 'avatar', - 'back-top', - 'badge', - 'breadcrumb', - 'button', - 'card', - - 'carousel', - 'cascader', - 'checkbox', - 'data-table', - 'datepicker', - 'dragdrop', - 'drawer', - 'dropdown', - 'editable-select', - 'form', - - - 'fullscreen', - 'gantt', - 'image-preview', - 'input-number', - 'layout', - 'loading', - 'modal', - 'multi-auto-complete', - 'pagination', - 'panel', - - 'popover', - 'progress', - 'quadrant-diagram', - 'radio', - 'rate', - 'read-tip', - 'search', - 'select', - 'slider', - 'splitter', - - 'status', - 'steps-guide', - 'sticky', - 'tabs', - 'tags', - 'tags-input', - 'text-input', - 'textarea', - 'time-axis', - 'time-picker', - - 'toast', - 'switch', - 'tooltip', - 'transfer', - 'tree', - 'tree-select', - 'upload', -] - -module.exports = { - COMPONENTS -} diff --git a/scripts/convert-component-route.js b/scripts/convert-component-route.js deleted file mode 100644 index eb459e23..00000000 --- a/scripts/convert-component-route.js +++ /dev/null @@ -1,72 +0,0 @@ -const fs = require('fs'); -const path = require('path'); -const shelljs = require('shelljs'); -const program = require('commander'); - -const DEFAULT_SOURCE_PATH = path.resolve(__dirname, '../docs/component.route.ts'); -const DEFAULT_TARGET_PATH = path.resolve(__dirname, '../src/components'); - -// 从命令行参数中取源文件和目标文件路径 -program - .option('-s, --source ', 'Original file path', DEFAULT_SOURCE_PATH) - .option('-t, --target ', 'Target file path', DEFAULT_TARGET_PATH) -program.parse(process.argv); - -const { source, target } = program.opts(); - -/** - * 将 ng-devui 的组件路由文件转换成 vue-devui 的路由文件 - * - * 主要转换规则: - * 1. loadChildren 整行移除,loadChildren 分多行的,需要将多行都移除 - * 2. data 改成 meta - * 3. import 的组件都从 app-demo-cell 导入 - * - * 例如: - * import { ExamplePanelComponent } from './example-panel.component'; -> import ExamplePanelComponent from './app-demo-cell.vue'; - * import { GetStartedComponent } from './get-started.component'; -> import GetStartedComponent from './app-demo-cell.vue'; - * import { ColorComponent } from './color/color.component'; -> import ColorComponent from './app-demo-cell.vue'; - * import { ThemeGuideComponent } from './theme-guide.component'; -> import ThemeGuideComponent from './app-demo-cell.vue'; - * - * { - * path: 'accordion', - * component: ExamplePanelComponent, - * loadChildren: () => import('../../../devui/accordion/demo/accordion-demo.moudule').then((m) => m.AccordionDemoModule), - * data: { - * type: '导航', - * enType: 'Navigation', - * name: 'Accordion', - * cnName: '手风琴', - * }, - * }, - * -> - * { - * path: 'accordion', - * component: ExamplePanelComponent, - * meta: { - * type: '导航', - * enType: 'Navigation', - * name: 'Accordion', - * cnName: '手风琴', - * }, - * }, - */ -function convertComponentRoute(source, target) { - shelljs.sed('-i', /import { ExamplePanelComponent } from '.\/example-panel.component'/, 'import ExamplePanelComponent from \'.\/app-demo-cell.vue\'', source); - shelljs.sed('-i', /import { GetStartedComponent } from '.\/get-started.component'/, 'import GetStartedComponent from \'.\/app-demo-cell.vue\'', source); - shelljs.sed('-i', /import { ColorComponent } from '.\/color\/color.component'/, 'import ColorComponent from \'.\/app-demo-cell.vue\'', source); - shelljs.sed('-i', /import { ThemeGuideComponent } from '.\/theme-guide.component'/, 'import ThemeGuideComponent from \'.\/app-demo-cell.vue\'', source); - - shelljs.sed('-i', /redirectTo: 'get-start'/, 'redirect: \'/components/button\'', source); - - shelljs.sed('-i', /^.*loadChildren.*$/, '', source); - shelljs.sed('-i', /^.*import\(.*$/, '', source); - - shelljs.sed('-i', /data: {/, 'meta: {', source); - - shelljs.sed('-i', /];/, '];\n\nexport default routesConfig;', source); - - shelljs.cp(source, target); -} - -convertComponentRoute(source, target); diff --git a/scripts/delete-old-api.js b/scripts/delete-old-api.js deleted file mode 100644 index b4517dff..00000000 --- a/scripts/delete-old-api.js +++ /dev/null @@ -1,28 +0,0 @@ -const fs = require('fs') -const path = require('path') -const shelljs = require('shelljs') -const { COMPONENTS } = require('./const') - -const targetPath = path.resolve(__dirname, '../devui') - -function deleteOldApi(targetPath) { - fs.readdir(targetPath, function(targetPathError, targetComponentFolder) { - if (targetPathError) { - console.error(targetPathError) - return - } - - targetComponentFolder - .filter(doc => COMPONENTS.includes(doc)) - .forEach((componentName) => { - const targetApiPath = path.resolve(targetPath, componentName, 'api') - - // 在组件目录下创建 doc 目录 - if (fs.existsSync(targetApiPath)) { - shelljs.rm('-rf', targetApiPath); - } - }) - }) -} - -deleteOldApi(targetPath) diff --git a/scripts/generate-devui.js b/scripts/generate-devui.js deleted file mode 100644 index 34976e1a..00000000 --- a/scripts/generate-devui.js +++ /dev/null @@ -1,47 +0,0 @@ -require('esbuild-register'); - -const path = require('path'); -const fs = require('fs-extra'); - -const config = require('../sites/.vitepress/config/sidebar').default; -console.log('config:', config); - -let importStr = `import { App } from 'vue';\n\n`; -const components = []; - -config['/'].forEach(({ text: ctext, children }) => { - if (ctext !== '快速开始') { - importStr += `// ${ctext}\n`; - console.log('ctext:', ctext); - console.log('children:', children); - children && children.forEach(({ text, link }) => { - const name = text.split(' ')[0]; - const linkItem = link.split('/').filter(item => item); - const filename = linkItem[1]; - importStr += `import ${name} from './${filename}';\n`; - components.push(name); - }) - importStr += `\n`; - } -}); - -const componentStr = components.join(', '); - -let installStr = `function install(app: App): void { - const packages = [ ${componentStr} ]; - packages.forEach((item: any) => { - if (item.install) { - app.use(item); - } else if (item.name) { - app.component(item.name, item); - } - }); -}\n\n`; - -const exportStr = `export { ${componentStr} }; -export default { install, version: '0.0.1' };`; - -const fileStr = importStr + installStr + exportStr; - -const targetFile = path.resolve(__dirname, '../devui/vue-devui.ts'); -fs.outputFile(targetFile, fileStr, 'utf8'); -- Gitee