@lyda/kilo-ui 0.1.0 → 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 CHANGED
@@ -8,30 +8,28 @@ This package does **not** work like a normal UI runtime dependency. It works lik
8
8
 
9
9
  From any Vue project:
10
10
 
11
- ```bash
12
- npm install -D "C:\UI Library"
13
- npx kilo-ui init
14
- npx kilo-ui add data-table app-navbar activity-log
15
- ```
16
-
17
- After you **publish** this project to npm, install the **exact** `name` from its `package.json` (for example `@ui-library/kilo-ui`).
11
+ After you **publish** this project to npm, install the **exact** `name` from its `package.json` (for example `@lyda/kilo-ui`).
18
12
  **Do not** run `npm install -D kilo-ui` expecting this Vue CLI — the public npm name `kilo-ui` is already used by a different project.
19
13
 
20
14
  ```bash
21
- npm install -D @ui-library/kilo-ui
22
- npx kilo-ui init
15
+ npm install -D @lyda/kilo-ui
23
16
  npx kilo-ui add data-table
24
17
  ```
25
18
 
19
+ **First install in a new project:** the package **postinstall** runs `kilo-ui init` once (unless `kilo.config.ts` already exists). That creates **`kilo.config.ts` in your app root** (next to `package.json`) — not inside `node_modules`. Edit it for **aliases**, **`ui.componentsDir`** (folder prefix under `src/components`, default `ui`), and **Tailwind CSS path**. An annotated example ships with the library at **`node_modules/@lyda/kilo-ui/config/kilo.config.example.ts`**. If install used **`--ignore-scripts`**, run **`npx kilo-ui init`** once yourself.
20
+
21
+ You can still run **`npx kilo-ui init`** anytime to add missing scaffold files; use **`init --force`** to reset **`kilo.config.ts`** to defaults (back up first if you customized it).
22
+
26
23
  **Note:** The public npm name `kilo-ui` may point to a different project (not this Vue CLI). If `npm install -D kilo-ui` pulls SvelteKit or other wrong peers, use a scoped name or install from `file:` / Git. See [Installation](docs/docs/installation.md) in the docs site.
27
24
 
28
25
  ## What `init` Creates
29
26
 
30
27
  `npx kilo-ui init` creates:
31
28
 
32
- - `components.json` - config and aliases
29
+ - **`kilo.config.ts`** - TypeScript project config (`defineConfig` from `@lyda/kilo-ui/config`), aliases, and **`ui.componentsDir`** (subfolder for installed components, default `ui`)
33
30
  - `src/styles/teamwork-ui.css` - Tailwind v4 import + Kilo UI theme tokens
34
31
  - `src/lib/utils.ts` - shared helper utilities
32
+ - `env.d.ts` (project root) - Vue + Vite TypeScript declarations for `*.vue` modules (skip if the file already exists); `init` also updates `tsconfig.app.json` / `tsconfig.json` with `paths` for `@/*` when possible
35
33
 
36
34
  Add the stylesheet once in your app entry, usually `src/main.ts`:
37
35
 
@@ -159,7 +157,7 @@ Editing a component? Update the file in `registry/`. The CLI and docs both pick
159
157
  5. Consumers install with:
160
158
 
161
159
  ```bash
162
- npm install -D @ui-library/kilo-ui
160
+ npm install -D @lyda/kilo-ui
163
161
  npx kilo-ui init
164
162
  npx kilo-ui add data-table
165
163
  ```
package/bin/kilo-ui.mjs CHANGED
@@ -1,4 +1,5 @@
1
1
  #!/usr/bin/env node
2
+ import { createJiti } from 'jiti'
2
3
  import { existsSync, mkdirSync, readFileSync, writeFileSync } from 'node:fs'
3
4
  import { dirname, join, relative, resolve } from 'node:path'
4
5
  import { fileURLToPath } from 'node:url'
@@ -6,15 +7,24 @@ import { fileURLToPath } from 'node:url'
6
7
  const __dirname = dirname(fileURLToPath(import.meta.url))
7
8
  const packageRoot = resolve(__dirname, '..')
8
9
  const registryRoot = join(packageRoot, 'registry')
10
+ const cliEntry = fileURLToPath(import.meta.url)
9
11
 
