Divyansh Singh 6 months ago
parent b28667b6b0
commit 266c754de4

@ -51,18 +51,10 @@
"lib"
],
"scripts": {
"clean": "node -e \"require('node:fs').rmSync('./dist',{recursive:!0,force:!0,maxRetries:10})\"",
"dev": "pnpm clean && pnpm dev:shared && pnpm dev:start",
"dev:start": "pnpm --stream '/^dev:(client|node|watch)$/'",
"dev:client": "tsc --sourcemap -w --preserveWatchOutput -p src/client",
"dev:node": "DEV=true pnpm build:node -w",
"dev:shared": "node scripts/copyShared",
"dev:watch": "node scripts/watchAndCopy",
"build": "pnpm build:prepare && pnpm build:client && pnpm build:node",
"build:prepare": "pnpm clean && node scripts/copyShared",
"build:client": "vue-tsc --noEmit -p src/client && tsc -p src/client && node scripts/copyClient",
"build:node": "tsc -p src/node --noEmit && rollup --config rollup.config.ts --configPlugin esbuild",
"test": "pnpm --aggregate-output --reporter=append-only '/^test:(unit|e2e|init)$/'",
"dev": "tsdown --watch",
"build": "tsdown",
"test": "pnpm --aggregate-output --reporter=append-only '/^test:(type|unit|e2e|init)$/'",
"test:type": "vue-tsc -p src/client --noEmit && tsc -p src/node --noEmit",
"test:unit": "vitest run -r __tests__/unit",
"test:unit:watch": "vitest -r __tests__/unit",
"test:e2e": "pnpm test:e2e-dev && pnpm test:e2e-build",
@ -96,16 +88,16 @@
"*": "prettier --experimental-cli --ignore-unknown --write"
},
"dependencies": {
"@docsearch/css": "^4.5.3",
"@docsearch/js": "^4.5.3",
"@docsearch/sidepanel-js": "^4.5.3",
"@iconify-json/simple-icons": "^1.2.69",
"@docsearch/css": "^4.5.4",
"@docsearch/js": "^4.5.4",
"@docsearch/sidepanel-js": "^4.5.4",
"@iconify-json/simple-icons": "^1.2.70",
"@shikijs/core": "^3.22.0",
"@shikijs/transformers": "^3.22.0",
"@shikijs/types": "^3.22.0",
"@types/markdown-it": "^14.1.2",
"@vitejs/plugin-vue": "^6.0.4",
"@vue/devtools-api": "^8.0.5",
"@vue/devtools-api": "^8.0.6",
"@vue/shared": "^3.5.27",
"@vueuse/core": "^14.2.0",
"@vueuse/integrations": "^14.2.0",
@ -127,11 +119,6 @@
"@mdit-vue/plugin-toc": "^3.0.2",
"@mdit-vue/shared": "^3.0.2",
"@polka/compression": "^1.0.0-next.28",
"@rollup/plugin-alias": "^6.0.0",
"@rollup/plugin-commonjs": "^29.0.0",
"@rollup/plugin-json": "^6.1.0",
"@rollup/plugin-node-resolve": "^16.0.3",
"@rollup/plugin-replace": "^6.0.3",
"@types/cross-spawn": "^6.0.6",
"@types/fs-extra": "^11.0.4",
"@types/lodash.template": "^4.5.3",
@ -140,14 +127,13 @@
"@types/markdown-it-container": "^4.0.0",
"@types/markdown-it-emoji": "^3.0.1",
"@types/minimist": "^1.2.5",
"@types/node": "^25.2.0",
"@types/node": "^25.2.2",
"@types/picomatch": "^4.0.2",
"@types/prompts": "^2.4.9",
"chokidar": "^4.0.3",
"chokidar": "^5.0.0",
"conventional-changelog": "^7.1.1",
"conventional-changelog-angular": "^8.1.0",
"cross-spawn": "^7.0.6",
"esbuild": "^0.27.2",
"execa": "^9.6.1",
"fs-extra": "^11.3.3",
"get-port": "^7.1.0",
@ -159,35 +145,33 @@
"markdown-it-anchor": "^9.2.0",
"markdown-it-async": "^2.2.0",
"markdown-it-attrs": "^4.3.1",
"markdown-it-cjk-friendly": "^2.0.1",
"markdown-it-cjk-friendly": "^2.0.2",
"markdown-it-container": "^4.0.0",
"markdown-it-emoji": "^3.0.0",
"markdown-it-mathjax3": "^4.3.2",
"minimist": "^1.2.8",
"nanoid": "^5.1.6",
"obug": "^2.1.1",
"ora": "^9.1.0",
"ora": "^9.3.0",
"oxc-minify": "^0.98.0",
"p-map": "^7.0.4",
"package-directory": "^8.2.0",
"path-to-regexp": "^6.3.0",
"picocolors": "^1.1.1",
"picomatch": "^4.0.3",
"playwright-chromium": "^1.58.1",
"playwright-chromium": "^1.58.2",
"polka": "^1.0.0-next.28",
"postcss": "^8.5.6",
"postcss-selector-parser": "^7.1.1",
"prettier": "^3.8.1",
"prompts": "^2.4.2",
"punycode": "^2.3.1",
"rollup": "^4.57.1",
"rollup-plugin-dts": "6.1.1",
"rollup-plugin-esbuild": "^6.2.1",
"semver": "^7.7.3",
"semver": "^7.7.4",
"simple-git-hooks": "^2.13.1",
"sirv": "^3.0.2",
"sitemap": "^9.0.0",
"tinyglobby": "^0.2.15",
"tsdown": "^0.20.3",
"typescript": "^5.9.3",
"vitest": "4.0.0-beta.4",
"vue-tsc": "^3.2.4",
@ -209,5 +193,5 @@
"optional": true
}
},
"packageManager": "pnpm@10.28.2"
"packageManager": "pnpm@10.29.1"
}

