@bndynet/vue-site 0.1.2 → 0.1.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +53 -3
- package/bin/vue-site.mjs +98 -10
- package/dist/index.es.js +3 -3
- package/dist/types.d.ts +3 -2
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -50,6 +50,14 @@ npx vue-site build
|
|
|
50
50
|
npx vue-site preview
|
|
51
51
|
```
|
|
52
52
|
|
|
53
|
+
Subpath deploy: pass Vite’s public base on the CLI (overrides `env.vite.base` in `site.config`):
|
|
54
|
+
|
|
55
|
+
```bash
|
|
56
|
+
npx vue-site build --base=/app/
|
|
57
|
+
# or
|
|
58
|
+
npx vue-site build --base /app/
|
|
59
|
+
```
|
|
60
|
+
|
|
53
61
|
Add `"dev": "vue-site dev"` (or `vs dev`) in `package.json` scripts if you like.
|
|
54
62
|
|
|
55
63
|
## Config reference
|
|
@@ -68,7 +76,7 @@ Add `"dev": "vue-site dev"` (or `vs dev`) in `package.json` scripts if you like.
|
|
|
68
76
|
| `packageRepository` | Usually set by CLI from `package.json`; omit when using `createSiteApp` alone |
|
|
69
77
|
| `env` | Dev/build options — see below |
|
|
70
78
|
| `bootstrap` | Optional path from site root (e.g. `./bootstrap.ts`) — module loaded once before the Vue app |
|
|
71
|
-
| `configureApp` | Optional `(app) => void
|
|
79
|
+
| `configureApp` | Optional `(app) => void \| Promise<void>` after router install, before `mount` (see [Local packages in `configureApp`](#local-packages-in-configureapp)) |
|
|
72
80
|
|
|
73
81
|
### `NavItem`
|
|
74
82
|
|
|
@@ -96,9 +104,36 @@ Add `"dev": "vue-site dev"` (or `vs dev`) in `package.json` scripts if you like.
|
|
|
96
104
|
| `port` | Dev server port |
|
|
97
105
|
| `outDir` | Build output (relative to site root; default `{folder}-dist`) |
|
|
98
106
|
| `customElements` | Tag prefixes for custom elements (e.g. `['chat-', 'i-']`) |
|
|
99
|
-
| `watchPackages` | Local packages
|
|
107
|
+
| `watchPackages` | Local packages — see [env.watchPackages](#envwatchpackages) |
|
|
100
108
|
| `vite` | Vite overrides (not `root`); framework merges aliases, `server.fs.allow`, `build.outDir`, etc. |
|
|
101
109
|
|
|
110
|
+
### `env.watchPackages`
|
|
111
|
+
|
|
112
|
+
- **String** — package name only (e.g. workspace symlink / `npm link`). Dependency pre-bundling is skipped; file watching follows Vite defaults.
|
|
113
|
+
- **`{ name, entryPath }`** — `name` must match the import specifier (e.g. `@scope/pkg`). `entryPath` is **relative to the directory where you run the CLI** (the folder that contains `site.config.*`). Vite resolves that package to your **source entry** for dev HMR and adds the package directory to `server.fs.allow`.
|
|
114
|
+
- If you use **`env.vite.resolve.alias` as an array** (`{ find, replacement }[]`), the CLI still merges `watchPackages` aliases correctly (object-only spread would break this).
|
|
115
|
+
- **Do not** add a **top-level value import** of the same package in `site.config.ts` if it is listed here — the config preload runs in Node and would resolve `node_modules`, while the app uses Vite. Use **`configureApp` + dynamic `import()`** instead (see next section).
|
|
116
|
+
|
|
117
|
+
### Local packages in `configureApp`
|
|
118
|
+
|
|
119
|
+
`configureApp` may be **`async`** so you can `await import('your-package')` after the router is installed. That dynamic import runs in the browser under Vite, so it respects `watchPackages` and does not run during CLI config loading.
|
|
120
|
+
|
|
121
|
+
```typescript
|
|
122
|
+
export default defineConfig({
|
|
123
|
+
env: {
|
|
124
|
+
watchPackages: [{ name: '@acme/widgets', entryPath: '../widgets/src/index.ts' }],
|
|
125
|
+
},
|
|
126
|
+
async configureApp(app) {
|
|
127
|
+
const w = await import('@acme/widgets')
|
|
128
|
+
w.register(app)
|
|
129
|
+
},
|
|
130
|
+
})
|
|
131
|
+
```
|
|
132
|
+
|
|
133
|
+
### Dev server filesystem access
|
|
134
|
+
|
|
135
|
+
The CLI allows `server.fs` reads under the site root, the installed `vue-site` package directory, the **parent** of the site root (for `../…` imports), and — when it would not widen to the filesystem root — the **grandparent** (common in monorepos, e.g. `../../packages/...`). Add more paths with `env.vite.server.fs.allow` if needed. Entries from `watchPackages` with `{ entryPath }` also extend `fs.allow` for those package trees.
|
|
136
|
+
|
|
102
137
|
## Library mode
|
|
103
138
|
|
|
104
139
|
Own `index.html` + Vite setup:
|
|
@@ -112,7 +147,7 @@ const app = await createSiteApp(config)
|
|
|
112
147
|
app.mount('#app')
|
|
113
148
|
```
|
|
114
149
|
|
|
115
|
-
Use a top-level `await` in your entry (or an async IIFE): `createSiteApp` is async
|
|
150
|
+
Use a top-level `await` in your entry (or an async IIFE): `createSiteApp` is async and **awaits** `configureApp` when it returns a `Promise`. If you set optional `bootstrap` in config, that module loads before the app is created; if you omit `bootstrap`, that step is skipped.
|
|
116
151
|
|
|
117
152
|
Exports: `createSiteApp`, `defineConfig`, `useTheme`, `useSiteConfig`, `themeRefKey`. Types: `SiteConfig`, `SiteEnvConfig`, `SiteViteConfig`, `SiteExternalLink`, `NavItem`, `ThemeConfig`, `ThemeOption`, `ThemePaletteVars`, `ResolvedNavItem`.
|
|
118
153
|
|
|
@@ -156,6 +191,21 @@ npm run dev # watch-build lib + example site
|
|
|
156
191
|
npm run build # `dist/` + `example/example-dist`
|
|
157
192
|
```
|
|
158
193
|
|
|
194
|
+
### Using a local build in another project
|
|
195
|
+
|
|
196
|
+
The published entry points at `dist/`. After changing library **source** under `src/`, run `npm run build:lib` (or `build:lib:watch`) before the consumer sees updates. Changes to **`bin/vue-site.mjs`** apply on the next `vue-site` run without a lib rebuild.
|
|
197
|
+
|
|
198
|
+
```bash
|
|
199
|
+
cd /path/to/vue-site
|
|
200
|
+
npm install && npm run build:lib
|
|
201
|
+
npm link
|
|
202
|
+
|
|
203
|
+
cd /path/to/consumer
|
|
204
|
+
npm link @bndynet/vue-site
|
|
205
|
+
```
|
|
206
|
+
|
|
207
|
+
You do not need to run `npm link` again after editing files; the symlink stays. Use `npm unlink @bndynet/vue-site` and `npm install` in the consumer when done.
|
|
208
|
+
|
|
159
209
|
## License
|
|
160
210
|
|
|
161
211
|
MIT
|
package/bin/vue-site.mjs
CHANGED
|
@@ -20,7 +20,66 @@ function resolvePkgDir(pkg) {
|
|
|
20
20
|
const vuePath = resolvePkgDir('vue')
|
|
21
21
|
const vueRouterPath = resolvePkgDir('vue-router')
|
|
22
22
|
const cwd = process.cwd()
|
|
23
|
-
|
|
23
|
+
/** Lets `import('../file.md?raw')` work when `site.config` lives in a subfolder (README next to cwd). In-repo, ../ often falls under pkgDir; from npm install it does not, so we allow cwd's parent explicitly. */
|
|
24
|
+
const cwdParent = resolve(cwd, '..')
|
|
25
|
+
/** Two levels up: monorepos (`apps/docs` importing `../../packages/...`). Omitted when that would be the FS root (too permissive for dev). */
|
|
26
|
+
const cwdGrandparent = resolve(cwd, '../..')
|
|
27
|
+
|
|
28
|
+
/**
|
|
29
|
+
* @param {string[]} argv
|
|
30
|
+
* @returns {{ command: string, cliBase?: string }}
|
|
31
|
+
*/
|
|
32
|
+
function parseCliArgv(argv = process.argv) {
|
|
33
|
+
const sub = argv[2]
|
|
34
|
+
const command =
|
|
35
|
+
sub && !sub.startsWith('-')
|
|
36
|
+
? sub
|
|
37
|
+
: 'dev'
|
|
38
|
+
|
|
39
|
+
let cliBase
|
|
40
|
+
const flagStart = command === sub && sub ? 3 : 2
|
|
41
|
+
for (let i = flagStart; i < argv.length; i++) {
|
|
42
|
+
const a = argv[i]
|
|
43
|
+
if (a === '--base') {
|
|
44
|
+
const v = argv[i + 1]
|
|
45
|
+
if (!v || v.startsWith('-')) {
|
|
46
|
+
console.error(
|
|
47
|
+
'[vue-site] --base requires a value (e.g. --base=/app/ or --base /app/)',
|
|
48
|
+
)
|
|
49
|
+
process.exit(1)
|
|
50
|
+
}
|
|
51
|
+
cliBase = v
|
|
52
|
+
i++
|
|
53
|
+
} else if (a.startsWith('--base=')) {
|
|
54
|
+
const v = a.slice('--base='.length)
|
|
55
|
+
if (!v) {
|
|
56
|
+
console.error(
|
|
57
|
+
'[vue-site] --base= requires a value (e.g. --base=/app/)',
|
|
58
|
+
)
|
|
59
|
+
process.exit(1)
|
|
60
|
+
}
|
|
61
|
+
cliBase = v
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
return { command, cliBase }
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
function isLikelyFilesystemRoot(dir) {
|
|
68
|
+
if (dir === '/' || dir === '//') return true
|
|
69
|
+
if (process.platform === 'win32') {
|
|
70
|
+
return /^[a-zA-Z]:[\\/]$/i.test(dir)
|
|
71
|
+
}
|
|
72
|
+
return false
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
const defaultServerFsAllow = [cwd, pkgDir, cwdParent]
|
|
76
|
+
if (
|
|
77
|
+
cwdGrandparent !== cwdParent &&
|
|
78
|
+
cwdGrandparent !== cwd &&
|
|
79
|
+
!isLikelyFilesystemRoot(cwdGrandparent)
|
|
80
|
+
) {
|
|
81
|
+
defaultServerFsAllow.push(cwdGrandparent)
|
|
82
|
+
}
|
|
24
83
|
|
|
25
84
|
const configCandidates = [
|
|
26
85
|
'site.config.ts',
|
|
@@ -194,15 +253,20 @@ function vueSitePlugin() {
|
|
|
194
253
|
]
|
|
195
254
|
}
|
|
196
255
|
|
|
197
|
-
async function buildViteConfig() {
|
|
256
|
+
async function buildViteConfig(options = {}) {
|
|
257
|
+
const { cliBase } = options
|
|
198
258
|
const siteConfig = await loadSiteConfig()
|
|
259
|
+
const env = siteConfig.env || {}
|
|
199
260
|
const {
|
|
200
261
|
port,
|
|
201
262
|
outDir,
|
|
202
263
|
customElements = [],
|
|
203
|
-
watchPackages = [],
|
|
204
264
|
vite: userVite = {},
|
|
205
|
-
} =
|
|
265
|
+
} = env
|
|
266
|
+
const watchPackages =
|
|
267
|
+
env.watchPackages !== undefined
|
|
268
|
+
? env.watchPackages
|
|
269
|
+
: siteConfig.watchPackages ?? []
|
|
206
270
|
const { vue: userVueOpts = {}, plugins: userPlugins, ...userViteRest } =
|
|
207
271
|
userVite
|
|
208
272
|
|
|
@@ -230,10 +294,16 @@ async function buildViteConfig() {
|
|
|
230
294
|
watchPatterns.push(`!**/node_modules/${pkg}/**`)
|
|
231
295
|
} else {
|
|
232
296
|
const entryAbs = resolve(cwd, pkg.entryPath)
|
|
233
|
-
const entryDir = entryAbs
|
|
297
|
+
const entryDir = dirname(entryAbs)
|
|
298
|
+
if (!fs.existsSync(entryAbs)) {
|
|
299
|
+
console.warn(
|
|
300
|
+
`[vue-site] env.watchPackages: entry not found (entryPath is relative to the directory where you run the CLI):\n ${entryAbs}\n package: ${pkg.name}`,
|
|
301
|
+
)
|
|
302
|
+
}
|
|
234
303
|
excludeNames.push(pkg.name)
|
|
235
304
|
localAliases[pkg.name] = entryAbs
|
|
236
|
-
|
|
305
|
+
const dirForGlob = entryDir.replace(/\\/g, '/')
|
|
306
|
+
watchPatterns.push(`!${dirForGlob}/**`)
|
|
237
307
|
fsAllowPaths.push(entryDir)
|
|
238
308
|
}
|
|
239
309
|
}
|
|
@@ -256,9 +326,22 @@ async function buildViteConfig() {
|
|
|
256
326
|
},
|
|
257
327
|
}
|
|
258
328
|
if (Object.keys(localAliases).length) {
|
|
329
|
+
const prevAlias = userViteRest.resolve?.alias
|
|
330
|
+
const extraPairs = Object.entries(localAliases).map(([find, replacement]) => ({
|
|
331
|
+
find,
|
|
332
|
+
replacement,
|
|
333
|
+
}))
|
|
334
|
+
let mergedAlias
|
|
335
|
+
if (prevAlias == null) {
|
|
336
|
+
mergedAlias = { ...localAliases }
|
|
337
|
+
} else if (Array.isArray(prevAlias)) {
|
|
338
|
+
mergedAlias = [...prevAlias, ...extraPairs]
|
|
339
|
+
} else {
|
|
340
|
+
mergedAlias = { ...prevAlias, ...localAliases }
|
|
341
|
+
}
|
|
259
342
|
userViteRest.resolve = {
|
|
260
343
|
...userViteRest.resolve,
|
|
261
|
-
alias:
|
|
344
|
+
alias: mergedAlias,
|
|
262
345
|
}
|
|
263
346
|
}
|
|
264
347
|
if (fsAllowPaths.length) {
|
|
@@ -288,20 +371,22 @@ async function buildViteConfig() {
|
|
|
288
371
|
open: true,
|
|
289
372
|
...(port != null && { port }),
|
|
290
373
|
fs: {
|
|
291
|
-
allow:
|
|
374
|
+
allow: defaultServerFsAllow,
|
|
292
375
|
},
|
|
293
376
|
},
|
|
294
377
|
build: {
|
|
295
378
|
outDir: resolve(cwd, outDir || `${basename(cwd)}-dist`),
|
|
296
379
|
emptyOutDir: true,
|
|
297
380
|
},
|
|
381
|
+
...(cliBase != null && { base: cliBase }),
|
|
298
382
|
}
|
|
299
383
|
|
|
300
384
|
return mergeConfig(userViteRest, baseConfig)
|
|
301
385
|
}
|
|
302
386
|
|
|
303
387
|
async function run() {
|
|
304
|
-
const
|
|
388
|
+
const { command, cliBase } = parseCliArgv()
|
|
389
|
+
const viteConfig = await buildViteConfig({ cliBase })
|
|
305
390
|
|
|
306
391
|
if (command === 'dev') {
|
|
307
392
|
const server = await createServer(viteConfig)
|
|
@@ -350,7 +435,10 @@ import { repositoryUrl } from '${VIRTUAL_PACKAGE}'
|
|
|
350
435
|
)
|
|
351
436
|
server.printUrls()
|
|
352
437
|
} else {
|
|
353
|
-
console.log(
|
|
438
|
+
console.log(
|
|
439
|
+
'Usage: vue-site|vs <dev|build|preview> [--base=<path>]\n' +
|
|
440
|
+
' --base Public path for assets (overrides env.vite.base); e.g. --base=/app/',
|
|
441
|
+
)
|
|
354
442
|
process.exit(1)
|
|
355
443
|
}
|
|
356
444
|
}
|
package/dist/index.es.js
CHANGED
|
@@ -38138,9 +38138,9 @@ async function sA(e) {
|
|
|
38138
38138
|
await import(lA(String(e.bootstrap)));
|
|
38139
38139
|
}
|
|
38140
38140
|
async function fA(e) {
|
|
38141
|
-
var d, h, s, y
|
|
38141
|
+
var d, h, s, y;
|
|
38142
38142
|
await sA(e);
|
|
38143
|
-
const a = GI(e.nav), c = fS(a), o = ["light", "dark", ...((h = (d = e.theme) == null ? void 0 : d.extraThemes) == null ? void 0 : h.filter((
|
|
38143
|
+
const a = GI(e.nav), c = fS(a), o = ["light", "dark", ...((h = (d = e.theme) == null ? void 0 : d.extraThemes) == null ? void 0 : h.filter((f) => f.id !== "light" && f.id !== "dark").map((f) => f.id)) ?? []], i = bS(e.theme), u = me("light");
|
|
38144
38144
|
mS(
|
|
38145
38145
|
u,
|
|
38146
38146
|
((s = e.theme) == null ? void 0 : s.default) ?? "light",
|
|
@@ -38149,7 +38149,7 @@ async function fA(e) {
|
|
|
38149
38149
|
(y = e.theme) == null ? void 0 : y.colors
|
|
38150
38150
|
), document.title = e.title;
|
|
38151
38151
|
const r = tL(hA);
|
|
38152
|
-
return r.provide(XI, u), r.provide(dI, { config: e, resolvedNav: a }), r.use(c),
|
|
38152
|
+
return r.provide(XI, u), r.provide(dI, { config: e, resolvedNav: a }), r.use(c), e.configureApp && await Promise.resolve(e.configureApp(r)), r;
|
|
38153
38153
|
}
|
|
38154
38154
|
function MA(e) {
|
|
38155
38155
|
return e;
|
package/dist/types.d.ts
CHANGED
|
@@ -65,7 +65,7 @@ export interface SiteEnvConfig {
|
|
|
65
65
|
/**
|
|
66
66
|
* Local packages to watch for source changes and exclude from pre-bundling.
|
|
67
67
|
* - `string` -- symlinked package name (npm workspaces / npm link)
|
|
68
|
-
* - `{ name, entryPath }` -- resolve imports to a source entry file so Vite compiles it directly (
|
|
68
|
+
* - `{ name, entryPath }` -- resolve imports to a source entry file so Vite compiles it directly; `entryPath` is relative to the directory where you run `vue-site` (the folder that contains `site.config.*`)
|
|
69
69
|
*/
|
|
70
70
|
watchPackages?: (string | {
|
|
71
71
|
name: string;
|
|
@@ -107,8 +107,9 @@ export interface SiteConfig {
|
|
|
107
107
|
/**
|
|
108
108
|
* Called after the app is created, context is provided, and the router is installed — before
|
|
109
109
|
* `createSiteApp` resolves (call `.mount()` after `await`). Use for `app.use()`, global directives, etc.
|
|
110
|
+
* May return a Promise (e.g. after `await import()` of a package listed in `env.watchPackages`).
|
|
110
111
|
*/
|
|
111
|
-
configureApp?: (app: App) => void
|
|
112
|
+
configureApp?: (app: App) => void | Promise<void>;
|
|
112
113
|
}
|
|
113
114
|
export interface ResolvedNavItem extends NavItem {
|
|
114
115
|
resolvedPath: string;
|