10
12
  const pkg = JSON.parse(readFileSync(join(packageRoot, 'package.json'), 'utf8'))
11
13
  const cliName = typeof pkg.name === 'string' ? pkg.name : 'kilo-ui'
14
+ const pkgName = cliName
12
15
 
13
16
  const commands = new Set(['init', 'add', 'list', 'help'])
14
17
  const [, , maybeCommand, ...args] = process.argv
15
18
  const command = commands.has(maybeCommand) ? maybeCommand : 'help'
16
19
 
17
- const configFile = 'components.json'
20
+ const KILO_TS = 'kilo.config.ts'
21
+ const KILO_MTS = 'kilo.config.mts'
22
+ const KILO_JS = 'kilo.config.js'
23
+ const KILO_MJS = 'kilo.config.mjs'
24
+ const CONFIG_MODULES = [KILO_TS, KILO_MTS, KILO_JS, KILO_MJS]
25
+
26
+ const UI_JSON = 'ui.json'
27
+ const LEGACY_JSON = 'components.json'
18
28
 
19
29
  function log(message = '') {
20
30
  console.log(message)
@@ -26,7 +36,8 @@ function fail(message) {
26
36
  }
27
37
 
28
38
  function readJson(path) {
29
- return JSON.parse(readFileSync(path, 'utf8'))
39
+ const raw = readFileSync(path, 'utf8').replace(/^\uFEFF/, '')
40
+ return JSON.parse(raw)
30
41
  }
31
42
 
32
43
  function writeJson(path, value) {
@@ -51,17 +62,82 @@ function registry() {
51
62
  return readJson(join(registryRoot, 'index.json'))
52
63
  }
53
64
 
65
+ const defaultAliases = {
66
+ components: '@/components',
67
+ composables: '@/composables',
68
+ lib: '@/lib',
69
+ types: '@/types',
70
+ }
71
+
72
+ function normalizeConfig(raw) {
73
+ const c = typeof raw === 'object' && raw !== null ? { ...raw } : {}
74
+ c.srcDir = c.srcDir || 'src'
75
+ c.aliases = { ...defaultAliases, ...(c.aliases || {}) }
76
+ c.tailwind = c.tailwind || { css: `${c.srcDir}/styles/teamwork-ui.css` }
77
+ const uiRaw =
78
+ typeof c.ui === 'object' && c.ui !== null ? { ...c.ui } : {}
79
+ const componentsPrefix = uiRaw.componentsPrefix
80
+ delete uiRaw.componentsPrefix
81
+ c.ui = { componentsDir: 'ui', ...uiRaw }
82
+ if (
83
+ (c.ui.componentsDir === undefined || c.ui.componentsDir === null) &&
84
+ componentsPrefix !== undefined &&
85
+ componentsPrefix !== null
86
+ ) {
87
+ c.ui.componentsDir = componentsPrefix
88
+ }
89
+ if (c.ui.componentsDir === undefined || c.ui.componentsDir === null) {
90
+ c.ui.componentsDir = 'ui'
91
+ }
92
+ return c
93
+ }
94
+
95
+ function hasKiloModuleConfig(cwd) {
96
+ return CONFIG_MODULES.some((name) => existsSync(join(cwd, name)))
97
+ }
98
+
99
+ function loadProjectConfigFromDisk(cwd) {
100
+ const jiti = createJiti(cliEntry, { interopDefault: true, cwd })
101
+
102
+ for (const name of CONFIG_MODULES) {
103
+ const p = join(cwd, name)
104
+ if (!existsSync(p)) continue
105
+ try {
106
+ const mod = jiti(p)
107
+ const raw = mod?.default ?? mod
108
+ if (!raw || typeof raw !== 'object') {
109
+ fail(`${name} must default-export a config object.`)
110
+ }
111
+ return normalizeConfig(raw)
112
+ } catch (e) {
113
+ const msg = e instanceof Error ? e.message : String(e)
114
+ fail(`Failed to load ${name}: ${msg}`)
115
+ }
116
+ }
117
+
118
+ const uiPath = join(cwd, UI_JSON)
119
+ if (existsSync(uiPath)) return normalizeConfig(readJson(uiPath))
120
+
121
+ const legacyPath = join(cwd, LEGACY_JSON)
122
+ if (existsSync(legacyPath)) return normalizeConfig(readJson(legacyPath))
123
+
124
+ return null
125
+ }
126
+
54
127
  function projectConfig() {
55
- const path = join(process.cwd(), configFile)
56
- if (!existsSync(path)) {
57
- fail(`Missing ${configFile}. Run "npx ${cliName} init" first.`)
128
+ const cwd = process.cwd()
129
+ const config = loadProjectConfigFromDisk(cwd)
130
+ if (!config) {
131
+ fail(
132
+ `Missing kilo.config.ts (or kilo.config.mjs, ${UI_JSON}, ${LEGACY_JSON}). Run "npx ${cliName} init" first.`,
133
+ )
58
134
  }
59
- return readJson(path)
135
+ return config
60
136
  }
61
137
 
62
138
  function aliasPath(config, key) {
63
139
  const value = config.aliases?.[key]
64
- if (!value) fail(`Missing aliases.${key} in ${configFile}`)
140
+ if (!value) fail(`Missing aliases.${key} in kilo.config / ${UI_JSON} / ${LEGACY_JSON}`)
65
141
  return value.replace(/^@\//, config.srcDir ? `${config.srcDir}/` : 'src/')
66
142
  }
67
143
 
@@ -69,8 +145,22 @@ function resolveTarget(config, alias, fileName) {
69
145
  return join(process.cwd(), aliasPath(config, alias), fileName)
70
146
  }
71
147
 
148
+ /** Path segments under the components alias (e.g. ["ui"] → …/components/ui/…). Empty string = no extra folder. */
149
+ function componentDirSegments(config) {
150
+ const dir = config.ui?.componentsDir
151
+ if (dir === '') return []
152
+ if (dir === undefined) return ['ui']
153
+ return String(dir).replace(/\\/g, '/').split('/').filter(Boolean)
154
+ }
155
+
72
156
  function componentFilePath(config, componentName, fileName) {
73
- return join(process.cwd(), aliasPath(config, 'components'), 'ui', componentName, fileName)
157
+ return join(
158
+ process.cwd(),
159
+ aliasPath(config, 'components'),
160
+ ...componentDirSegments(config),
161
+ componentName,
162
+ fileName,
163
+ )
74
164
  }
75
165
 
76
166
  function copyRegistryFile(sourceRelative, targetPath, config, force) {
@@ -84,13 +174,105 @@ function copyRegistryFile(sourceRelative, targetPath, config, force) {
84
174
  writeFile(targetPath, content, force)
85
175
  }
86
176
 
177
+ /**
178
+ * Vite resolves `@` from vite.config; TypeScript needs matching paths or `@/…` imports fail in the editor / vue-tsc.
179
+ * Vue templates usually keep env.d.ts at the project root next to tsconfig.app.json (not under src/).
180
+ */
181
+ function kiloConfigSerializable(config) {
182
+ const n = normalizeConfig(config)
183
+ return {
184
+ style: n.style ?? 'default',
185
+ srcDir: n.srcDir,
186
+ ui: n.ui,
187
+ tailwind: n.tailwind,
188
+ aliases: n.aliases,
189
+ }
190
+ }
191
+
192
+ function buildKiloConfigFileContent(config) {
193
+ const obj = kiloConfigSerializable(config)
194
+ const body = JSON.stringify(obj, null, 2)
195
+ const header = `// Kilo UI — app config (generated in your project root by ${pkgName}, not inside the library package)\n// ui.componentsDir = folder prefix under aliases.components (default "ui" → …/components/ui/<component>/)\n// Use "" for no prefix: …/components/<component>/\n\n`
196
+ return `${header}import { defineConfig } from '${pkgName}/config'\n\nexport default defineConfig(${body})\n`
197
+ }
198
+
199
+ /** Create kilo.config.ts when missing, or overwrite when force (unless a non-.ts kilo module is the only config). */
200
+ function writeKiloConfigTs(cwd, config, force) {
201
+ const kiloPath = join(cwd, KILO_TS)
202
+ if (hasKiloModuleConfig(cwd) && !force) return
203
+ if (!force && existsSync(kiloPath)) return
204
+
205
+ const rel = relative(cwd, kiloPath)
206
+ const existed = existsSync(kiloPath)
207
+ ensureDir(dirname(kiloPath))
208
+ writeFileSync(kiloPath, buildKiloConfigFileContent(config), 'utf8')
209
+ log(`${force || existed ? 'write' : 'add'} ${rel}`)
210
+ }
211
+
212
+ function mergeTsconfigForAliases(cwd, srcDir = 'src') {
213
+ const srcNorm = String(srcDir || 'src').replace(/\\/g, '/').replace(/\/$/, '') || 'src'
214
+ const pathPattern = `./${srcNorm}/*`
215
+ const appPath = join(cwd, 'tsconfig.app.json')
216
+ const rootPath = join(cwd, 'tsconfig.json')
217
+
218
+ function tryMerge(filePath) {
219
+ if (!existsSync(filePath)) return false
220
+ let parsed
221
+ try {
222
+ parsed = readJson(filePath)
223
+ } catch {
224
+ log(`skip ${relative(cwd, filePath)} (invalid JSON — fix or add paths manually)`)
225
+ return false
226
+ }
227
+ const relName = relative(cwd, filePath)
228
+ if (relName === 'tsconfig.json' && parsed.references?.length && !parsed.compilerOptions) {
229
+ return false
230
+ }
231
+ parsed.compilerOptions = parsed.compilerOptions || {}
232
+ const co = parsed.compilerOptions
233
+ const paths = { ...(co.paths || {}) }
234
+ const key = '@/*'
235
+ if (paths[key]?.[0] === pathPattern) {
236
+ log(`skip ${relName} (paths "@/*" already set)`)
237
+ return true
238
+ }
239
+ if (paths[key]?.length) {
240
+ log(
241
+ `skip ${relName} (paths "@/*" already defined — ensure it points at your ${srcNorm}/ folder for kilo-ui imports)`,
242
+ )
243
+ return true
244
+ }
245
+ paths[key] = [pathPattern]
246
+ co.paths = paths
247
+ if (co.baseUrl === undefined) co.baseUrl = '.'
248
+
249
+ if (Array.isArray(parsed.include)) {
250
+ const hasEnv = parsed.include.some((entry) => String(entry).includes('env.d.ts'))
251
+ if (!hasEnv) parsed.include.unshift('env.d.ts')
252
+ }
253
+
254
+ writeJson(filePath, parsed)
255
+ log(`update ${relName} (TypeScript paths for @ + env.d.ts in include)`)
256
+ return true
257
+ }
258
+
259
+ if (tryMerge(appPath)) return
260
+ if (tryMerge(rootPath)) return
261
+
262
+ log('\nTip: Add TypeScript paths so editors resolve @ imports (same folder as vite alias):')
263
+ log(` "compilerOptions": { "baseUrl": ".", "paths": { "@/*": ["${pathPattern}"] } }`)
264
+ }
265
+
87
266
  function init(args) {
88
267
  const force = args.includes('--force')
89
- const configPath = join(process.cwd(), configFile)
90
- const defaultConfig = {
91
- $schema: 'https://kilo-ui.local/schema.json',
268
+ const cwd = process.cwd()
269
+ const uiPath = join(cwd, UI_JSON)
270
+ const legacyPath = join(cwd, LEGACY_JSON)
271
+
272
+ const defaultConfig = normalizeConfig({
92
273
  style: 'default',
93
274
  srcDir: 'src',
275
+ ui: { componentsDir: 'ui' },
94
276
  tailwind: {
95
277
  css: 'src/styles/teamwork-ui.css',
96
278
  },
@@ -100,23 +282,43 @@ function init(args) {
100
282
  lib: '@/lib',
101
283
  types: '@/types',
102
284
  },
103
- }
104
- const config = existsSync(configPath) && !force ? readJson(configPath) : defaultConfig
285
+ })
286
+
287
+ let config
105
288
 
106
- if (existsSync(configPath) && !force) {
107
- log(`skip ${configFile} (already exists)`)
289
+ if (!force) {
290
+ if (hasKiloModuleConfig(cwd)) {
291
+ config = loadProjectConfigFromDisk(cwd)
292
+ if (!config) fail('Could not read kilo config.')
293
+ log(`skip kilo.config.* (already exists)`)
294
+ } else if (existsSync(uiPath)) {
295
+ config = normalizeConfig(readJson(uiPath))
296
+ log(`using ${UI_JSON} (legacy). Prefer ${KILO_TS} — run init on a fresh branch or add the file from docs.`)
297
+ } else if (existsSync(legacyPath)) {
298
+ config = normalizeConfig(readJson(legacyPath))
299
+ log(`using ${LEGACY_JSON} (legacy fields). Adding ${KILO_TS} if missing.`)
300
+ } else {
301
+ config = defaultConfig
302
+ }
108
303
  } else {
109
- writeJson(configPath, config)
110
- log(`write ${configFile}`)
304
+ config = defaultConfig
111
305
  }
112
306
 
307
+ writeKiloConfigTs(cwd, config, force)
308
+
113
309
  copyRegistryFile('styles/teamwork-ui.css', join(process.cwd(), config.tailwind.css), config, force)
114
310
  copyRegistryFile('lib/utils.ts', resolveTarget(config, 'lib', 'utils.ts'), config, force)
311
+ copyRegistryFile('vue/env.d.ts', join(process.cwd(), 'env.d.ts'), config, force)
312
+
313
+ mergeTsconfigForAliases(process.cwd(), config.srcDir || 'src')
115
314
 
315
+ const sub = componentDirSegments(config).join('/') || '(components root)'
116
316
  log('\nDone. Add this once in your app entry or main stylesheet:')
117
317
  log(` import './styles/${config.tailwind.css.replace(/^.*\//, '')}'`)
318
+ log(`\nComponents install under: ${aliasPath(config, 'components').replace(/\\/g, '/')}/${sub}/<name>/`)
118
319
  log('\nThen add components:')
119
320
  log(` npx ${cliName} add data-table app-navbar activity-log`)
321
+ log(`\nEdit ${KILO_TS} to change where components install (aliases, ui.componentsDir).`)
120
322
  }
121
323
 
122
324
  function add(args) {
@@ -163,6 +365,8 @@ Usage:
163
365
  npx ${cliName} add <component...> [--force]
164
366
  npx ${cliName} list
165
367
 
368
+ Config: ${KILO_TS} (or ${KILO_MJS}, legacy ${UI_JSON} / ${LEGACY_JSON}). Use defineConfig from "${pkgName}/config". Set ui.componentsDir for the folder under your components alias (default "ui").
369
+
166
370
  Examples:
167
371
  npx ${cliName} init
168
372
  npx ${cliName} add data-table app-navbar
@@ -0,0 +1,47 @@
1
+ #!/usr/bin/env node
2
+ import { existsSync } from 'node:fs'
3
+ import { basename, dirname, join, resolve } from 'node:path'
4
+ import { fileURLToPath } from 'node:url'
5
+ import { spawnSync } from 'node:child_process'
6
+
7
+ const __dirname = dirname(fileURLToPath(import.meta.url))
8
+ const packageRoot = resolve(__dirname, '..')
9
+
10
+ const initCwd = resolveConsumerProjectRoot()
11
+ if (!initCwd) process.exit(0)
12
+
13
+ // Avoid running when installing this repo itself.
14
+ if (resolve(initCwd) === resolve(packageRoot)) process.exit(0)
15
+
16
+ // Only skip auto-init when a kilo config module already exists.
17
+ // Do not treat components.json / ui.json as "done" — shadcn and other tools use those too,
18
+ // and we still need to add kilo.config.ts.
19
+ const kiloModuleNames = ['kilo.config.ts', 'kilo.config.mts', 'kilo.config.js', 'kilo.config.mjs']
20
+ if (kiloModuleNames.some((name) => existsSync(join(initCwd, name)))) process.exit(0)
21
+
22
+ const cliEntry = join(packageRoot, 'bin', 'kilo-ui.mjs')
23
+
24
+ const result = spawnSync(process.execPath, [cliEntry, 'init'], {
25
+ cwd: initCwd,
26
+ stdio: 'inherit',
27
+ })
28
+
29
+ process.exit(result.status ?? 1)
30
+
31
+ /**
32
+ * Prefer npm's INIT_CWD or npm_config_local_prefix. If missing, infer the app root only when
33
+ * this package lives under node_modules (never guess from a bare repo path).
34
+ */
35
+ function resolveConsumerProjectRoot() {
36
+ const fromEnv = process.env.INIT_CWD || process.env.npm_config_local_prefix
37
+ if (fromEnv) return resolve(fromEnv)
38
+
39
+ const norm = packageRoot.replace(/\\/g, '/')
40
+ if (!norm.includes('/node_modules/')) return null
41
+
42
+ const parent = dirname(packageRoot)
43
+ if (basename(parent).startsWith('@')) {
44
+ return resolve(parent, '..', '..')
45
+ }
46
+ return resolve(parent, '..')
47
+ }
@@ -0,0 +1,26 @@
1
+ export interface KiloUiUserConfig {
2
+ /** @deprecated informational only */
3
+ $schema?: string
4
+ style?: string
5
+ srcDir?: string
6
+ ui?: {
7
+ /**
8
+ * Folder prefix under `aliases.components` where `kilo-ui add` places each component
9
+ * (default `"ui"` → e.g. `src/components/ui/<name>/`). Use `""` for `…/components/<name>/`.
10
+ */
11
+ componentsDir?: string
12
+ /** Same as `componentsDir` if you prefer the name “prefix”. */
13
+ componentsPrefix?: string
14
+ }
15
+ tailwind?: {
16
+ css: string
17
+ }
18
+ aliases: {
19
+ components: string
20
+ composables: string
21
+ lib: string
22
+ types: string
23
+ }
24
+ }
25
+
26
+ export function defineConfig(config: KiloUiUserConfig): KiloUiUserConfig
@@ -0,0 +1,4 @@
1
+ /** @param {import('./define-config.d.ts').KiloUiUserConfig} config */
2
+ export function defineConfig(config) {
3
+ return config
4
+ }
@@ -0,0 +1,29 @@
1
+ /**
2
+ * Example config shipped with the npm package at:
3
+ * node_modules/@lyda/kilo-ui/config/kilo.config.example.ts
4
+ *
5
+ * Your Vue app does NOT edit this file. On `npm install`, the CLI creates
6
+ * **`kilo.config.ts` in your project root** (next to package.json).
7
+ *
8
+ * Change **`ui.componentsDir`** to set the folder prefix under your components path
9
+ * (e.g. `"ui"` → src/components/ui/data-table/…). Use `componentsPrefix` as an alias.
10
+ */
11
+ import { defineConfig } from '@lyda/kilo-ui/config'
12
+
13
+ export default defineConfig({
14
+ style: 'default',
15
+ srcDir: 'src',
16
+ ui: {
17
+ /** Folder prefix under `aliases.components` for copied registry components */
18
+ componentsDir: 'ui',
19
+ },
20
+ tailwind: {
21
+ css: 'src/styles/teamwork-ui.css',
22
+ },
23
+ aliases: {
24
+ components: '@/components',
25
+ composables: '@/composables',
26
+ lib: '@/lib',
27
+ types: '@/types',
28
+ },
29
+ })
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lyda/kilo-ui",
3
- "version": "0.1.0",
3
+ "version": "0.1.4",
4
4
  "description": "shadcn-style Vue component registry for team CRUD apps",
5
5
  "type": "module",
6
6
  "repository": {
@@ -17,12 +17,20 @@
17
17
  "bin": {
18
18
  "kilo-ui": "bin/kilo-ui.mjs"
19
19
  },
20
+ "exports": {
21
+ "./config": {
22
+ "types": "./config/define-config.d.ts",
23
+ "default": "./config/define-config.mjs"
24
+ }
25
+ },
20
26
  "files": [
21
27
  "bin",
28
+ "config",
22
29
  "registry",
23
30
  "README.md"
24
31
  ],
25
32
  "scripts": {
33
+ "postinstall": "node bin/postinstall.mjs",
26
34
  "docs:dev": "vitepress dev docs",
27
35
  "docs:build": "vitepress build docs",
28
36
  "docs:preview": "vitepress preview docs",
@@ -48,5 +56,8 @@
48
56
  "crud",
49
57
  "ui"
50
58
  ],
51
- "license": "MIT"
59
+ "license": "MIT",
60
+ "dependencies": {
61
+ "jiti": "^2.7.0"
62
+ }
52
63
  }
@@ -0,0 +1,7 @@
1
+ /// <reference types="vite/client" />
2
+
3
+ declare module '*.vue' {
4
+ import type { DefineComponent } from 'vue'
5
+ const component: DefineComponent<object, object, any>
6
+ export default component
7
+ }