Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/angularjs/23.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Angularjs 根据条件重定向到某个路由_Angularjs_Ngroute - Fatal编程技术网

Angularjs 根据条件重定向到某个路由

Angularjs 根据条件重定向到某个路由,angularjs,ngroute,Angularjs,Ngroute,我正在编写一个小AngularJS应用程序,它有一个登录视图和一个主视图,配置如下: $routeProvider .when('/main' , {templateUrl: 'partials/main.html', controller: MainController}) .when('/login', {templateUrl: 'partials/login.html', controller: LoginController}) .otherwise({redirectTo:

我正在编写一个小AngularJS应用程序,它有一个登录视图和一个主视图,配置如下:

$routeProvider
 .when('/main' , {templateUrl: 'partials/main.html',  controller: MainController})
 .when('/login', {templateUrl: 'partials/login.html', controller: LoginController})
 .otherwise({redirectTo: '/login'});
My LoginController检查用户/通行证组合,并在$rootScope上设置一个属性,反映以下内容:

function LoginController($scope, $location, $rootScope) {
 $scope.attemptLogin = function() {
   if ( $scope.username == $scope.password ) { // test
        $rootScope.loggedUser = $scope.username;
        $location.path( "/main" );
    } else {
        $scope.loginError = "Invalid user/pass.";
    }
}
一切正常,但如果我访问
http://localhost/#/main
我最终绕过了登录屏幕。我想写一些类似于“每当路由改变时,如果$rootScope.loggedUser为null,则重定向到/login”


。。。等待我能听听路线的变化吗?无论如何,我会发布这个问题并继续查找。

在深入阅读了一些文档和源代码之后,我想我已经找到了工作。也许这对其他人有用

我在模块配置中添加了以下内容:

angular.module(...)
 .config( ['$routeProvider', function($routeProvider) {...}] )
 .run( function($rootScope, $location) {

    // register listener to watch route changes
    $rootScope.$on( "$routeChangeStart", function(event, next, current) {
      if ( $rootScope.loggedUser == null ) {
        // no logged user, we should be going to #login
        if ( next.templateUrl != "partials/login.html" ) {
          // not going to #login, we should redirect now
          $location.path( "/login" );
        }
      }         
    });
 })

奇怪的是,我不得不测试部分名称(
login.html
),因为“下一个”路由对象没有url或其他内容。也许有更好的方法吗?

实现登录重定向的另一种方法是使用事件和拦截器。本文描述了一些额外的优点,如检测何时需要登录、排队请求以及在登录成功后重播请求


您可以试用一个工作演示并查看演示源。

我也一直在尝试这样做。在与同事合作后,提出了另一个更简单的解决方案。我在
$location.path()
上安装了一块手表。这就是诀窍。我刚刚开始学习AngularJS,发现它更清晰易读

$scope.$watch(function() { return $location.path(); }, function(newValue, oldValue){  
    if ($scope.loggedIn == false && newValue != '/login'){  
            $location.path('/login');  
    }  
});

我用拦截器。我已经创建了一个库文件,可以添加到index.html文件中。这样,您就可以对rest服务调用进行全局错误处理,而不必单独关心所有错误。接下来,我还粘贴了我的基本身份验证登录库。在那里你可以看到,我还检查了401错误并重定向到另一个位置。请参见lib/ea-basic-auth-login.js

lib/http错误处理.js

/**
* @ngdoc overview
* @name http-error-handling
* @description
*
* Module that provides http error handling for apps.
*
* Usage:
* Hook the file in to your index.html: <script src="lib/http-error-handling.js"></script>
* Add <div class="messagesList" app-messages></div> to the index.html at the position you want to
* display the error messages.
*/
(function() {
'use strict';
angular.module('http-error-handling', [])
    .config(function($provide, $httpProvider, $compileProvider) {
        var elementsList = $();

        var showMessage = function(content, cl, time) {
            $('<div/>')
                .addClass(cl)
                .hide()
                .fadeIn('fast')
                .delay(time)
                .fadeOut('fast', function() { $(this).remove(); })
                .appendTo(elementsList)
                .text(content);
        };

        $httpProvider.responseInterceptors.push(function($timeout, $q) {
            return function(promise) {
                return promise.then(function(successResponse) {
                    if (successResponse.config.method.toUpperCase() != 'GET')
                        showMessage('Success', 'http-success-message', 5000);
                    return successResponse;

                }, function(errorResponse) {
                    switch (errorResponse.status) {
                        case 400:
                            showMessage(errorResponse.data.message, 'http-error-message', 6000);
                                }
                            }
                            break;
                        case 401:
                            showMessage('Wrong email or password', 'http-error-message', 6000);
                            break;
                        case 403:
                            showMessage('You don\'t have the right to do this', 'http-error-message', 6000);
                            break;
                        case 500:
                            showMessage('Server internal error: ' + errorResponse.data.message, 'http-error-message', 6000);
                            break;
                        default:
                            showMessage('Error ' + errorResponse.status + ': ' + errorResponse.data.message, 'http-error-message', 6000);
                    }
                    return $q.reject(errorResponse);
                });
            };
        });

        $compileProvider.directive('httpErrorMessages', function() {
            return {
                link: function(scope, element, attrs) {
                    elementsList.push($(element));
                }
            };
        });
    });
})();
.http-error-message {
    background-color: #fbbcb1;
    border: 1px #e92d0c solid;
    font-size: 12px;
    font-family: arial;
    padding: 10px;
    width: 702px;
    margin-bottom: 1px;
}

.http-error-validation-message {
    background-color: #fbbcb1;
    border: 1px #e92d0c solid;
    font-size: 12px;
    font-family: arial;
    padding: 10px;
    width: 702px;
    margin-bottom: 1px;
}

http-success-message {
    background-color: #adfa9e;
    border: 1px #25ae09 solid;
    font-size: 12px;
    font-family: arial;
    padding: 10px;
    width: 702px;
    margin-bottom: 1px;
}
index.html

<!doctype html>
<html lang="en" ng-app="cc">
    <head>
        <meta charset="utf-8">
        <title>yourapp</title>
        <link rel="stylesheet" href="css/http-error-handling.css"/>
    </head>
    <body>

<!-- Display top tab menu -->
<ul class="menu">
  <li><a href="#/user">Users</a></li>
  <li><a href="#/vendor">Vendors</a></li>
  <li><logout-link/></li>
</ul>

<!-- Display errors -->
<div class="http-error-messages" http-error-messages></div>

<!-- Display partial pages -->
<div ng-view></div>

<!-- Include all the js files. In production use min.js should be used -->
<script src="lib/angular114/angular.js"></script>
<script src="lib/angular114/angular-resource.js"></script>
<script src="lib/http-error-handling.js"></script>
<script src="js/app.js"></script>
<script src="js/services.js"></script>
<script src="js/controllers.js"></script>
<script src="js/filters.js"></script>

你的应用程序

lib/ea basic auth login.js

/**
* @ngdoc overview
* @name http-error-handling
* @description
*
* Module that provides http error handling for apps.
*
* Usage:
* Hook the file in to your index.html: <script src="lib/http-error-handling.js"></script>
* Add <div class="messagesList" app-messages></div> to the index.html at the position you want to
* display the error messages.
*/
(function() {
'use strict';
angular.module('http-error-handling', [])
    .config(function($provide, $httpProvider, $compileProvider) {
        var elementsList = $();

        var showMessage = function(content, cl, time) {
            $('<div/>')
                .addClass(cl)
                .hide()
                .fadeIn('fast')
                .delay(time)
                .fadeOut('fast', function() { $(this).remove(); })
                .appendTo(elementsList)
                .text(content);
        };

        $httpProvider.responseInterceptors.push(function($timeout, $q) {
            return function(promise) {
                return promise.then(function(successResponse) {
                    if (successResponse.config.method.toUpperCase() != 'GET')
                        showMessage('Success', 'http-success-message', 5000);
                    return successResponse;

                }, function(errorResponse) {
                    switch (errorResponse.status) {
                        case 400:
                            showMessage(errorResponse.data.message, 'http-error-message', 6000);
                                }
                            }
                            break;
                        case 401:
                            showMessage('Wrong email or password', 'http-error-message', 6000);
                            break;
                        case 403:
                            showMessage('You don\'t have the right to do this', 'http-error-message', 6000);
                            break;
                        case 500:
                            showMessage('Server internal error: ' + errorResponse.data.message, 'http-error-message', 6000);
                            break;
                        default:
                            showMessage('Error ' + errorResponse.status + ': ' + errorResponse.data.message, 'http-error-message', 6000);
                    }
                    return $q.reject(errorResponse);
                });
            };
        });

        $compileProvider.directive('httpErrorMessages', function() {
            return {
                link: function(scope, element, attrs) {
                    elementsList.push($(element));
                }
            };
        });
    });
})();
.http-error-message {
    background-color: #fbbcb1;
    border: 1px #e92d0c solid;
    font-size: 12px;
    font-family: arial;
    padding: 10px;
    width: 702px;
    margin-bottom: 1px;
}