File diff suppressed because it is too large Load Diff

@ -10,11 +10,11 @@ onlyBuiltDependencies:
- simple-git-hooks
overrides:
ora>string-width: ^5
rolldown: latest
vite: npm:rolldown-vite@latest
patchedDependencies:
'@types/markdown-it-attrs': patches/@types__markdown-it-attrs.patch
'@types/markdown-it-attrs@4.1.3': patches/@types__markdown-it-attrs@4.1.3.patch
'@types/mdurl@2.0.0': patches/@types__mdurl@2.0.0.patch
markdown-it-anchor@9.2.0: patches/markdown-it-anchor@9.2.0.patch
markdown-it-attrs@4.3.1: patches/markdown-it-attrs@4.3.1.patch

@ -1,98 +0,0 @@
import alias from '@rollup/plugin-alias'
import commonjs from '@rollup/plugin-commonjs'
import json from '@rollup/plugin-json'
import { nodeResolve } from '@rollup/plugin-node-resolve'
import replace from '@rollup/plugin-replace'
import * as fs from 'node:fs/promises'
import { builtinModules, createRequire } from 'node:module'
import { type RollupOptions, defineConfig } from 'rollup'
import dts from 'rollup-plugin-dts'
import esbuild from 'rollup-plugin-esbuild'
const require = createRequire(import.meta.url)
const pkg = require('./package.json')
const DEV = !!process.env.DEV
const PROD = !DEV
const external = [
...Object.keys(pkg.dependencies),
...Object.keys(pkg.peerDependencies),
...builtinModules.flatMap((m) =>
m.includes('punycode') ? [] : [m, `node:${m}`]
)
]
const plugins = [
alias({ entries: { 'readable-stream': 'stream' } }),
replace({
// polyfill broken browser check from bundled deps
'navigator.userAgentData': 'undefined',
'navigator.userAgent': 'undefined',
preventAssignment: true
}),
commonjs(),
nodeResolve({ preferBuiltins: false }),
esbuild({ target: 'node20' }),
json()
]
const esmBuild: RollupOptions = {
input: ['src/node/index.ts', 'src/node/cli.ts'],
output: {
format: 'esm',
entryFileNames: `[name].js`,
chunkFileNames: 'chunk-[hash].js',
dir: 'dist/node',
sourcemap: DEV
},
external,
plugins,
onwarn(warning, warn) {
if (warning.code !== 'EVAL') warn(warning)
}
}
const typesExternal = [
...external,
/\/vitepress\/(?!(dist|node_modules|vitepress)\/).*\.d\.ts$/,
/^markdown-it(?:\/|$)/
]
const dtsNode = dts({
respectExternal: true,
tsconfig: 'src/node/tsconfig.json',
compilerOptions: { preserveSymlinks: false }
})
const nodeTypes: RollupOptions = {
input: 'src/node/index.ts',
output: {
format: 'esm',
file: 'dist/node/index.d.ts'
},
external: typesExternal,
plugins: [dtsNode]
}
const clientTypes: RollupOptions = {
input: 'dist/client-types/index.d.ts',
output: {
format: 'esm',
file: 'dist/client/index.d.ts'
},
external: typesExternal,
plugins: [
dts({ respectExternal: true }),
{
name: 'cleanup',
async closeBundle() {
if (PROD) {
await fs.rm('dist/client-types', { recursive: true })
}
}
}
]
}
export default defineConfig([esmBuild, nodeTypes, clientTypes])

