nuxt-typed-router 1.0.2 → 1.1.0-beta.0
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 +36 -8
- package/dist/module.json +1 -1
- package/dist/module.mjs +55 -45
- package/package.json +2 -7
- package/dist/runtime/index.d.ts +0 -1
- package/dist/runtime/index.mjs +0 -1
- package/dist/runtime/typed-router.d.ts +0 -34
- package/dist/runtime/typed-router.mjs +0 -34
- package/dist/runtime/useTypedRouter.d.ts +0 -42
- package/dist/runtime/useTypedRouter.mjs +0 -42
- package/hook.d.ts +0 -4
- package/hook.mjs +0 -1
package/README.md
CHANGED
|
@@ -77,16 +77,22 @@ interface ModuleOptions {
|
|
|
77
77
|
|
|
78
78
|
# Generated files
|
|
79
79
|
|
|
80
|
-
The module will
|
|
80
|
+
The module will generate 4 files each time you modify the `pages` folder :
|
|
81
81
|
|
|
82
|
-
-
|
|
83
|
-
- `
|
|
82
|
+
- `~/<outDir>/__routes.ts` with the global object of the route names inside.
|
|
83
|
+
- `~/<outDir>/__useTypedRouter` Composable tu simply access your typed routes
|
|
84
|
+
- `~/<outDir>/typed-router.d.ts` containing the global typecript definitions and exports
|
|
85
|
+
- `~/plugins/__typed_router.ts` Plugin that will inject `$typedRouter` and `$routesList` (`@nuxt/kit` has problems registering plugin templates so this is a workaround)
|
|
84
86
|
|
|
85
87
|
# Usage in Vue/Nuxt
|
|
86
88
|
|
|
89
|
+
## Check out this demo and clone it! [nuxt-typed-router-demo](https://github.com/victorgarciaesgi/nuxt-typed-router-demo)
|
|
90
|
+
|
|
91
|
+
<br/>
|
|
92
|
+
|
|
87
93
|
### **_Requirements_**
|
|
88
94
|
|
|
89
|
-
You
|
|
95
|
+
You can specify the output dir of the generated files in your configuration. It defaults to `<srcDir>/generated`
|
|
90
96
|
|
|
91
97
|
```ts
|
|
92
98
|
import TypedRouter from 'nuxt-typed-router';
|
|
@@ -146,13 +152,16 @@ export type TypedRouteList =
|
|
|
146
152
|
| 'index-user';
|
|
147
153
|
```
|
|
148
154
|
|
|
155
|
+
> nuxt-typed-router will also create a plugin in your `<srcDir>/plugins` folder with the injected `$typedRouter` and `$routesList` helpers
|
|
156
|
+
|
|
149
157
|
# Usage with `useTypedRouter` hook
|
|
150
158
|
|
|
151
159
|
`useTypedRouter` is an exported composable from nuxt-typed-router. It contains a clone of `vue-router` but with stritly typed route names and params type-check
|
|
152
160
|
|
|
153
161
|
```vue
|
|
154
162
|
<script lang="ts">
|
|
155
|
-
|
|
163
|
+
// The path here is `~/generated` because I set `outDir: './generated'` in my module options
|
|
164
|
+
import { useTypedRouter } from '~/generated';
|
|
156
165
|
|
|
157
166
|
export default defineComponent({
|
|
158
167
|
setup() {
|
|
@@ -171,7 +180,7 @@ export default defineComponent({
|
|
|
171
180
|
</script>
|
|
172
181
|
```
|
|
173
182
|
|
|
174
|
-
# Usage with `$typedRouter` injected
|
|
183
|
+
# Usage with `$typedRouter` and `$routesList` injected helpers
|
|
175
184
|
|
|
176
185
|
`$typedRouter` is an injected clone of vue-router `$router`, but fully typed with all your routes.
|
|
177
186
|
It's available anywhere you have access to Nuxt context
|
|
@@ -183,10 +192,10 @@ import { defineComponent } from 'vue';
|
|
|
183
192
|
export default defineComponent({
|
|
184
193
|
name: 'Index',
|
|
185
194
|
setup() {
|
|
186
|
-
const { $typedRouter } = useNuxtApp();
|
|
195
|
+
const { $typedRouter, $routesList } = useNuxtApp();
|
|
187
196
|
|
|
188
197
|
function navigate() {
|
|
189
|
-
$typedRouter.push({ name:
|
|
198
|
+
$typedRouter.push({ name: $routesList.activate });
|
|
190
199
|
}
|
|
191
200
|
|
|
192
201
|
return {
|
|
@@ -197,6 +206,25 @@ export default defineComponent({
|
|
|
197
206
|
</script>
|
|
198
207
|
```
|
|
199
208
|
|
|
209
|
+
# Usage outside Vue component
|
|
210
|
+
|
|
211
|
+
You can import the `useTypedRouter` composable from where it's generated.
|
|
212
|
+
Exemple with `pinia` store here
|
|
213
|
+
|
|
214
|
+
```ts
|
|
215
|
+
import pinia from 'pinia';
|
|
216
|
+
import { useTypedRouter } from '~/generated';
|
|
217
|
+
|
|
218
|
+
export const useFooStore = defineStore('foo', {
|
|
219
|
+
actions: {
|
|
220
|
+
bar() {
|
|
221
|
+
const { router, routes } = useTypedRouter();
|
|
222
|
+
router.push({ name: routes.index.user, params: { user: 2 } });
|
|
223
|
+
},
|
|
224
|
+
},
|
|
225
|
+
});
|
|
226
|
+
```
|
|
227
|
+
|
|
200
228
|
## Development
|
|
201
229
|
|
|
202
230
|
1. Clone this repository
|
package/dist/module.json
CHANGED
package/dist/module.mjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { extendPages,
|
|
1
|
+
import { extendPages, defineNuxtModule } from '@nuxt/kit';
|
|
2
2
|
import { fileURLToPath } from 'url';
|
|
3
3
|
import chalk from 'chalk';
|
|
4
4
|
import logSymbols from 'log-symbols';
|
|
@@ -192,8 +192,12 @@ function walkThoughRoutes({
|
|
|
192
192
|
}
|
|
193
193
|
|
|
194
194
|
const signatureTemplate = `/**
|
|
195
|
-
*
|
|
196
|
-
*
|
|
195
|
+
* ---------------------
|
|
196
|
+
* \u{1F697}\u{1F6A6} Generated by nuxt-typed-router. Do not modify !
|
|
197
|
+
* ---------------------
|
|
198
|
+
* */
|
|
199
|
+
|
|
200
|
+
`;
|
|
197
201
|
const staticDeclImports = `
|
|
198
202
|
import type {
|
|
199
203
|
NavigationFailure,
|
|
@@ -288,18 +292,11 @@ const staticDeclarations = `
|
|
|
288
292
|
$routesList: RouteListDecl;
|
|
289
293
|
}
|
|
290
294
|
}
|
|
291
|
-
declare module 'nuxt-typed-router/hook' {
|
|
292
|
-
declare const useTypedRouter: () => {
|
|
293
|
-
/** Export of $router with type check */
|
|
294
|
-
router: TypedRouter,
|
|
295
|
-
/** Contains a typed dictionnary of all your route names (for syntax sugar) */
|
|
296
|
-
routes: RouteListDecl
|
|
297
|
-
};
|
|
298
|
-
}
|
|
299
295
|
`;
|
|
300
296
|
|
|
301
297
|
function createRuntimePluginFile(routesDeclTemplate) {
|
|
302
298
|
return `
|
|
299
|
+
${signatureTemplate}
|
|
303
300
|
import { defineNuxtPlugin } from '#app';
|
|
304
301
|
|
|
305
302
|
export default defineNuxtPlugin((nuxtApp) => {
|
|
@@ -307,7 +304,7 @@ function createRuntimePluginFile(routesDeclTemplate) {
|
|
|
307
304
|
|
|
308
305
|
return {
|
|
309
306
|
provide: {
|
|
310
|
-
typedRouter: nuxtApp
|
|
307
|
+
typedRouter: nuxtApp.$router,
|
|
311
308
|
routesList,
|
|
312
309
|
},
|
|
313
310
|
};
|
|
@@ -316,17 +313,22 @@ function createRuntimePluginFile(routesDeclTemplate) {
|
|
|
316
313
|
}
|
|
317
314
|
function createRuntimeHookFile(routesDeclTemplate) {
|
|
318
315
|
return `
|
|
316
|
+
${signatureTemplate}
|
|
319
317
|
import { getCurrentInstance } from 'vue';
|
|
318
|
+
import { useNuxtApp } from '#app';
|
|
320
319
|
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
320
|
+
/** Returns instances of $typedRouter and $routesList fully typed to use in your components or your Vuex/Pinia store
|
|
321
|
+
*
|
|
322
|
+
* @exemple
|
|
323
|
+
*
|
|
324
|
+
* const { router, routes } = useTypedRouter();
|
|
325
|
+
*/
|
|
326
|
+
export const useTypedRouter = (): {
|
|
327
|
+
/** Export of $router with type check */
|
|
328
|
+
router: TypedRouter,
|
|
329
|
+
/** Contains a typed dictionnary of all your route names (for syntax sugar) */
|
|
330
|
+
routes: RouteListDecl
|
|
331
|
+
} => {
|
|
330
332
|
const { $router } = useNuxtApp();
|
|
331
333
|
|
|
332
334
|
const routesList = ${routesDeclTemplate};
|
|
@@ -334,11 +336,18 @@ function createRuntimeHookFile(routesDeclTemplate) {
|
|
|
334
336
|
return {
|
|
335
337
|
router: $router,
|
|
336
338
|
routes: routesList,
|
|
337
|
-
};
|
|
339
|
+
} as any;
|
|
338
340
|
};
|
|
339
341
|
|
|
340
342
|
`;
|
|
341
343
|
}
|
|
344
|
+
function createRuntimeIndexFile() {
|
|
345
|
+
return `
|
|
346
|
+
${signatureTemplate}
|
|
347
|
+
export * from './__routes';
|
|
348
|
+
export * from './__useTypedRouter';
|
|
349
|
+
`;
|
|
350
|
+
}
|
|
342
351
|
function createRuntimeRoutesFile({
|
|
343
352
|
routesList,
|
|
344
353
|
routesObjectTemplate,
|
|
@@ -380,27 +389,28 @@ function createTypedRouteParamsExport(routesParams) {
|
|
|
380
389
|
}
|
|
381
390
|
|
|
382
391
|
const __dirname = dirname(fileURLToPath(import.meta.url));
|
|
383
|
-
function routeHook(outDir, routesObjectName) {
|
|
392
|
+
function routeHook(outDir, routesObjectName, srcDir, nuxt) {
|
|
384
393
|
try {
|
|
385
394
|
extendPages(async (routes) => {
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
routesList
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
395
|
+
if (routes.length) {
|
|
396
|
+
const { routesDeclTemplate, routesList, routesObjectTemplate, routesParams } = constructRouteMap(routes);
|
|
397
|
+
const pluginName = "__typed-router.ts";
|
|
398
|
+
const runtimeDir = resolve(__dirname, process.env.NUXT_BUILD_TYPE === "stub" ? "../../dist/runtime" : "./runtime");
|
|
399
|
+
const pluginPath = resolve(runtimeDir, pluginName);
|
|
400
|
+
nuxt.hook("build:done", async () => {
|
|
401
|
+
const pluginFolder = `${srcDir}/plugins`;
|
|
402
|
+
await saveRouteFiles(pluginFolder, pluginName, createRuntimePluginFile(routesDeclTemplate));
|
|
403
|
+
});
|
|
404
|
+
await Promise.all([
|
|
405
|
+
saveRouteFiles(outDir, "__useTypedRouter.ts", createRuntimeHookFile(routesDeclTemplate)),
|
|
406
|
+
saveRouteFiles(outDir, `__routes.ts`, createRuntimeRoutesFile({ routesList, routesObjectTemplate, routesObjectName })),
|
|
407
|
+
saveRouteFiles(outDir, `typed-router.d.ts`, createDeclarationRoutesFile({ routesDeclTemplate, routesList, routesParams })),
|
|
408
|
+
saveRouteFiles(outDir, "index.ts", createRuntimeIndexFile())
|
|
409
|
+
]);
|
|
410
|
+
console.log(logSymbols.success, `[typed-router] Routes definitions generated`);
|
|
411
|
+
} else {
|
|
412
|
+
console.log(logSymbols.warning, chalk.yellow(`[typed-router] No routes defined. Check if your ${chalk.underline(chalk.bold("pages"))} folder exists and remove ${chalk.underline(chalk.bold("app.vue"))}`));
|
|
413
|
+
}
|
|
404
414
|
});
|
|
405
415
|
} catch (e) {
|
|
406
416
|
console.error(chalk.red("Error while generating routes definitions model"), "\n" + e);
|
|
@@ -418,10 +428,10 @@ const module = defineNuxtModule({
|
|
|
418
428
|
stripAtFromName: false
|
|
419
429
|
},
|
|
420
430
|
setup(moduleOptions, nuxt) {
|
|
421
|
-
const
|
|
422
|
-
|
|
423
|
-
nuxt.hook("
|
|
424
|
-
routeHook(outDir, routesObjectName);
|
|
431
|
+
const srcDir = nuxt.options.srcDir;
|
|
432
|
+
const { outDir = `${srcDir}/generated`, routesObjectName } = moduleOptions;
|
|
433
|
+
nuxt.hook("pages:extend", () => routeHook(outDir, routesObjectName, srcDir, nuxt));
|
|
434
|
+
routeHook(outDir, routesObjectName, srcDir, nuxt);
|
|
425
435
|
}
|
|
426
436
|
});
|
|
427
437
|
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "nuxt-typed-router",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.1.0-beta.0",
|
|
4
4
|
"description": "Provide autocompletion for pages route names generated by Nuxt router",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"scripts": {
|
|
@@ -17,18 +17,13 @@
|
|
|
17
17
|
".": {
|
|
18
18
|
"import": "./dist/module.mjs",
|
|
19
19
|
"require": "./dist/module.cjs"
|
|
20
|
-
},
|
|
21
|
-
"./hook": {
|
|
22
|
-
"import": "./hook.mjs"
|
|
23
20
|
}
|
|
24
21
|
},
|
|
25
22
|
"main": "./dist/module.cjs",
|
|
26
23
|
"types": "./main.d.ts",
|
|
27
24
|
"files": [
|
|
28
25
|
"dist",
|
|
29
|
-
"main.d.ts"
|
|
30
|
-
"hook.mjs",
|
|
31
|
-
"hook.d.ts"
|
|
26
|
+
"main.d.ts"
|
|
32
27
|
],
|
|
33
28
|
"publishConfig": {
|
|
34
29
|
"access": "public"
|
package/dist/runtime/index.d.ts
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export { useTypedRouter } from './useTypedRouter';
|
package/dist/runtime/index.mjs
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export { useTypedRouter } from "./useTypedRouter.mjs";
|
|
@@ -1,34 +0,0 @@
|
|
|
1
|
-
import { defineNuxtPlugin } from '#app';
|
|
2
|
-
|
|
3
|
-
export default defineNuxtPlugin((nuxtApp) => {
|
|
4
|
-
const routesList = {
|
|
5
|
-
activate: 'activate',
|
|
6
|
-
index: 'index',
|
|
7
|
-
childOne: {
|
|
8
|
-
childOneChildOneSubOne: 'parent-child-one-child-one-sub-one',
|
|
9
|
-
user: { index: 'parent-child-one-child-one-sub-one-user' },
|
|
10
|
-
childOneChildOneSubTwo: 'parent-child-one-child-one-sub-two',
|
|
11
|
-
index: 'parent-child-one',
|
|
12
|
-
},
|
|
13
|
-
childTwo: {
|
|
14
|
-
childTwoId: 'parent-child-two-id',
|
|
15
|
-
childTwoChildOneSubOne: 'parent-child-two-child-one-sub-one',
|
|
16
|
-
index: 'parent-child-two',
|
|
17
|
-
profile: {
|
|
18
|
-
id: {
|
|
19
|
-
slug: { index: 'parent-child-two-profile-id-slug' },
|
|
20
|
-
index: 'parent-child-two-profile-id',
|
|
21
|
-
},
|
|
22
|
-
index: 'parent-child-two-profile',
|
|
23
|
-
},
|
|
24
|
-
},
|
|
25
|
-
rootPage: 'rootPage',
|
|
26
|
-
};
|
|
27
|
-
|
|
28
|
-
return {
|
|
29
|
-
provide: {
|
|
30
|
-
typedRouter: nuxtApp.vueApp.$router,
|
|
31
|
-
routesList,
|
|
32
|
-
},
|
|
33
|
-
};
|
|
34
|
-
});
|
|
@@ -1,34 +0,0 @@
|
|
|
1
|
-
import { defineNuxtPlugin } from '#app';
|
|
2
|
-
|
|
3
|
-
export default defineNuxtPlugin((nuxtApp) => {
|
|
4
|
-
const routesList = {
|
|
5
|
-
activate: 'activate',
|
|
6
|
-
index: 'index',
|
|
7
|
-
childOne: {
|
|
8
|
-
childOneChildOneSubOne: 'parent-child-one-child-one-sub-one',
|
|
9
|
-
user: { index: 'parent-child-one-child-one-sub-one-user' },
|
|
10
|
-
childOneChildOneSubTwo: 'parent-child-one-child-one-sub-two',
|
|
11
|
-
index: 'parent-child-one',
|
|
12
|
-
},
|
|
13
|
-
childTwo: {
|
|
14
|
-
childTwoId: 'parent-child-two-id',
|
|
15
|
-
childTwoChildOneSubOne: 'parent-child-two-child-one-sub-one',
|
|
16
|
-
index: 'parent-child-two',
|
|
17
|
-
profile: {
|
|
18
|
-
id: {
|
|
19
|
-
slug: { index: 'parent-child-two-profile-id-slug' },
|
|
20
|
-
index: 'parent-child-two-profile-id',
|
|
21
|
-
},
|
|
22
|
-
index: 'parent-child-two-profile',
|
|
23
|
-
},
|
|
24
|
-
},
|
|
25
|
-
rootPage: 'rootPage',
|
|
26
|
-
};
|
|
27
|
-
|
|
28
|
-
return {
|
|
29
|
-
provide: {
|
|
30
|
-
typedRouter: nuxtApp.vueApp.$router,
|
|
31
|
-
routesList,
|
|
32
|
-
},
|
|
33
|
-
};
|
|
34
|
-
});
|
|
@@ -1,42 +0,0 @@
|
|
|
1
|
-
import { getCurrentInstance } from 'vue';
|
|
2
|
-
|
|
3
|
-
function useNuxtApp() {
|
|
4
|
-
const vm = getCurrentInstance();
|
|
5
|
-
if (!vm) {
|
|
6
|
-
throw new Error('nuxt instance unavailable');
|
|
7
|
-
}
|
|
8
|
-
return vm.appContext.app.$nuxt;
|
|
9
|
-
}
|
|
10
|
-
|
|
11
|
-
export const useTypedRouter = () => {
|
|
12
|
-
const { $router } = useNuxtApp();
|
|
13
|
-
|
|
14
|
-
const routesList = {
|
|
15
|
-
activate: 'activate',
|
|
16
|
-
index: 'index',
|
|
17
|
-
childOne: {
|
|
18
|
-
childOneChildOneSubOne: 'parent-child-one-child-one-sub-one',
|
|
19
|
-
user: { index: 'parent-child-one-child-one-sub-one-user' },
|
|
20
|
-
childOneChildOneSubTwo: 'parent-child-one-child-one-sub-two',
|
|
21
|
-
index: 'parent-child-one',
|
|
22
|
-
},
|
|
23
|
-
childTwo: {
|
|
24
|
-
childTwoId: 'parent-child-two-id',
|
|
25
|
-
childTwoChildOneSubOne: 'parent-child-two-child-one-sub-one',
|
|
26
|
-
index: 'parent-child-two',
|
|
27
|
-
profile: {
|
|
28
|
-
id: {
|
|
29
|
-
slug: { index: 'parent-child-two-profile-id-slug' },
|
|
30
|
-
index: 'parent-child-two-profile-id',
|
|
31
|
-
},
|
|
32
|
-
index: 'parent-child-two-profile',
|
|
33
|
-
},
|
|
34
|
-
},
|
|
35
|
-
rootPage: 'rootPage',
|
|
36
|
-
};
|
|
37
|
-
|
|
38
|
-
return {
|
|
39
|
-
router: $router,
|
|
40
|
-
routes: routesList,
|
|
41
|
-
};
|
|
42
|
-
};
|
|
@@ -1,42 +0,0 @@
|
|
|
1
|
-
import { getCurrentInstance } from 'vue';
|
|
2
|
-
|
|
3
|
-
function useNuxtApp() {
|
|
4
|
-
const vm = getCurrentInstance();
|
|
5
|
-
if (!vm) {
|
|
6
|
-
throw new Error('nuxt instance unavailable');
|
|
7
|
-
}
|
|
8
|
-
return vm.appContext.app.$nuxt;
|
|
9
|
-
}
|
|
10
|
-
|
|
11
|
-
export const useTypedRouter = () => {
|
|
12
|
-
const { $router } = useNuxtApp();
|
|
13
|
-
|
|
14
|
-
const routesList = {
|
|
15
|
-
activate: 'activate',
|
|
16
|
-
index: 'index',
|
|
17
|
-
childOne: {
|
|
18
|
-
childOneChildOneSubOne: 'parent-child-one-child-one-sub-one',
|
|
19
|
-
user: { index: 'parent-child-one-child-one-sub-one-user' },
|
|
20
|
-
childOneChildOneSubTwo: 'parent-child-one-child-one-sub-two',
|
|
21
|
-
index: 'parent-child-one',
|
|
22
|
-
},
|
|
23
|
-
childTwo: {
|
|
24
|
-
childTwoId: 'parent-child-two-id',
|
|
25
|
-
childTwoChildOneSubOne: 'parent-child-two-child-one-sub-one',
|
|
26
|
-
index: 'parent-child-two',
|
|
27
|
-
profile: {
|
|
28
|
-
id: {
|
|
29
|
-
slug: { index: 'parent-child-two-profile-id-slug' },
|
|
30
|
-
index: 'parent-child-two-profile-id',
|
|
31
|
-
},
|
|
32
|
-
index: 'parent-child-two-profile',
|
|
33
|
-
},
|
|
34
|
-
},
|
|
35
|
-
rootPage: 'rootPage',
|
|
36
|
-
};
|
|
37
|
-
|
|
38
|
-
return {
|
|
39
|
-
router: $router,
|
|
40
|
-
routes: routesList,
|
|
41
|
-
};
|
|
42
|
-
};
|
package/hook.d.ts
DELETED
package/hook.mjs
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export { useTypedRouter } from './dist/runtime/useTypedRouter.mjs';
|