From ea7f4bb3bc1d9897481ebd929dbee59e43f5bdb6 Mon Sep 17 00:00:00 2001 From: "moxey.eth" Date: Tue, 24 Oct 2023 12:30:11 +1100 Subject: [PATCH] wip: cli init cmd --- bun.lockb | Bin 249015 -> 257845 bytes package.json | 4 +- scripts/postbuild.ts | 9 +++ site/package.json | 6 +- src/cli.ts | 35 --------- src/cli/commands/build.ts | 4 + src/cli/commands/dev.ts | 6 ++ src/cli/commands/init.ts | 92 +++++++++++++++++++++++ src/cli/commands/preview.ts | 5 ++ src/cli/index.ts | 31 ++++++++ src/cli/templates/default/README.md | 1 + src/cli/templates/default/_gitignore | 21 ++++++ src/cli/templates/default/docs/index.mdx | 3 + src/cli/templates/default/package.json | 15 ++++ src/cli/templates/default/tsconfig.json | 24 ++++++ src/{ => cli}/version.ts | 0 src/package.json | 8 +- src/vite/plugins/css.ts | 8 +- src/vite/plugins/dev.ts | 5 +- src/vite/plugins/postcss/rawStyles.ts | 6 +- tsconfig.base.json | 2 +- 21 files changed, 233 insertions(+), 52 deletions(-) delete mode 100644 src/cli.ts create mode 100644 src/cli/commands/build.ts create mode 100644 src/cli/commands/dev.ts create mode 100644 src/cli/commands/init.ts create mode 100644 src/cli/commands/preview.ts create mode 100644 src/cli/index.ts create mode 100644 src/cli/templates/default/README.md create mode 100644 src/cli/templates/default/_gitignore create mode 100644 src/cli/templates/default/docs/index.mdx create mode 100644 src/cli/templates/default/package.json create mode 100644 src/cli/templates/default/tsconfig.json rename src/{ => cli}/version.ts (100%) diff --git a/bun.lockb b/bun.lockb index 987a9a8a9facfb0082b40bc53f8cd5a01df24535..7ce0d3d2300c5b7339cc17292dce4ceb8f8d6f60 100755 GIT binary patch delta 47537 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 akWpXYtQZ>|4Y|K*Tt?tNeT-tFGy?6c<#v*Y7} znF|Zfu37D2U#n-1M3s8K$BlLGsoCoLi75^HoNVh1zOPzXhY?$2_I1DcSeQ?*d*^g5 z=cIPtGP0-B{qd4MUlE@#<1#WY@*?sE

