diff --git a/package.json b/package.json index 1a2202e..de1346f 100644 --- a/package.json +++ b/package.json @@ -26,7 +26,8 @@ "homepage": "https://github.com/xus-code/bundle-tools#readme", "scripts": { "test": "jest", - "copy:preset": "xus copy --src packages/preset-built-in/src/plugin/template --dest packages/preset-built-in/dist/plugin/template" + "copy:preset": "xus copy --src packages/preset-built-in/src/plugin/template --dest packages/preset-built-in/dist/plugin/template", + "copy:create": "xus copy --src packages/create-lib/src/template --dest packages/create-lib/dist/template" }, "devDependencies": { "@types/jest": "^26.0.20", diff --git a/packages/cli-shared/src/file/copyDir.ts b/packages/cli-shared/src/file/copyDir.ts index b3aceea..f482fe3 100644 --- a/packages/cli-shared/src/file/copyDir.ts +++ b/packages/cli-shared/src/file/copyDir.ts @@ -2,15 +2,15 @@ import { mkdirSync, readdirSync, statSync, copyFileSync } from 'fs' import { resolve } from 'path' export function copy(src: string, dest: string) { - mkdirSync(dest, { recursive: true }) - for (const file of readdirSync(src)) { - const srcPath = resolve(src, file) - const destPath = resolve(dest, file) - const stat = statSync(srcPath) - if (stat.isDirectory()) { + const stat = statSync(src) + if (stat.isDirectory()) { + mkdirSync(dest, { recursive: true }) + for (const file of readdirSync(src)) { + const srcPath = resolve(src, file) + const destPath = resolve(dest, file) copy(srcPath, destPath) - } else { - copyFileSync(srcPath, destPath) } + } else { + copyFileSync(src, dest) } } diff --git a/packages/plugin-cmd-create/README.md b/packages/create-lib/README.md similarity index 100% rename from packages/plugin-cmd-create/README.md rename to packages/create-lib/README.md diff --git a/packages/plugin-cmd-create/package.json b/packages/create-lib/package.json similarity index 75% rename from packages/plugin-cmd-create/package.json rename to packages/create-lib/package.json index 5b4d2eb..0293fc8 100644 --- a/packages/plugin-cmd-create/package.json +++ b/packages/create-lib/package.json @@ -1,7 +1,11 @@ { - "name": "@xus/preset-cmd-create", - "version": "0.1.2", + "name": "@xus/create-lib", + "version": "0.1.0", "description": "xus cli cmd create", + "bin": { + "create-lib": "dist/cli.js", + "cxl": "dist/cli.js" + }, "main": "dist/index.js", "typings": "dist/index.d.ts", "keywords": [ @@ -20,7 +24,8 @@ }, "scripts": { "dev:create": "tsc --watch", - "build:create": "tsc" + "build:create": "tsc", + "update:temp": "node ./updateVersion.js" }, "bugs": { "url": "https://github.com/xus-code/bundle-tools/issues" @@ -28,4 +33,4 @@ "dependencies": { "@xus/cli": "^0.1.5" } -} \ No newline at end of file +} diff --git a/packages/create-lib/src/cli.ts b/packages/create-lib/src/cli.ts new file mode 100644 index 0000000..3b1ce99 --- /dev/null +++ b/packages/create-lib/src/cli.ts @@ -0,0 +1,15 @@ +#!/usr/bin/env node + +import { createTemp } from './create' +import { yParser } from '@xus/cli' +const rawArgs = process.argv.slice(2) +const args = yParser(rawArgs) + +async function main() { + await createTemp(args) +} + +main().catch((e) => { + console.log(e) + process.exit(1) +}) diff --git a/packages/create-lib/src/create.ts b/packages/create-lib/src/create.ts new file mode 100644 index 0000000..c221c5e --- /dev/null +++ b/packages/create-lib/src/create.ts @@ -0,0 +1,108 @@ +import type { IPluginAPI, IArgs } from '@xus/cli' +import { + prompt, + emptyDir, + copy, + getPkgManager, + runCmd, + Spinner +} from '@xus/cli' +import { join } from 'path' +import { existsSync, mkdirSync, readdirSync, writeFileSync } from 'fs' + +const BuiltInTemp = ['ts-lib'] +const FileMap: Record = { + _eslintignore: '.eslintignore', + '_eslintrc.js': '.eslintrc.js', + _gitignore: '.gitignore', + '_prettierrc.js': '.prettierrc.js' +} +const spinner = new Spinner() + +export async function createTemp(args: IArgs, api?: IPluginAPI) { + api?.logger.debug(`handle of project dir`) + let projectDir = args._.shift() + if (!projectDir) { + const { name } = await prompt<{ name: string }>({ + type: 'input', + name: 'name', + message: `Project name:`, + initial: 'xus-project' + }) + projectDir = name + } + api?.logger.debug(projectDir) + + const root = join(process.cwd(), projectDir) + api?.logger.debug(`create root ${root}`) + if (!existsSync(root)) { + mkdirSync(root, { recursive: true }) + } else { + const files = readdirSync(root) + if (files.length > 0) { + const { yes } = await prompt<{ yes: boolean }>({ + type: 'confirm', + name: 'yes', + initial: 'Y', + message: + `Target directory ${root} is not empty.\n` + + `Remove existing files and continue?` + }) + + if (yes) { + emptyDir(root) + } else { + return + } + } + } + + api?.logger.debug(`ready to copy`) + api?.logger.debug(`ensure template`) + let temp = args?.t || args?.template + let message = 'Select a template' + let isvalidTemp = false + + if (temp) { + isvalidTemp = BuiltInTemp.includes(temp) + message = `${temp} isn't a valid template. Please choose:` + } + + if (!temp || !isvalidTemp) { + const { t } = await prompt<{ t: string }>({ + type: 'select', + name: 't', + message, + choices: BuiltInTemp + }) + temp = t + } + api?.logger.debug(temp) + + api?.logger.debug(`copy file`) + spinner.start(`Create project start`) + const tempDir = join(__dirname, `./template/${temp}`) + function write(file: string, content?: string) { + const to = join(root, FileMap[file] ? FileMap[file] : file) + const form = join(tempDir, file) + if (content) { + writeFileSync(to, content) + } else { + copy(form, to) + } + } + const files = readdirSync(tempDir) + for (const file of files) { + write(file) + } + spinner.succeed(`Create project succeed`) + + const pkgManager = getPkgManager() + api?.logger.debug(`current pkgManager ${pkgManager}`) + api?.logger.debug(`install deps`) + await runCmd(pkgManager, pkgManager === 'yarn' ? [] : ['install'], { + start: 'Install deps start', + succeed: 'Install deps succeed', + failed: 'Install deps failed' + }) +} diff --git a/packages/create-lib/src/index.ts b/packages/create-lib/src/index.ts new file mode 100644 index 0000000..7f03b80 --- /dev/null +++ b/packages/create-lib/src/index.ts @@ -0,0 +1,22 @@ +import { createPlugin } from '@xus/cli' +import { createTemp } from './create' + +export default createPlugin({ + name: 'cmd:create', + apply(api) { + api.registerCommand( + 'create', + { + desc: 'create template project', + usage: 'xus create [dir]', + options: { + '--template': 'point a template', + '-t': 'point a template short option' + } + }, + async (args) => { + await createTemp(args, api) + } + ) + } +}) diff --git a/packages/create-lib/src/template/ts-lib/__test__/index.spec.ts b/packages/create-lib/src/template/ts-lib/__test__/index.spec.ts new file mode 100644 index 0000000..249f2dd --- /dev/null +++ b/packages/create-lib/src/template/ts-lib/__test__/index.spec.ts @@ -0,0 +1,7 @@ +import { helloWord } from '../src' + +describe('test index ', () => { + test('test helloWord ', () => { + expect(helloWord()).toBe('hello-word') + }) +}) diff --git a/packages/create-lib/src/template/ts-lib/_eslintignore b/packages/create-lib/src/template/ts-lib/_eslintignore new file mode 100644 index 0000000..de4d1f0 --- /dev/null +++ b/packages/create-lib/src/template/ts-lib/_eslintignore @@ -0,0 +1,2 @@ +dist +node_modules diff --git a/packages/create-lib/src/template/ts-lib/_eslintrc.js b/packages/create-lib/src/template/ts-lib/_eslintrc.js new file mode 100644 index 0000000..fb9d647 --- /dev/null +++ b/packages/create-lib/src/template/ts-lib/_eslintrc.js @@ -0,0 +1,3 @@ +module.exports = { + extends: [require.resolve('@xus/eslint-config')] +} diff --git a/packages/create-lib/src/template/ts-lib/_gitignore b/packages/create-lib/src/template/ts-lib/_gitignore new file mode 100644 index 0000000..6704566 --- /dev/null +++ b/packages/create-lib/src/template/ts-lib/_gitignore @@ -0,0 +1,104 @@ +# Logs +logs +*.log +npm-debug.log* +yarn-debug.log* +yarn-error.log* +lerna-debug.log* + +# Diagnostic reports (https://nodejs.org/api/report.html) +report.[0-9]*.[0-9]*.[0-9]*.[0-9]*.json + +# Runtime data +pids +*.pid +*.seed +*.pid.lock + +# Directory for instrumented libs generated by jscoverage/JSCover +lib-cov + +# Coverage directory used by tools like istanbul +coverage +*.lcov + +# nyc test coverage +.nyc_output + +# Grunt intermediate storage (https://gruntjs.com/creating-plugins#storing-task-files) +.grunt + +# Bower dependency directory (https://bower.io/) +bower_components + +# node-waf configuration +.lock-wscript + +# Compiled binary addons (https://nodejs.org/api/addons.html) +build/Release + +# Dependency directories +node_modules/ +jspm_packages/ + +# TypeScript v1 declaration files +typings/ + +# TypeScript cache +*.tsbuildinfo + +# Optional npm cache directory +.npm + +# Optional eslint cache +.eslintcache + +# Microbundle cache +.rpt2_cache/ +.rts2_cache_cjs/ +.rts2_cache_es/ +.rts2_cache_umd/ + +# Optional REPL history +.node_repl_history + +# Output of 'npm pack' +*.tgz + +# Yarn Integrity file +.yarn-integrity + +# dotenv environment variables file +.env +.env.test + +# parcel-bundler cache (https://parceljs.org/) +.cache + +# Next.js build output +.next + +# Nuxt.js build / generate output +.nuxt +dist + +# Gatsby files +.cache/ +# Comment in the public line in if your project uses Gatsby and *not* Next.js +# https://nextjs.org/blog/next-9-1#public-directory-support +# public + +# vuepress build output +.vuepress/dist + +# Serverless directories +.serverless/ + +# FuseBox cache +.fusebox/ + +# DynamoDB Local files +.dynamodb/ + +# TernJS port file +.tern-port diff --git a/packages/create-lib/src/template/ts-lib/_prettierrc.js b/packages/create-lib/src/template/ts-lib/_prettierrc.js new file mode 100644 index 0000000..1ce560a --- /dev/null +++ b/packages/create-lib/src/template/ts-lib/_prettierrc.js @@ -0,0 +1,5 @@ +const prettier = require('@xus/eslint-config/prettier') + +module.exports = { + ...prettier +} diff --git a/packages/create-lib/src/template/ts-lib/jest.config.js b/packages/create-lib/src/template/ts-lib/jest.config.js new file mode 100644 index 0000000..40dd03c --- /dev/null +++ b/packages/create-lib/src/template/ts-lib/jest.config.js @@ -0,0 +1,13 @@ +const path = require('path') + +module.exports = { + preset: 'ts-jest', + rootDir: __dirname, + collectCoverage: true, + collectCoverageFrom: ['./src/**/**.ts'], + coverageDirectory: path.resolve(__dirname, 'coverage'), + coverageReporters: ['html', 'text'], + moduleFileExtensions: ['ts', 'tsx', 'js', 'json'], + watchPathIgnorePatterns: ['node_modules'], + testMatch: ['./__test__/**/*spec.[jt]s?(x)'] +} diff --git a/packages/create-lib/src/template/ts-lib/package.json b/packages/create-lib/src/template/ts-lib/package.json new file mode 100644 index 0000000..b6fbcc3 --- /dev/null +++ b/packages/create-lib/src/template/ts-lib/package.json @@ -0,0 +1,41 @@ +{ + "name": "ts-lib-template", + "version": "1.0.0", + "description": "ts lib", + "main": "dist/index.cjs.js", + "module": "dist/index.esm.js", + "types": "dist/index.d.ts", + "scripts": { + "build": "xus lib", + "lint-fix": "xus lint", + "test": "jest", + "changelog": "xus changelog", + "release": "xus release" + }, + "keywords": [ + "ts", + "lib" + ], + "author": "who am i", + "license": "MIT", + "gitHooks": { + "pre-commit": "lint-staged", + "commit-msg": "xus commit-lint" + }, + "lint-staged": { + "*.{ts}": [ + "lint-fix", + "prettier --parser=typescript --write" + ] + }, + "devDependencies": { + "@types/jest": "^26.0.20", + "@types/node": "^14.14.22", + "@xus/cli": "^0.1.3", + "@xus/eslint-config": "^0.1.2", + "jest": "^26.6.3", + "lint-staged": "^10.2.11", + "ts-jest": "^26.4.4", + "typescript": "^4.1.3" + } +} diff --git a/packages/create-lib/src/template/ts-lib/src/index.ts b/packages/create-lib/src/template/ts-lib/src/index.ts new file mode 100644 index 0000000..4013776 --- /dev/null +++ b/packages/create-lib/src/template/ts-lib/src/index.ts @@ -0,0 +1 @@ +export const helloWord = () => 'hello-word' diff --git a/packages/create-lib/src/template/ts-lib/tsconfig.json b/packages/create-lib/src/template/ts-lib/tsconfig.json new file mode 100644 index 0000000..498c07f --- /dev/null +++ b/packages/create-lib/src/template/ts-lib/tsconfig.json @@ -0,0 +1,12 @@ +{ + "compilerOptions": { + "target": "esnext", + "module": "esnext", + "strict": true, + "skipLibCheck": true, + "esModuleInterop": true, + "moduleResolution": "node", + "lib": ["esnext", "dom"] + }, + "exclude": ["**/__test__/**/*"] +} diff --git a/packages/create-lib/src/template/ts-lib/xus.config.ts b/packages/create-lib/src/template/ts-lib/xus.config.ts new file mode 100644 index 0000000..fe9263d --- /dev/null +++ b/packages/create-lib/src/template/ts-lib/xus.config.ts @@ -0,0 +1,19 @@ +import { defineConfig } from '@xus/cli' + +export default defineConfig({ + libBuild: { + targets: ['esm', 'cjs', 'browser'], + rollTypes: true + }, + lint: { + eslint: { + include: './src/**/*', + ext: ['.ts'] + }, + stylelint: false + }, + release: { + beforeRelease: [], + branch: 'main' + } +}) diff --git a/packages/plugin-cmd-create/tsconfig.json b/packages/create-lib/tsconfig.json similarity index 100% rename from packages/plugin-cmd-create/tsconfig.json rename to packages/create-lib/tsconfig.json diff --git a/packages/create-lib/updateVersion.js b/packages/create-lib/updateVersion.js new file mode 100644 index 0000000..ab0e759 --- /dev/null +++ b/packages/create-lib/updateVersion.js @@ -0,0 +1,13 @@ +const fs = require('fs') +const path = require('path') + +;(async () => { + const templates = fs.readdirSync(path.join(__dirname, './src/template')) + for (const t of templates) { + const pkgPath = path.join(__dirname, t, `package.json`) + const pkg = require(pkgPath) + pkg.devDependencies['@xus/cli'] = + `^` + require('../cli/package.json').version + fs.writeFileSync(pkgPath, JSON.stringify(pkg, null, 2)) + } +})() diff --git a/packages/plugin-cmd-create/src/index.ts b/packages/plugin-cmd-create/src/index.ts deleted file mode 100644 index dddd5ef..0000000 --- a/packages/plugin-cmd-create/src/index.ts +++ /dev/null @@ -1,17 +0,0 @@ -import { createPlugin } from '@xus/cli' - -export default createPlugin({ - name: 'cmd:create', - apply(api) { - api.registerCommand( - 'create', - { - desc: 'create template project', - usage: 'xus create [dir]' - }, - () => { - // - } - ) - } -}) diff --git a/packages/plugin-cmd-create/src/template/ts-lib/xus.config.ts b/packages/plugin-cmd-create/src/template/ts-lib/xus.config.ts deleted file mode 100644 index bafb717..0000000 --- a/packages/plugin-cmd-create/src/template/ts-lib/xus.config.ts +++ /dev/null @@ -1,7 +0,0 @@ -import { defineConfig } from '@xus/cli' - -export default defineConfig({ - libBuild: { - targets: ['esm', 'cjs', 'browser'] - } -}) diff --git a/packages/preset-built-in/src/plugin/command/copy.ts b/packages/preset-built-in/src/plugin/command/copy.ts index 40b45bc..ab572f4 100644 --- a/packages/preset-built-in/src/plugin/command/copy.ts +++ b/packages/preset-built-in/src/plugin/command/copy.ts @@ -31,6 +31,8 @@ export default createPlugin({ api.logger.error(error) spinner.failed(`copy failed`) } + } else { + api.logger.wran(`src ${src} not exists`) } } }