AngularJS - UI路由页面重新加载无法设置状态

5
这是我的主要应用程序(app.js)。
(function(ng, module) {
    module.config(['$stateProvider', '$urlRouterProvider', function( $stateProvider, $urlRouterProvider){

        $urlRouterProvider.otherwise("app");

        $stateProvider.state('login', {
            url: 'login',
            templateUrl: '/assets/templates/pages/login.html'
        }).state('root', {
            url: '',
            templateUrl: '/assets/templates/pages/index.html'
        });


    }]);
}) (angular, angular.module('myapp', ['ui.router', 'myapp.submodule']));

这是子模块(submodule.js)。

(function(ng, module) {
    module.config(['$stateProvider', function($stateProvider){
        $stateProvider.state('root.substate', {
            url: 'todo/{type}',
            templateUrl: '/assets/app/todo/todo.html',
            controller: function($stateParams, $scope) {
                // Do stuff.
            }
        });
    }]);

}) (angular, angular.module('myapp.submodule', ['ui.router']));

预期的行为应该是:

  • 在找不到匹配路由时,重定向到“app”网址
  • 在根网址上激活“root”状态
  • 在/todo网址上激活“root.substate”状态

这个功能正常工作。

然而,如果我刷新页面,状态就没有被激活,而我被发送回“app”。为什么呢?


1
也许不是真正的问题,但我肯定会以 / 开头来启动任何 URL - url: '/todo/{type}' - Radim Köhler
我还在测试中,但似乎前导斜杠可能是问题所在。 - brazorf
你知道为什么吗?简单来说,必须有一种明确定义状态URL起始位置的方法。你的URL映射是这样的:domain/applogin,而我建议使用domain/app/login,所以没有斜杠...如果你知道我的意思,那对引擎会造成很大的问题。 - Radim Köhler
嗯,我还是有点困惑。登录和根状态前面的斜杠可以修复它们。嵌套的root.substate状态在没有前导斜杠的情况下运行良好,并且在有前导斜杠的情况下存在错误。错误=刷新会导致未解决的路由。编辑:错误= URL呈现为foo.bar/#//todo(双斜杠)。我认为我对URL生成有所遗漏。 - brazorf
我会尝试向您展示如何回答问题,请稍等。 - Radim Köhler
2个回答

7
我们有两个根状态(没有父级)。它们应该没有URL,或者URL应该以某个唯一标志开始 - 最好的选择总是使用斜杠符号“/”(URI规范)。
// domain/app/login - easy to find
.state('login', {
    url: 'login',
    ...
})
// no def === domain/app
.state('root', {
    url: '',
    ...
});

现在,让我们甚至为我们的'root'状态使用一些url:
// domain/app/
.state('root', {
    url: '/',
    ...
});

这意味着我们的子级状态 'root.substate' 也将包含父级 url 部分。因此,如果我们使用这个方法

// this is a child and its url will be in fact: domain/app//todo/sometype
.state('root.substate', {
    url: '/todo/{type}',
    ...
});

看,这样一来,我们的url现在会包含//(双斜杠)。

为了避免这种情况,我们可以使用UI-Router的'^'特性。

// this stat will not use the parent part
// this will work domain/app/todo/sometype
.state('root.substate', {
    url: '^/todo/{type}',
    ...
});

请查看文档:

绝对路径 (^)

如果您想要进行绝对url匹配,则需要在您的url字符串前添加一个特殊符号'^'。

$stateProvider
  .state('contacts', {
     url: '/contacts',
     ...
  })
  .state('contacts.list', {
     url: '^/list',
     ...
  });

谢谢,这就是我在寻找的答案。 - brazorf
如果这有所帮助那就太好了。享受强大的UI-Router吧 ;) - Radim Köhler
1
我尝试了这个解决方案,它有效。但是我仍然有关于刷新页面导致默认路由($otherwise)的问题。 - Raymond Ativie

0

我知道还有很多时间。但是关于刷新的问题。如果你想在刷新之后保持与之前相同的URL地址,你应该添加以下内容:

angular.module('app').run(['$state', '$stateParams', function($state, $stateParams) {
   //this solves page refresh and getting back to state
}]);

就像在上一个答案中提到的这里


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接