B8nV2*PE_g7kL}6c9pRW*krX{A4lh1cJcs{IL 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

YbRL9k_ykr19 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 Zm3b%_wmMJdwB=#H7SBA888$rj{{YFMv{wKC diff --git a/package.json b/package.json index 9b7f6dce..b9648a85 100644 --- a/package.json +++ b/package.json @@ -4,9 +4,11 @@ "type": "module", "scripts": { "build": "rimraf src/_lib src/tsconfig.build.* && tsc -p tsconfig.build.json && bun scripts/postbuild.ts", - "dev": "cd playgrounds/default && bun run dev", + "docs:dev": "cd site && bun run dev", + "docs:build": "cd site && bun run build", "format": "biome format . --write", "lint": "biome lint . --apply-unsafe", + "playground": "cd playgrounds/default && bun run dev", "prepare": "bun x simple-git-hooks", "typecheck": "tsc --noEmit" }, diff --git a/scripts/postbuild.ts b/scripts/postbuild.ts index 04cb76a9..0ddd44c7 100644 --- a/scripts/postbuild.ts +++ b/scripts/postbuild.ts @@ -4,15 +4,24 @@ import { readdirSync } from 'node:fs' import { resolve } from 'node:path' import { copy, copyFileSync, readFileSync, writeFileSync } from 'fs-extra' +// Copy index.html copyFileSync( resolve(import.meta.dir, '../src/vite/index.html'), resolve(import.meta.dir, '../src/_lib/vite/index.html'), ) + +// Copy styles copy( resolve(import.meta.dir, '../src/app/styles'), resolve(import.meta.dir, '../src/_lib/app/styles'), ) +// Copy CLI init templates +copy( + resolve(import.meta.dir, '../src/cli/templates'), + resolve(import.meta.dir, '../src/_lib/cli/templates'), +) + rewriteExtensions(resolve(import.meta.dir, '../src/_lib')) //////////////////////////////////////////////////////////////////// diff --git a/site/package.json b/site/package.json index c7f9c292..c3380d88 100644 --- a/site/package.json +++ b/site/package.json @@ -3,9 +3,9 @@ "version": "0.0.0", "type": "module", "scripts": { - "dev": "bun ../src/cli.ts", - "build": "NODE_ENV=production bun ../src/cli.ts build", - "preview": "bun ../src/cli.ts preview" + "dev": "bun ../src/cli/index.ts", + "build": "NODE_ENV=production bun ../src/cli/index.ts build", + "preview": "bun ../src/cli/index.ts preview" }, "dependencies": { "react": "^18.2.0", diff --git a/src/cli.ts b/src/cli.ts deleted file mode 100644 index d2e83884..00000000 --- a/src/cli.ts +++ /dev/null @@ -1,35 +0,0 @@ -#!/usr/bin/env node -import { cac } from 'cac' - -import { version } from './version.js' - -const cli = cac('vocs') - -// dev -cli - .command('[root]') - .alias('dev') - .action(async () => { - const { createDevServer } = await import('./vite/dev-server.js') - const server = await createDevServer() - await server.listen() - server.printUrls() - }) - -// build -cli.command('build').action(async () => { - const { build } = await import('./vite/build.js') - await build() -}) - -// preview -cli.command('preview').action(async () => { - const { preview } = await import('./vite/preview.js') - const server = await preview() - server.printUrls() -}) - -cli.help() -cli.version(version) - -cli.parse() diff --git a/src/cli/commands/build.ts b/src/cli/commands/build.ts new file mode 100644 index 00000000..901ae926 --- /dev/null +++ b/src/cli/commands/build.ts @@ -0,0 +1,4 @@ +export async function build() { + const { build } = await import('../../vite/build.js') + await build() +} diff --git a/src/cli/commands/dev.ts b/src/cli/commands/dev.ts new file mode 100644 index 00000000..d9e5ff80 --- /dev/null +++ b/src/cli/commands/dev.ts @@ -0,0 +1,6 @@ +export async function dev() { + const { createDevServer } = await import('../../vite/dev-server.js') + const server = await createDevServer() + await server.listen() + server.printUrls() +} diff --git a/src/cli/commands/init.ts b/src/cli/commands/init.ts new file mode 100644 index 00000000..8b81ef8a --- /dev/null +++ b/src/cli/commands/init.ts @@ -0,0 +1,92 @@ +// TODO: spice it up + +import { dirname, resolve } from 'node:path' +import { fileURLToPath } from 'node:url' +// @ts-expect-error +import { detect } from 'detect-package-manager' +import { execa } from 'execa' +import { default as fs } from 'fs-extra' +import { default as prompts } from 'prompts' + +type InitParameters = { name: string; git: boolean; install: boolean } + +const __dirname = dirname(fileURLToPath(import.meta.url)) + +export async function init(options: InitParameters) { + const templateDir = resolve(__dirname, '../templates/default') + + const displayName = + options.name || + (( + await prompts({ + type: 'text', + name: 'displayName', + message: 'Enter the name of your project', + validate: (value) => (value ? true : 'Please enter a name'), + }) + ).displayName as string) + const name = kebabcase(displayName) as string + + const destDir = resolve(process.cwd(), name) + + console.log(`Scaffolding project in ${name}...`) + + // Copy contents + fs.copySync(templateDir, destDir) + + // Replace dotfiles + for (const file of fs.readdirSync(destDir)) { + if (!file.startsWith('_')) continue + fs.renameSync(resolve(destDir, file), resolve(destDir, `.${file.slice(1)}`)) + } + + // Replace package.json properties + const pkgJson = fs.readJsonSync(resolve(destDir, 'package.json')) + pkgJson.name = name + fs.writeJsonSync(resolve(destDir, 'package.json'), pkgJson, { spaces: 2 }) + + // Install dependencies + if (options.install) { + const packageManager = + typeof options.install === 'string' ? options.install : detectPackageManager() + await execa(packageManager, ['install', packageManager === 'npm' ? '--quiet' : '--silent'], { + cwd: destDir, + env: { + ...process.env, + ADBLOCK: '1', + DISABLE_OPENCOLLECTIVE: '1', + // we set NODE_ENV to development as pnpm skips dev + // dependencies when production + NODE_ENV: 'development', + }, + }) + } + + // Create git repository + if (options.git) { + await execa('git', ['init'], { cwd: destDir }) + await execa('git', ['add', '.'], { cwd: destDir }) + await execa('git', ['commit', '--no-verify', '--message', 'initial commit'], { + cwd: destDir, + }) + } + + console.log('Done!') +} + +export function kebabcase(str: string) { + return str + .match(/[A-Z]{2,}(?=[A-Z][a-z]+[0-9]*|\b)|[A-Z]?[a-z]+[0-9]*|[A-Z]|[0-9]+/g) + ?.join('-') + .toLowerCase() +} + +export function detectPackageManager() { + const userAgent = process.env.npm_config_user_agent + if (!userAgent) return 'npm' + if (userAgent.includes('pnpm')) return 'pnpm' + if (userAgent.includes('npm')) return 'npm' + if (userAgent.includes('yarn')) return 'yarn' + if (userAgent.includes('bun')) return 'bun' + return 'npm' +} diff --git a/src/cli/commands/preview.ts b/src/cli/commands/preview.ts new file mode 100644 index 00000000..6c35146c --- /dev/null +++ b/src/cli/commands/preview.ts @@ -0,0 +1,5 @@ +export async function preview() { + const { preview } = await import('../../vite/preview.js') + const server = await preview() + server.printUrls() +} diff --git a/src/cli/index.ts b/src/cli/index.ts new file mode 100644 index 00000000..4dc577f2 --- /dev/null +++ b/src/cli/index.ts @@ -0,0 +1,31 @@ +#!/usr/bin/env node +import { cac } from 'cac' + +import { build } from './commands/build.js' +import { dev } from './commands/dev.js' +import { init } from './commands/init.js' +import { preview } from './commands/preview.js' +import { version } from './version.js' + +const cli = cac('vocs') + +cli.command('[root]').alias('dev').action(dev) +cli + .command('init') + .option('-n, --name [name]', 'Name of project') + .option( + '-i, --install [false|npm|pnpm|yarn|bun]', + 'Install dependencies (and optionally force package manager)', + { + default: true, + }, + ) + .option('-g, --git', 'Initialize git repository', { default: true }) + .action(init) +cli.command('build').action(build) +cli.command('preview').action(preview) + +cli.help() +cli.version(version) + +cli.parse() diff --git a/src/cli/templates/default/README.md b/src/cli/templates/default/README.md new file mode 100644 index 00000000..3bb11a44 --- /dev/null +++ b/src/cli/templates/default/README.md @@ -0,0 +1 @@ +This is a [Vocs](https://vocs.dev) project bootstrapped with the Vocs CLI. diff --git a/src/cli/templates/default/_gitignore b/src/cli/templates/default/_gitignore new file mode 100644 index 00000000..7dc3ceb2 --- /dev/null +++ b/src/cli/templates/default/_gitignore @@ -0,0 +1,21 @@ +# See https://help.github.com/articles/ignoring-files/ for more about ignoring files. + +# dependencies +/node_modules +/.pnp +.pnp.js + +# production +/dist + +# misc +.DS_Store +*.pem + +# debug +npm-debug.log* +yarn-debug.log* +yarn-error.log* + +# typescript +*.tsbuildinfo \ No newline at end of file diff --git a/src/cli/templates/default/docs/index.mdx b/src/cli/templates/default/docs/index.mdx new file mode 100644 index 00000000..6a1b6c6a --- /dev/null +++ b/src/cli/templates/default/docs/index.mdx @@ -0,0 +1,3 @@ +# Hello world! + +Welcome to my site! \ No newline at end of file diff --git a/src/cli/templates/default/package.json b/src/cli/templates/default/package.json new file mode 100644 index 00000000..d9435ae2 --- /dev/null +++ b/src/cli/templates/default/package.json @@ -0,0 +1,15 @@ +{ + "name": "__DOCS_NAME__", + "version": "0.0.0", + "type": "module", + "scripts": { + "dev": "vocs", + "build": "vocs build", + "preview": "vocs preview" + }, + "dependencies": { + "react": "latest", + "react-dom": "latest", + "vocs": "latest" + } +} diff --git a/src/cli/templates/default/tsconfig.json b/src/cli/templates/default/tsconfig.json new file mode 100644 index 00000000..d2636aac --- /dev/null +++ b/src/cli/templates/default/tsconfig.json @@ -0,0 +1,24 @@ +{ + "compilerOptions": { + "target": "ES2020", + "useDefineForClassFields": true, + "lib": ["ES2020", "DOM", "DOM.Iterable"], + "module": "ESNext", + "skipLibCheck": true, + + /* Bundler mode */ + "moduleResolution": "bundler", + "allowImportingTsExtensions": true, + "resolveJsonModule": true, + "isolatedModules": true, + "noEmit": true, + "jsx": "react-jsx", + + /* Linting */ + "strict": true, + "noUnusedLocals": true, + "noUnusedParameters": true, + "noFallthroughCasesInSwitch": true + }, + "include": ["**/*.ts", "**/*.tsx"] +} diff --git a/src/version.ts b/src/cli/version.ts similarity index 100% rename from src/version.ts rename to src/cli/version.ts diff --git a/src/package.json b/src/package.json index 2aa8ae0d..44e45627 100644 --- a/src/package.json +++ b/src/package.json @@ -3,7 +3,7 @@ "version": "0.0.0", "type": "module", "bin": { - "vocs": "./_lib/cli.js" + "vocs": "./_lib/cli/index.js" }, "main": "./_lib/index.js", "exports": { @@ -31,6 +31,9 @@ "autoprefixer": "^10.4.16", "cac": "^6.7.14", "compression": "^1.7.4", + "detect-package-manager": "^3.0.1", + "execa": "^8.0.1", + "fs-extra": "^11.1.1", "globby": "^13.2.2", "hastscript": "^8.0.0", "mdast": "^3.0.0", @@ -39,6 +42,7 @@ "minimatch": "^9.0.3", "postcss": "^8.4.31", "postcss-prefix-selector": "^1.16.0", + "prompts": "^2.4.2", "react-helmet": "^6.1.0", "react-router-dom": "^6.16.0", "remark-directive": "^3.0.0", @@ -53,7 +57,9 @@ "vite": "4.4.11" }, "devDependencies": { + "@types/fs-extra": "^11.0.2", "@types/postcss-prefix-selector": "^1.16.2", + "@types/prompts": "^2.4.7", "@types/ua-parser-js": "^0.7.38" } } diff --git a/src/vite/plugins/css.ts b/src/vite/plugins/css.ts index 86c9297d..dabc697c 100644 --- a/src/vite/plugins/css.ts +++ b/src/vite/plugins/css.ts @@ -1,7 +1,7 @@ import { accessSync } from 'node:fs' import { resolve } from 'node:path' -import * as autoprefixer from 'autoprefixer' -import * as tailwindcss from 'tailwindcss' +import { default as autoprefixer } from 'autoprefixer' +import { default as tailwindcss } from 'tailwindcss' import type { PluginOption } from 'vite' import { postcssRawStyles } from './postcss/rawStyles.js' @@ -16,9 +16,9 @@ export function css(): PluginOption { postcss: { plugins: [ postcssRawStyles(), - (autoprefixer as any).default(), + autoprefixer(), tailwindConfig - ? tailwindcss.default({ + ? (tailwindcss as any)({ config: tailwindConfig, }) : undefined, diff --git a/src/vite/plugins/dev.ts b/src/vite/plugins/dev.ts index 0793ff80..5cd7b56f 100644 --- a/src/vite/plugins/dev.ts +++ b/src/vite/plugins/dev.ts @@ -1,7 +1,7 @@ import { readFileSync } from 'node:fs' import { dirname, resolve } from 'node:path' import { fileURLToPath } from 'node:url' -import * as serveStatic from 'serve-static' +import { default as serveStatic } from 'serve-static' import type { PluginOption } from 'vite' const __dirname = dirname(fileURLToPath(import.meta.url)) @@ -17,8 +17,7 @@ export function dev(): PluginOption { }, configureServer(server) { return () => { - // @ts-expect-error - server.middlewares.use(serveStatic.default(resolve(process.cwd(), 'public'))) + server.middlewares.use(serveStatic(resolve(process.cwd(), 'public'))) server.middlewares.use(async (req, res, next) => { const url = req.url && cleanUrl(req.url) diff --git a/src/vite/plugins/postcss/rawStyles.ts b/src/vite/plugins/postcss/rawStyles.ts index 88fa4568..a647d2a4 100644 --- a/src/vite/plugins/postcss/rawStyles.ts +++ b/src/vite/plugins/postcss/rawStyles.ts @@ -1,9 +1,7 @@ -// @ts-expect-error -import * as postcssPrefixSelector from 'postcss-prefix-selector' +import { default as postcssPrefixSelector } from 'postcss-prefix-selector' export function postcssRawStyles() { - // @ts-expect-error - return postcssPrefixSelector.default({ + return postcssPrefixSelector({ prefix: ':not([data-vocs-raw])', includeFiles: [/elements\.css/, /layouts\.css/], transform(prefix: string, selector_: string) { diff --git a/tsconfig.base.json b/tsconfig.base.json index c473eccb..d0cec300 100644 --- a/tsconfig.base.json +++ b/tsconfig.base.json @@ -22,7 +22,7 @@ // Interop constraints "esModuleInterop": false, - "allowSyntheticDefaultImports": false, + "allowSyntheticDefaultImports": true, "forceConsistentCasingInFileNames": true, "verbatimModuleSyntax": true, "importHelpers": true, // This is only used for build validation. Since we do not have `tslib` installed, this will fail if we accidentally make use of anything that'd require injection of helpers.