fix(angular1_router): support link generation with custom hashPrefixes
This commit is contained in:
parent
69c1405196
commit
0f8efce799
|
@ -320,9 +320,5 @@ Location.prototype.prepareExternalUrl = function(url) {
|
|||
if (url.length > 0 && !url.startsWith('/')) {
|
||||
url = '/' + url;
|
||||
}
|
||||
if(!$location.$$html5) {
|
||||
return '#' + url;
|
||||
} else {
|
||||
return '.' + url;
|
||||
}
|
||||
return $location.$$html5 ? '.' + url : '#' + $locationHashPrefix + url;
|
||||
};
|
||||
|
|
|
@ -4,9 +4,33 @@ angular.module('ngComponentRouter').
|
|||
// Because Angular 1 has no notion of a root component, we use an object with unique identity
|
||||
// to represent this. Can be overloaded with a component name
|
||||
value('$routerRootComponent', new Object()).
|
||||
factory('$rootRouter', ['$q', '$location', '$browser', '$rootScope', '$injector', '$routerRootComponent', routerFactory]);
|
||||
|
||||
function routerFactory($q, $location, $browser, $rootScope, $injector, $routerRootComponent) {
|
||||
// Unfortunately, $location doesn't expose what the current hashPrefix is
|
||||
// So we have to monkey patch the $locationProvider to capture this value
|
||||
provider('$locationHashPrefix', ['$locationProvider', $locationHashPrefixProvider]).
|
||||
factory('$rootRouter', ['$q', '$location', '$browser', '$rootScope', '$injector', '$routerRootComponent', '$locationHashPrefix', routerFactory]);
|
||||
|
||||
function $locationHashPrefixProvider($locationProvider) {
|
||||
|
||||
// Get hold of the original hashPrefix method
|
||||
var hashPrefixFn = $locationProvider.hashPrefix.bind($locationProvider);
|
||||
|
||||
// Read the current hashPrefix (in case it was set before this monkey-patch occurred)
|
||||
var hashPrefix = hashPrefixFn();
|
||||
|
||||
// Override the helper so that we can read any changes to the prefix (after this monkey-patch)
|
||||
$locationProvider.hashPrefix = function(prefix) {
|
||||
if (angular.isDefined(prefix)) {
|
||||
hashPrefix = prefix;
|
||||
}
|
||||
return hashPrefixFn(prefix);
|
||||
}
|
||||
|
||||
// Return the final hashPrefix as the value of this service
|
||||
this.$get = function() { return hashPrefix; };
|
||||
}
|
||||
|
||||
function routerFactory($q, $location, $browser, $rootScope, $injector, $routerRootComponent, $locationHashPrefix) {
|
||||
|
||||
// When this file is processed, the line below is replaced with
|
||||
// the contents of `../lib/facades.es5`.
|
||||
|
|
|
@ -2,8 +2,23 @@
|
|||
|
||||
describe('ngLink', function () {
|
||||
|
||||
describe('html5Mode enabled', function () {
|
||||
runHrefTestsAndExpectPrefix(true);
|
||||
});
|
||||
|
||||
describe('html5Mode disabled', function () {
|
||||
runHrefTestsAndExpectPrefix(false, '');
|
||||
});
|
||||
|
||||
describe('html5Mode disabled, with hash prefix', function () {
|
||||
runHrefTestsAndExpectPrefix(false, '!');
|
||||
});
|
||||
|
||||
function runHrefTestsAndExpectPrefix(html5Mode, hashPrefix) {
|
||||
var prefix = html5Mode ? '.' : '#' + hashPrefix;
|
||||
|
||||
it('should allow linking from the parent to the child', function () {
|
||||
setup();
|
||||
setup({html5Mode: html5Mode, hashPrefix: hashPrefix});
|
||||
configureRouter([
|
||||
{ path: '/a', component: 'oneCmp' },
|
||||
{ path: '/b', component: 'twoCmp', name: 'Two' }
|
||||
|
@ -11,11 +26,11 @@ describe('ngLink', function () {
|
|||
|
||||
var elt = compile('<a ng-link="[\'/Two\']">link</a> | outer { <div ng-outlet></div> }');
|
||||
navigateTo('/a');
|
||||
expect(elt.find('a').attr('href')).toBe('./b');
|
||||
expect(elt.find('a').attr('href')).toBe(prefix + '/b');
|
||||
});
|
||||
|
||||
it('should allow linking from the child and the parent', function () {
|
||||
setup();
|
||||
setup({html5Mode: html5Mode, hashPrefix: hashPrefix});
|
||||
configureRouter([
|
||||
{ path: '/a', component: 'oneCmp' },
|
||||
{ path: '/b', component: 'twoCmp', name: 'Two' }
|
||||
|
@ -23,12 +38,12 @@ describe('ngLink', function () {
|
|||
|
||||
var elt = compile('outer { <div ng-outlet></div> }');
|
||||
navigateTo('/b');
|
||||
expect(elt.find('a').attr('href')).toBe('./b');
|
||||
expect(elt.find('a').attr('href')).toBe(prefix + '/b');
|
||||
});
|
||||
|
||||
|
||||
it('should allow params in routerLink directive', function () {
|
||||
setup();
|
||||
setup({html5Mode: html5Mode, hashPrefix: hashPrefix});
|
||||
registerComponent('twoLinkCmp', '<div><a ng-link="[\'/Two\', {param: \'lol\'}]">{{twoLinkCmp.number}}</a></div>', function () {this.number = 'two'});
|
||||
configureRouter([
|
||||
{ path: '/a', component: 'twoLinkCmp' },
|
||||
|
@ -37,12 +52,12 @@ describe('ngLink', function () {
|
|||
|
||||
var elt = compile('<div ng-outlet></div>');
|
||||
navigateTo('/a');
|
||||
expect(elt.find('a').attr('href')).toBe('./b/lol');
|
||||
expect(elt.find('a').attr('href')).toBe(prefix + '/b/lol');
|
||||
});
|
||||
|
||||
|
||||
it('should update the href of links with bound params', function () {
|
||||
setup();
|
||||
setup({html5Mode: html5Mode, hashPrefix: hashPrefix});
|
||||
registerComponent('twoLinkCmp', '<div><a ng-link="[\'/Two\', {param: $ctrl.number}]">{{$ctrl.number}}</a></div>', function () {this.number = 43});
|
||||
configureRouter([
|
||||
{ path: '/a', component: 'twoLinkCmp' },
|
||||
|
@ -52,12 +67,12 @@ describe('ngLink', function () {
|
|||
var elt = compile('<div ng-outlet></div>');
|
||||
navigateTo('/a');
|
||||
expect(elt.find('a').text()).toBe('43');
|
||||
expect(elt.find('a').attr('href')).toBe('./b/43');
|
||||
expect(elt.find('a').attr('href')).toBe(prefix + '/b/43');
|
||||
});
|
||||
|
||||
|
||||
it('should navigate on left-mouse click when a link url matches a route', function () {
|
||||
setup();
|
||||
setup({html5Mode: html5Mode, hashPrefix: hashPrefix});
|
||||
configureRouter([
|
||||
{ path: '/', component: 'oneCmp' },
|
||||
{ path: '/two', component: 'twoCmp', name: 'Two'}
|
||||
|
@ -65,7 +80,7 @@ describe('ngLink', function () {
|
|||
|
||||
var elt = compile('<a ng-link="[\'/Two\']">link</a> | <div ng-outlet></div>');
|
||||
expect(elt.text()).toBe('link | one');
|
||||
expect(elt.find('a').attr('href')).toBe('./two');
|
||||
expect(elt.find('a').attr('href')).toBe(prefix + '/two');
|
||||
|
||||
elt.find('a')[0].click();
|
||||
inject(function($rootScope) { $rootScope.$digest(); });
|
||||
|
@ -74,7 +89,7 @@ describe('ngLink', function () {
|
|||
|
||||
|
||||
it('should not navigate on non-left mouse click when a link url matches a route', function() {
|
||||
setup();
|
||||
setup({html5Mode: html5Mode, hashPrefix: hashPrefix});
|
||||
configureRouter([
|
||||
{ path: '/', component: 'oneCmp' },
|
||||
{ path: '/two', component: 'twoCmp', name: 'Two'}
|
||||
|
@ -90,7 +105,7 @@ describe('ngLink', function () {
|
|||
|
||||
// See https://github.com/angular/router/issues/206
|
||||
it('should not navigate a link without an href', function () {
|
||||
setup();
|
||||
setup({html5Mode: html5Mode, hashPrefix: hashPrefix});
|
||||
configureRouter([
|
||||
{ path: '/', component: 'oneCmp' },
|
||||
{ path: '/two', component: 'twoCmp', name: 'Two'}
|
||||
|
@ -104,7 +119,7 @@ describe('ngLink', function () {
|
|||
});
|
||||
|
||||
it('should add an ng-link-active class on the current link', function() {
|
||||
setup();
|
||||
setup({html5Mode: html5Mode, hashPrefix: hashPrefix});
|
||||
configureRouter([
|
||||
{ path: '/', component: 'oneCmp', name: 'One' }
|
||||
]);
|
||||
|
@ -113,22 +128,7 @@ describe('ngLink', function () {
|
|||
navigateTo('/');
|
||||
expect(elt.find('a').attr('class')).toBe('ng-link-active');
|
||||
});
|
||||
|
||||
|
||||
describe('html5Mode disabled', function () {
|
||||
it('should prepend href with a hash', function () {
|
||||
setup({ html5Mode: false });
|
||||
module(function($locationProvider) {
|
||||
$locationProvider.html5Mode(false);
|
||||
});
|
||||
configureRouter([
|
||||
{ path: '/b', component: 'twoCmp', name: 'Two' }
|
||||
]);
|
||||
var elt = compile('<a ng-link="[\'/Two\']">link</a>');
|
||||
expect(elt.find('a').attr('href')).toBe('#/b');
|
||||
});
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
function registerComponent(name, template, controller) {
|
||||
module(function($compileProvider) {
|
||||
|
@ -140,10 +140,10 @@ describe('ngLink', function () {
|
|||
}
|
||||
|
||||
function setup(config) {
|
||||
var html5Mode = !(config && config.html5Mode === false);
|
||||
module('ngComponentRouter')
|
||||
module(function($locationProvider) {
|
||||
$locationProvider.html5Mode(html5Mode);
|
||||
$locationProvider.html5Mode(config.html5Mode);
|
||||
$locationProvider.hashPrefix(config.hashPrefix);
|
||||
});
|
||||
registerComponent('userCmp', '<div>hello {{$ctrl.$routeParams.name}}</div>', function () {});
|
||||
registerComponent('oneCmp', '<div>{{$ctrl.number}}</div>', function () {this.number = 'one'});
|
||||
|
|
Loading…
Reference in New Issue