2014-10-01 94 views
7

我在我的Angular應用中使用ui.router進行路由。有一個典型的登錄場景,如果他沒有登錄,我將用戶重定向到登錄網址。沒有ui.router庫,使用$ routeChangeStart事件並結合$location.path可以正常工作。現在,我正在使用$stateChangeStart事件,加上$state.go,沒有什麼效果!它也將我的瀏覽器發送到無限循環。我從其他來源讀到這是一個已知的錯誤,並且沒有任何建議的解決方案適用於我。而且,$location.path也不會重定向到登錄頁面。Angular ui路由器 - 重定向根本不起作用

這是我是如何配置我的路徑:

.config(['$stateProvider', '$urlRouterProvider', function ($stateProvider, $urlRouterProvider) { 
    $stateProvider 
     .state('main', { 
      url: '/', 
      templateUrl: 'views/main.html', 
      controller: 'MainCtrl' 
     }) 
     .state('about', { 
      url: '/about', 
      templateUrl: 'views/about.html', 
      controller: 'AboutCtrl' 
     }) 
     .state('login', { 
      url: '/login', 
      templateUrl: 'views/loginform.html', 
      controller: 'LoginCtrl' 
     }); 
    $urlRouterProvider.otherwise("/"); 
}]) 

而且我run方法:

.run(['$state', '$rootScope', '$location', function($state, $rootScope, $location) { 
    //Check when routing starts 
    //event, next, current 
    $rootScope.$on('$stateChangeStart', function(e, toState, toParams, fromState, fromParams) { 
     //Redirect to login if the user is not logged in 
     if (!isUserLoggedIn) { 

      //Some suggestion 
      //e.preventDefault(); 
      console.log('Not logged in'); 

      //Infinite loop, kills my browser! 
      $state.go('login'); 
      $state.transitionTo('login'); 

      //Some suggestion 
      $state.go('login', { url: '/login'}); 

      //Doesn't work 
      $location.path('/login'); 

      //$location.path($state.href('login'); 
      console.log('Redirected'); 
     } 
    }); 
+1

'isUserLoggedIn'定義在哪裏? – Phil 2014-10-01 06:36:35

+0

我有一個身份驗證服務,由於某些官方原因,我從此代碼中跳過了它。它與默認路由很好地協作。 – 2014-10-01 06:38:17

回答

8

我們需要這裏,就是沒有自動跳轉,如果該國是已經是'登錄'了。

只是一個草擬的調整將是

$rootScope.$on('$stateChangeStart', function(e, toState , toParams 
               , fromState, fromParams) { 

    var isLogin = toState.name === "login"; 

    if(isLogin){ 

     return; // no need to redirect anymore 
    } 
    ... 

而且,我們應該叫$state.go('login');event.preventDefault();

... 
// also prevent default on redirect 
$state.go('login'); 
event.preventDefault(); 
... 

請檢查這個問答&一個How can I fix 'Maximum call stack size exceeded' AngularJSa plunker,有着相近的解決方案

+0

但我登錄的標誌實際上是一個函數,返回一個布爾值,它是一些服務的一部分。我如何在這種情況下使用它?另外,無處不在的循環是否會出現? – 2014-10-01 06:40:27

+0

你可以檢查這個答案:http://stackoverflow.com/a/24725180/1679310?並嘗試這個運動員http://plnkr.co/edit/JLABnz?p=preview?它應該顯示它如何工作。還有一些Extern服務'User'返回布爾值,但是在$ stateChangeStart中仍然評估邏輯if /重定向的位置。這有幫助嗎? – 2014-10-01 07:05:24

+0

太棒了! 'preventDefault'在事件處理程序中起作用,現在重定向到登錄頁面正常工作。但是,在我的註銷功能中,我使用$ state.go重定向到登錄頁面,它仍然導致循環。註銷由按鈕點擊觸發,因此我可以使用preventDefault。 – 2014-10-01 07:44:15

1

我用了類似的東西:

MyApp.run(['$rootScope', '$state', function ($rootScope, $state) { 
    // The event 
    $rootScope.$on('$stateChangeStart', function (e, toState, toParams, fromState, fromParams) { 
    // Is user already logged in? 
    var isUserLoggedIn = $rootScope.isUserLoggedIn(); 

    if (isUserLoggedIn) { 
     // don't let user visit login state, he's already logged in. 
     $state.go('home'); 
     // preventDefault as described in @radim's answer 
     e.preventDefault(); 
    } else if (toState.name === "login") { 
     // user is not logged in and is not going to login state right now, send him there first. 
     $state.go('login'); 
     // preventDefault as described in @radim's answer 
     e.preventDefault(); 
    } 
    }); 
}]); 
相關問題