From b2f395294696c8eac03330ac29cba67da2160b65 Mon Sep 17 00:00:00 2001 From: Andrew Scott Date: Mon, 26 Oct 2020 20:38:28 -0700 Subject: [PATCH] fix(router): Ensure all outlets are used when commands have a prefix (#39456) When there is a primary outlet present in the outlets map and the object is also prefixed with some other commands, the current logic only uses the primary outlet and ignores the others. This change ensures that all outlets are respected at the segment level when prefixed with other commands. PR Close #39456 --- packages/router/src/create_url_tree.ts | 18 +++++++++--------- packages/router/test/create_url_tree.spec.ts | 4 ++-- 2 files changed, 11 insertions(+), 11 deletions(-) diff --git a/packages/router/src/create_url_tree.ts b/packages/router/src/create_url_tree.ts index c7fcb312600..2a70e23e2c8 100644 --- a/packages/router/src/create_url_tree.ts +++ b/packages/router/src/create_url_tree.ts @@ -186,13 +186,6 @@ function createPositionApplyingDoubleDots( return new Position(g, false, ci - dd); } -function getPath(command: any): any { - if (isCommandWithOutlets(command)) { - return command.outlets[PRIMARY_OUTLET]; - } - return `${command}`; -} - function getOutlets(commands: any[]): {[k: string]: any[]} { if (isCommandWithOutlets(commands[0])) { return commands[0].outlets; @@ -259,7 +252,14 @@ function prefixedWith(segmentGroup: UrlSegmentGroup, startIndex: number, command while (currentPathIndex < segmentGroup.segments.length) { if (currentCommandIndex >= commands.length) return noMatch; const path = segmentGroup.segments[currentPathIndex]; - const curr = getPath(commands[currentCommandIndex]); + const command = commands[currentCommandIndex]; + // Do not try to consume command as part of the prefixing if it has outlets because it can + // contain outlets other than the one being processed. Consuming the outlets command would + // result in other outlets being ignored. + if (isCommandWithOutlets(command)) { + break; + } + const curr = `${command}`; const next = currentCommandIndex < commands.length - 1 ? commands[currentCommandIndex + 1] : null; @@ -298,7 +298,7 @@ function createNewSegmentGroup( continue; } - const curr = getPath(command); + const curr = isCommandWithOutlets(command) ? command.outlets[PRIMARY_OUTLET] : `${command}`; const next = (i < commands.length - 1) ? commands[i + 1] : null; if (curr && next && isMatrixParams(next)) { paths.push(new UrlSegment(curr, stringify(next))); diff --git a/packages/router/test/create_url_tree.spec.ts b/packages/router/test/create_url_tree.spec.ts index 75e25644926..d51fa48d957 100644 --- a/packages/router/test/create_url_tree.spec.ts +++ b/packages/router/test/create_url_tree.spec.ts @@ -150,13 +150,13 @@ describe('createUrlTree', () => { expect(serializer.serialize(t)).toEqual('/parent/child'); }); - xit('should support updating secondary and primary outlets with prefix', () => { + it('should support updating secondary and primary outlets with prefix', () => { const p = serializer.parse('/parent/child'); const t = createRoot(p, ['parent', {outlets: {primary: 'child', secondary: 'popup'}}]); expect(serializer.serialize(t)).toEqual('/parent/(child//secondary:popup)'); }); - xit('should support updating two outlets at the same time relative to non-root segment', () => { + it('should support updating two outlets at the same time relative to non-root segment', () => { const p = serializer.parse('/parent/child'); const t = create( p.root.children[PRIMARY_OUTLET], 0 /* relativeTo: 'parent' */, p,