@ -1,11 +0,0 @@
import { copy } from 'fs-extra'
import { globSync } from 'tinyglobby'
function toDest(file) {
return file.replace(/^src\//, 'dist/')
}
globSync(['src/client/**']).forEach((file) => {
if (/(\.ts|tsconfig\.json)$/.test(file)) return
copy(file, toDest(file))
})

@ -1,9 +0,0 @@
import { copy } from 'fs-extra'
import { globSync } from 'tinyglobby'
globSync(['src/shared/**/*.ts']).forEach(async (file) => {
await Promise.all([
copy(file, file.replace(/^src\/shared\//, 'src/node/')),
copy(file, file.replace(/^src\/shared\//, 'src/client/'))
])
})

@ -1,36 +0,0 @@
import { watch } from 'chokidar'
import { copy, remove } from 'fs-extra'
import { normalizePath } from 'vite'
function toClientAndNode(method, file) {
file = normalizePath(file)
if (method === 'copy') {
copy(file, file.replace(/^src\/shared\//, 'src/node/'))
copy(file, file.replace(/^src\/shared\//, 'src/client/'))
} else if (method === 'remove') {
remove(file.replace(/^src\/shared\//, 'src/node/'))
remove(file.replace(/^src\/shared\//, 'src/client/'))
}
}
function toDist(file) {
return normalizePath(file).replace(/^src\//, 'dist/')
}
// copy shared files to the client and node directory whenever they change.
watch('src/shared', {
ignored: (path, stats) => stats?.isFile() && !path.endsWith('.ts')
})
.on('change', (file) => toClientAndNode('copy', file))
.on('add', (file) => toClientAndNode('copy', file))
.on('unlink', (file) => toClientAndNode('remove', file))
// copy non ts files, such as an html or css, to the dist directory whenever
// they change.
watch('src/client', {
ignored: (path, stats) =>
stats?.isFile() && (path.endsWith('.ts') || path.endsWith('tsconfig.json'))
})
.on('change', (file) => copy(file, toDist(file)))
.on('add', (file) => copy(file, toDist(file)))
.on('unlink', (file) => remove(toDist(file)))

@ -5,7 +5,7 @@ const ignoredNodes = ['.vp-copy-ignore', '.diff.remove'].join(', ')
export function useCopyCode() {
if (inBrowser) {
const timeoutIdMap: WeakMap<HTMLElement, NodeJS.Timeout> = new WeakMap()
const timeoutIdMap: WeakMap<HTMLElement, number> = new WeakMap()
window.addEventListener('click', (e) => {
const el = e.target as HTMLElement
if (el.matches('div[class*="language-"] > button.copy')) {

@ -3,7 +3,7 @@ import { isExternal, treatAsHtml } from '../../shared'
import { useData } from '../composables/data'
export function throttleAndDebounce(fn: () => void, delay: number): () => void {
let timeoutId: NodeJS.Timeout
let timeoutId: number
let called = false
return () => {

@ -1,13 +1,10 @@
{
"extends": "../../tsconfig.json",
"compilerOptions": {
"baseUrl": ".",
"outDir": "../../dist/client",
"declaration": true,
"declarationDir": "../../dist/client-types",
"types": ["../../client.d.ts", "@types/node"],
"types": ["../../client.d.ts"],
"paths": {
"vitepress": ["index.ts"],
"vitepress": ["./index.ts"],
"vitepress/theme": ["../../theme.d.ts"]
}
},

@ -40,7 +40,7 @@ declare module 'vite' {
}
const themeRE = /(?:^|\/)\.vitepress\/theme\/index\.(m|c)?(j|t)s$/
const startsWithThemeRE = /^@theme(?:\/|$)/
const startsWithThemeRE = /^@theme(?:$|\/)/
const docsearchRE = /\/docsearch\.css(?:$|\?)/
const hashRE = /\.([-\w]+)\.js$/

@ -1,10 +1,8 @@
{
"extends": "../../tsconfig.json",
"compilerOptions": {
"baseUrl": ".",
"outDir": "../../dist/node",
"types": ["node"],
"sourceMap": true
"types": ["node"]
},
"include": ["."]
}

@ -230,8 +230,7 @@ const KNOWN_EXTENSIONS = new Set()
export function treatAsHtml(filename: string): boolean {
if (KNOWN_EXTENSIONS.size === 0) {
const extraExts =
(typeof process === 'object' && process.env?.VITE_EXTRA_EXTENSIONS) ||
(import.meta as any).env?.VITE_EXTRA_EXTENSIONS ||
((globalThis as any).process || import.meta).env?.VITE_EXTRA_EXTENSIONS ||
''
// md, html? are intentionally omitted

@ -1,8 +1,7 @@
{
"extends": "../../tsconfig.json",
"compilerOptions": {
"baseUrl": ".",
"lib": ["esnext", "dom", "dom.iterable"]
"types": []
},
"include": ["."]
}

@ -0,0 +1,138 @@
import { watch, type ChokidarOptions } from 'chokidar'
import fs from 'node:fs/promises'
import path from 'node:path'
import { glob } from 'tinyglobby'
import { defineConfig, type UserConfig } from 'tsdown'
const DEV = process.argv.includes('--watch') || process.argv.includes('-w')
const clientBase = path.resolve(import.meta.dirname, 'src/client')
const nodeBase = path.resolve(import.meta.dirname, 'src/node')
const sharedBase = path.resolve(import.meta.dirname, 'src/shared')
const distBase = path.resolve(import.meta.dirname, 'dist')
const distClientBase = path.resolve(import.meta.dirname, 'dist/client')
const typesExternal = [
/\/vitepress\/(?!(?:dist|node_modules|vitepress|src)\/).*\.d\.ts$/,
/^markdown-it(?:$|\/)/
]
await copyAndWatch()
const common = {
checks: { eval: false, pluginTimings: false },
clean: false,
dts: { resolver: 'tsc' },
failOnWarn: !DEV,
fixedExtension: false,
inlineOnly: false,
logLevel: 'warn',
minify: { codegen: false, compress: true, mangle: false },
nodeProtocol: true,
sourcemap: DEV,
external: (id, parentId) =>
(parentId?.endsWith('.d.ts') && typesExternal.some((re) => re.test(id))) ||
undefined
} satisfies UserConfig
export default defineConfig([
{
...common,
name: 'node',
entry: ['src/node/index.ts', 'src/node/cli.ts'],
outDir: 'dist/node',
platform: 'node',
target: 'node20',
tsconfig: 'src/node/tsconfig.json'
},
{
...common,
name: 'client',
entry: ['src/client/**/*.ts'],
outDir: 'dist/client',
platform: 'neutral',
target: ['node20', 'chrome107', 'firefox104', 'safari16'],
tsconfig: 'src/client/tsconfig.json',
external: (id, parentId) =>
id === '@localSearchIndex' ||
id === '@siteData' ||
id === '@theme/index' ||
shouldCopyFromClient(id) ||
common.external(id, parentId)
}
])
// #region Watchers
async function copyAndWatch() {
await fs.rm(distBase, { recursive: true, force: true, maxRetries: 10 })
await Promise.all([
...(await glob('**/*', { cwd: sharedBase })).map(cpShared),
...(await glob('**/*', { cwd: clientBase })).map(cpClient)
])
if (!DEV) return
const watcherOpts: ChokidarOptions = {
ignoreInitial: true,
awaitWriteFinish: { stabilityThreshold: 200, pollInterval: 50 }
}
const sharedWatcher = watch('.', {
cwd: sharedBase,
ignored: (val, stats) => !!stats?.isFile() && !shouldCopyFromShared(val),
...watcherOpts
})
.on('add', cpShared)
.on('change', cpShared)
const assetWatcher = watch('.', {
cwd: clientBase,
ignored: (val, stats) => !!stats?.isFile() && !shouldCopyFromClient(val),
...watcherOpts
})
.on('add', cpClient)
.on('change', cpClient)
.on('unlink', rmClient)
const closeAll = async () => {
await Promise.allSettled([sharedWatcher.close(), assetWatcher.close()])
}
process.once('SIGINT', () => closeAll().finally(() => process.exit(0)))
process.once('SIGTERM', () => closeAll().finally(() => process.exit(0)))
process.once('exit', () => closeAll())
}
async function cpShared(rel: string) {
if (!shouldCopyFromShared(rel)) return
const src = path.join(sharedBase, rel)
const destClient = path.join(clientBase, rel)
const destNode = path.join(nodeBase, rel)
await fs.copyFile(src, destClient)
await fs.copyFile(src, destNode)
}
async function cpClient(rel: string) {
if (!shouldCopyFromClient(rel)) return
const src = path.join(clientBase, rel)
const dest = path.join(distClientBase, rel)
await fs.mkdir(path.dirname(dest), { recursive: true })
await fs.copyFile(src, dest)
}
async function rmClient(rel: string) {
const dest = path.join(distClientBase, rel)
await fs.rm(dest, { force: true })
}
function shouldCopyFromShared(id: string) {
return id.endsWith('.ts')
}
function shouldCopyFromClient(id: string) {
return id.endsWith('.css') || id.endsWith('.vue') || id.endsWith('.woff2')
}
// #endregion
Loading…
Cancel
Save