.http-error-validation-message {
    background-color: #fbbcb1;
    border: 1px #e92d0c solid;
    font-size: 12px;
    font-family: arial;
    padding: 10px;
    width: 702px;
    margin-bottom: 1px;
}

http-success-message {
    background-color: #adfa9e;
    border: 1px #25ae09 solid;
    font-size: 12px;
    font-family: arial;
    padding: 10px;
    width: 702px;
    margin-bottom: 1px;
}
登录时也可以这样做。这里是重定向的答案($location.path(“/login”))

/**
*@ngdoc概述
*@name ea基本身份验证登录
*@说明
*
*为应用程序提供http基本身份验证的模块。
*
*用法:
*将文件挂接到index.html:
*将标签放入html登录页面
*将标记放在html页面中,用户必须单击该页面才能注销
*/
(功能(){
"严格使用",;
angular.module('ea-basic-auth-login',['ea-base64-login'])
.config(['$httpProvider',函数($httpProvider){
var ea_basic_auth_login_interceptor=['$location','$q',function($location,$q){
功能成功(响应){
返回响应;
}
功能错误(响应){
如果(response.status==401){
$location.path('/login');
返回$q.reject(响应);
}
否则{
返回$q.reject(响应);
}
}
返回函数(承诺){
回报承诺。然后(成功,错误);
}
}];
$httpProvider.responseInterceptors.push(ea_basic_auth_login_interceptor);
}])
.controller('EALoginCtrl'、['$scope'、'$http'、'$location'、'EABase64Login',函数($scope、$http、$location、EABase64Login){
$scope.login=函数(){
$http.defaults.headers.common['Authorization']='Basic'+EABase64Login.encode($scope.email+':'+$scope.password);
$location.path(“/user”);
};
$scope.logout=函数(){
$http.defaults.headers.common['Authorization']=未定义;
$location.path(“/login”);
};
}])
.directive('eaLoginForm',[function(){
返回{
限制:'E',
模板:“”+
'' +
'' +
“
”+ '' + “
”+ “登录”+ '' + '', 替换:正确 }; }]) .directive('eaLogoutLink',[function(){ 返回{ 限制:'E', 模板:“注销”, 替换:正确 } }]); 模块('ea-base64-login',[])。 工厂('EABase64Login',函数(){ var keyStr='ABCDEFGHIJKLMNOP'+ “qrstuvxyzabcdef”+ “ghijklmnopqrstuv”+ “wxyz0123456789+/”+ '='; 返回{ 编码:功能(输入){ var输出=”; 变量chr1,chr2,chr3=“”; 变量enc1、enc2、enc3、enc4=“”; var i=0; 做{ chr1=input.charCodeAt(i++); chr2=input.charCodeAt(i++); chr3=input.charCodeAt(i++); enc1=chr1>>2; enc2=((chr1&3)>4); enc3=((chr2&15)>6); enc4=chr3&63; if(isNaN(chr2)){ enc3=enc4=64; }否则如果(isNaN(chr3)){ enc4=64; } 输出=输出+ 钥匙字符(附件1)+ 钥匙字符(附件2)+ 钥匙字符(附件3)+ 钥匙字符(附件4); chr1=chr2=chr3=“”; enc1=enc2=enc3=enc4=“”; }而(i$routeProvider .when('/', { templateUrl: 'views/home.html', controller: 'HomeCtrl' }) .when('/login', { templateUrl: 'views/login.html', controller: 'LoginCtrl', publicAccess: true })
angular.module('myModule').run(function($rootScope, $location, user, $route) {

    var routesOpenToPublic = [];
    angular.forEach($route.routes, function(route, path) {
        // push route onto routesOpenToPublic if it has a truthy publicAccess value
        route.publicAccess && (routesOpenToPublic.push(path));
    });

    $rootScope.$on('$routeChangeStart', function(event, nextLoc, currentLoc) {
        var closedToPublic = (-1 === routesOpenToPublic.indexOf($location.path()));
        if(closedToPublic && !user.isLoggedIn()) {
            $location.path('/login');
        }
    });
})
// AuthService.js

  // auth successful
  $rootScope.user = user
// AdminController.js

.config(function ($routeProvider) {
  $routeProvider.when('/admin', {
    controller: 'AdminController',
    auth: function (user) {
      return user && user.isAdmin
    }
  })
})
// index.js

.run(function ($rootScope, $location) {
  $rootScope.$on('$routeChangeStart', function (ev, next, curr) {
    if (next.$$route) {
      var user = $rootScope.user
      var auth = next.$$route.auth
      if (auth && !auth(user)) { $location.path('/') }
    }
  })
})
 ---- app.js -----

 var app = angular.module('myApp', ['ui.router']);

 app.config(function ($stateProvider, $urlRouterProvider) {

    // Otherwise
    $urlRouterProvider.otherwise("/");

    $stateProvider
            // Index will decide if redirects to Login or Dashboard view
            .state("index", {
                 url: ""
                 controller: 'index_controller'
              })
            .state('dashboard', {
                url: "/dashboard",
                controller: 'dashboard_controller',
                templateUrl: "views/dashboard.html"
              })
            .state('login', {
                url: "/login",
                controller: 'login_controller',
                templateUrl: "views/login.html"
              });
 });

 // Associate the $state variable with $rootScope in order to use it with any controller
 app.run(function ($rootScope, $state, $stateParams) {
        $rootScope.$state = $state;
        $rootScope.$stateParams = $stateParams;
    });

 app.controller('index_controller', function ($scope, $log) {

    /* Check if the user is logged prior to use the next code */

    if (!isLoggedUser) {
        $log.log("user not logged, redirecting to Login view");
        // Redirect to Login view 
        $scope.$state.go("login");
    } else {
        // Redirect to dashboard view 
        $scope.$state.go("dashboard");
    }

 });

----- HTML -----

<!DOCTYPE html>
<html>
    <head>
        <title>My WebSite</title>

        <meta charset="utf-8">
        <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
        <meta name="description" content="MyContent">
        <meta name="viewport" content="width=device-width, initial-scale=1">

        <script src="js/libs/angular.min.js" type="text/javascript"></script>
        <script src="js/libs/angular-ui-router.min.js" type="text/javascript"></script>
        <script src="js/app.js" type="text/javascript"></script>

    </head>
    <body ng-app="myApp">
        <div ui-view></div>
    </body>
</html>
    $routeProvider
 .when('/main' , {templateUrl: 'partials/main.html',  controller: MainController})
 .when('/login', {templateUrl: 'partials/login.html', controller: LoginController}).
 .when('/login', {templateUrl: 'partials/index.html', controller: IndexController})
 .otherwise({redirectTo: '/index'});
app.config(["$routeProvider", function($routeProvider) {
    $routeProvider.when("/foo", {
        controller: "Foo",
        resolve: {
            controller: ["$q", function($q) {
                var deferred = $q.defer();
                require(["path/to/controller/Foo"], function(Foo) {
                    // now controller is loaded
                    deferred.resolve();
                });
                return deferred.promise;
            }]
        }
    });
}]);

app.run(["$rootScope", function($rootScope) {
    $rootScope.$on("$routeChangeStart", function(event, next, current) {
        console.log(next.$$route, next.locals); // undefined, undefined
    });
}]);
app.config(["$routeProvider", function($routeProvider) {
    $routeProvider.when("/foo", {
        controller: "Foo",
        resolve: {
            controller: ["$q", function($q) {
                var deferred = $q.defer();
                require(["path/to/controller/Foo"], function(Foo) {
                    // now controller is loaded
                    deferred.resolve();
                });
                return deferred.promise;
            }],
            access: ["$q", function($q) {
                var deferred = $q.defer();
                if (/* some logic to determine access is granted */) {
                    deferred.resolve();
                } else {
                    deferred.reject("You have no access rights to go there");
                }
                return deferred.promise;
            }],
        }
    });
}]);

app.run(["$rootScope", function($rootScope) {
    $rootScope.$on("$routeChangeError", function(event, next, current, error) {
        console.log("Error: " + error); // "Error: You have no access rights to go there"
    });
}]);
.run(["$rootScope", "$state", function($rootScope, $state) {

      $rootScope.$on('$locationChangeStart', function(event, next, current) {
        if (!$rootScope.loggedUser == null) {
          $state.go('home');
        }    
      });
}])