本文转自:点击打开链接
今天还是来说一下angular中的路由模块。我们实际项目中,各个页面的切换是经常会与Auth相关的。比如我网站的后台,是需要登录过的用户才能进去,那么我们用angularJS做前端路由的时候应该怎么完成这个功能呢
------------------------------------------------------------------------
我们还是先设想一个最简单的场景吧。我们的应用有两个页面,登录页面后内容页面,要求是必须要验证登录成功后才能进入内容页面,下面我们一起来实现一下这个例子吧。当然我觉得我的方法可能会比较Low,但是学习阶段我们能先把功能做出来比什么都重要。
首先用bootstrap来写一个简单的登录页面吧。具体bootstrap代码我就不说了,我们关注的是angular在这里面如何用起来
<
div
class
=
"col-md-offset-3 col-md-4"
>
<
form
class
=
"form"
role
=
"form"
name
=
"loginForm"
ng-submit
=
"loginCheck()"
>
<
div
class
=
"form-group"
>
<
label
class
=
"control-label"
>用户名</
label
>
<
input
type
=
"text"
class
=
"form-control"
required
placeholder
=
"请输入管理员账号"
ng-model
=
"admin.username"
>
</
div
>
<
div
class
=
"form-group"
>
<
label
class
=
"control-label"
>密码</
label
>
<
input
type
=
"password"
class
=
"form-control"
ng-model
=
"admin.pwd"
required
placeholder
=
"请输入密码"
>
</
div
>
<
div
ng-show
=
"showError"
class
=
"alert alert-danger alert-dismissible"
role
=
"alert"
>
<
button
ng-click
=
"showError=false"
type
=
"button"
class
=
"close"
data-dismiss
=
"alert"
><
span
aria-hidden
=
"true"
>×</
span
><
span
class
=
"sr-only"
>关闭</
span
></
button
>
用户名或密码错误!!你还有一次机会
</
div
>
<
input
type
=
"submit"
class
=
"btn btn-primary btn-lg"
value
=
"登录"
ng-disabled
=
"loginForm.$invalid"
>
</
form
>
</
div
>
|
效果如下
id="iframe_0.3253765239649169" src="data:text/html;charset=utf8,%3Cimg%20id=%22img%22%20src=%22http://img.mukewang.com/54788faf000197b405000227.jpg?_=4576483%22%20style=%22border:none;max-width:1571px%22%3E%3Cscript%3Ewindow.onload%20=%20function%20()%20%7Bvar%20img%20=%20document.getElementById('img');%20window.parent.postMessage(%7BiframeId:'iframe_0.3253765239649169',width:img.width,height:img.height%7D,%20'http://www.cnblogs.com');%7D%3C/script%3E" frameborder="0" scrolling="no" style="border-width: initial; border-style: none; width: 500px; height: 227px;">
当然我之前还有一些css的布局,粘代码过去可能会出错哦,至少得在最外层加一个div class="row"
还可以看见,我给登录按钮加了个ng-disabled,当表单没有通过验证的时候是不能点登录的。
然后我加了一个提示的tips,用到了ng-show,在controller里会有一个showError的属性来控制它的显示,当验证账号密码错误时showError为true。
当我们验证出错的时候
id="iframe_0.5126796091336738" src="data:text/html;charset=utf8,%3Cimg%20id=%22img%22%20src=%22http://img.mukewang.com/547892c90001675104860298.jpg?_=4576483%22%20style=%22border:none;max-width:1571px%22%3E%3Cscript%3Ewindow.onload%20=%20function%20()%20%7Bvar%20img%20=%20document.getElementById('img');%20window.parent.postMessage(%7BiframeId:'iframe_0.5126796091336738',width:img.width,height:img.height%7D,%20'http://www.cnblogs.com');%7D%3C/script%3E" frameborder="0" scrolling="no" style="border-width: initial; border-style: none; width: 486px; height: 298px;">
接着我们来看一下路由
var
myApp = angular.module(
'myApp'
, [
'ui.router'
,
'myModule'
]);
myApp.run(
function
($rootScope, $state, $stateParams){
$rootScope.$state = $state;
$rootScope.$stateParams = $stateParams;
$rootScope.$state.isLogin =
false
;
});
myApp.config(
function
($stateProvider, $urlRouterProvider) {
$urlRouterProvider.otherwise(
'/login'
);
$stateProvider
.state(
'login'
,{
url :
'/login'
,
templateUrl :
'tpls/login.html'
,
controller :
'LoginController'
})
.state(
'index'
,{
url :
'/index'
,
templateUrl :
'tpls/index.html'
,
controllerProvider :
function
($rootScope){
if
($rootScope.$state.isLogin ==
false
){
$rootScope.$state.go(
'login'
);
}
return
function
(){};
}
});
}
|
因为在整个页面中我们都会用到登录状态,所以我把登录状态绑定到rootscope中,isLogin刚开始是false表示未登录。
接着看路由里面,login这个很简单,主要看index页面。
关 键的一步就是index的controller,在这里我选择用controllerProvider的方式来生成controller,可以看到我们最 后实际上是返回的一个空的function,但是在返回空controller之前(index页面还没有解析),我可以做一些事情,那就是验证权限啦!
如 果$rootScope.$state.isLogin为false也就是还没有登录,那就直接跳转到登录页面。跳转用到了$state里面的go方 法,go中的变量就是我们每个页面的状态名,也就是state的第一个参数。我是go('login'),它就跳转到state的第一个参数是login 的那个页面去了,也就是登录页面。换句话说,如果我们登录提交后验证没有成功,当我们在地址栏输入/index的时候会跳到登录页面的哦。
那么再来看看我们的验证模块。
myModule
.controller(
'LoginController'
,
function
($scope,$rootScope,$http){
$scope.showError =
false
;
$scope.loginCheck =
function
(){
var
username = $scope.admin.username;
var
pwd = $scope.admin.pwd;
var
loginSuccess =
false
;
http.get(
'/acm-admin/data/user.json'
)
.success(
function
(response){
for
(
var
i=0; i<response.length; i++){
if
(response[i].username == username && response[i].pwd == pwd){
$rootScope.$state.isLogin =
true
;
loginSuccess =
true
;
$rootScope.$state.go(
'index'
);
}
}
if
(!loginSuccess){
$scope.showError =
true
;
}
});
}
})
|
初 始化我们给showError一个值为false,不要显示错误提示框。然后来看看验证登录的这个方法。首先获取到用户输入的用户名和密码,设置登录成功 的状态的false。然后通过$http.get,到指定的地方去取一个json文件,很显然这是个假数据,我们把预设的用户名和密码存放到这个json 文件中。取出预设的用户名和密码之后就和用户输入的来进行对比,相信这都很简单,大家肯定能看明白。如果用户名和密码都对上了,那么就把登录状态设置为 true,登录成功也设置为true。然后用$state的go方法跳转到Index页面。
如果登录信息验证失败,那么就把showError赋为true,页面上就会显示提示信息咯。
----------------------------------------------------------------------------
怎 么样,很简单吧。当然还有其它实现这一功能的方法,而且我上述的方法很可能还有诸多安全隐患,而且模块的分工也是不明确的,淡然实际部署不推荐这么写了。 我们可以优化改进的地方很多,比如验证的模块是不是应该独立出去呢,或者用户有没有什么办法能轻易绕过这个登录保护呢?这就留待小伙伴们自己探究了……继 续学习angular去了,大家晚安!!