fix(experimental): keep last hash param instead of throwing · vuejs/router@d1e8ac1 · GitHub
Skip to content

Commit d1e8ac1

Browse files
committed
fix(experimental): keep last hash param instead of throwing
1 parent e7f4f79 commit d1e8ac1

4 files changed

Lines changed: 53 additions & 26 deletions

File tree

‎packages/router/src/unplugin/codegen/generateRouteParams.spec.ts‎

Lines changed: 8 additions & 6 deletions

‎packages/router/src/unplugin/core/definePage.spec.ts‎

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -316,16 +316,18 @@ definePage({ params: { hash: {
316316
expect(isTreeParamOptional(node.hashParams[0]!)).toBe(optional)
317317
})
318318

319-
it('rejects multiple named hash parameters with options', () => {
319+
it('keeps the last of multiple named hash parameters with options', () => {
320320
const code = `definePage({ params: { hash: {
321321
section: { required: true }, tab: 'int'
322322
} } })`
323323
const node = new TreeNodeValueStatic('test', undefined)
324324
node.setOverride('test.ts', {
325325
params: extractDefinePageInfo(code, 'test.ts')!.params,
326326
})
327-
expect(() => node.hashParams).toThrow()
328-
expect('Only one hash param can be declared per route.').toHaveBeenWarned()
327+
expect(node.hashParams).toEqual([
328+
{ paramName: 'tab', parser: 'int', hash: true },
329+
])
330+
expect('using "tab" and ignoring: section').toHaveBeenWarned()
329331
})
330332

331333
it('extracts all types of params', () => {

‎packages/router/src/unplugin/core/treeNodeValue.ts‎

Lines changed: 34 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,11 @@ class _TreeNodeValueBase {
6161
*/
6262
private _warnedParsers = new Set<string>()
6363

64+
/**
65+
* Ignored hash params last warned about, for the same reason.
66+
*/
67+
private _warnedHashParams = ''
68+
6469
/**
6570
* View name (Vue Router feature) mapped to their corresponding file. By default, the view name is `default` unless
6671
* specified with a `@` e.g. `index@aux.vue` will have a view name of `aux`.
@@ -148,22 +153,36 @@ class _TreeNodeValueBase {
148153
* Gets hash params declared on this node.
149154
*/
150155
get hashParams(): TreeHashParam[] {
151-
const entries = Object.entries(this.overrides.params?.hash ?? {})
152-
if (entries.length > 1) {
153-
throw diagnostics.VUE_ROUTER_B0022({
154-
paramNames: entries.map(([name]) => name).join(', '),
155-
})
156-
}
157-
return entries.map(([paramName, config]) => {
158-
if (typeof config === 'string') config = { parser: config }
159-
return {
160-
paramName,
161-
parser: config.parser || null,
162-
defaultValue: config.default,
163-
required: config.required,
164-
hash: true,
156+
const hash = this.overrides.params?.hash ?? {}
157+
const paramNames = Object.keys(hash)
158+
// the last one wins, like other overrides
159+
const paramName = paramNames.at(-1)
160+
if (paramNames.length > 1) {
161+
const ignoredParamNames = paramNames.slice(0, -1).join(', ')
162+
if (this._warnedHashParams !== ignoredParamNames) {
163+
this._warnedHashParams = ignoredParamNames
164+
diagnostics.VUE_ROUTER_B0022({
165+
segment: this.rawSegment,
166+
usedParamName: paramName!,
167+
ignoredParamNames,
168+
})
165169
}
166-
})
170+
}
171+
172+
let config = paramName ? hash[paramName] : undefined
173+
if (typeof config === 'string') config = { parser: config }
174+
175+
return paramName && config
176+
? [
177+
{
178+
paramName,
179+
parser: config.parser || null,
180+
defaultValue: config.default,
181+
required: config.required,
182+
hash: true,
183+
},
184+
]
185+
: []
167186
}
168187

169188
/**

‎packages/router/src/unplugin/diagnostics.ts‎

Lines changed: 6 additions & 2 deletions

0 commit comments

Comments
 (0)