acegi 用户登录成功后记录用户登录日志
2009-07-24 15:46
302 查看
最近整理了一下开发工作,在开发过程中,对用户的登录日志进行记录,是每个系统最基础的工作,faceye使用了acegi作为基础安全框架,也需
要对用户登录日志进行记录,查阅了一下网上的资料,有提到使用Spring的ApplicationEvent来做的,主要是做一个
ApplicationListener,判断event类型,如果是用户登录成功event,就做日志记录.
看了一下,不太喜欢,于是,打开acegi的源码来看了一下,顺便说一下,这里的源码指的是acegi2.0.
当前使用到的用户登录,主要有两种类型,一种输入用户名密码登录,另一种是根据cookie记录进行登录,所以,要针对这两个Filter进行修改.
通常,我们使用的登录验证器是这个:AuthenticationProcessingFilter
所做的配置为:
<beanid="authenticationProcessingFilter"
class="org.springframework.security.ui.webapp.AuthenticationProcessingFilter">
....
</bean>
那么,在这里,就需要对这个类进行一下重载
在这个类中,要看其父类中的:AbstractProcessingFilter的doFilterHttp方法
整体方法如下:
viewsource
print
?
在这里,acegi已经给我们预留了登录成功后置事件接口,successfulAuthentication(...)
在这个方法里面,调用了一个空方法:
onSuccessfulAuthentication(request,response,authResult);
这个方法,在acegi的代码中,是一个懒汉型的,它只会在用户登录成功后被调用,如果用户登录失败,会相应的调用方法:
unsuccessfulAuthentication(HttpServletRequestrequest,HttpServletResponseresponse,AuthenticationExceptionfailed)
其中对应的后置方法为:
onUnsuccessfulAuthentication(request,response,failed);
这两个方法,都为懒汉型的,要对用户的登录动作(成功,失败)进行记录,只需要重载这两个方法即可.
所以,进行如下实现:
viewsource
print
?
以此来记录用户的登录日志,当然,还可以实现相应的:
onUnsuccessfulAuthentication(request,response,failed);
与上述代码类似.
同时,用户还可能通过RemeberMe功能进行自动登录,这时,就需要对另外一个进行重载,代码如下:
viewsource
print
?
至此,便可以完整的记录用户的登录日志了.
要对用户登录日志进行记录,查阅了一下网上的资料,有提到使用Spring的ApplicationEvent来做的,主要是做一个
ApplicationListener,判断event类型,如果是用户登录成功event,就做日志记录.
看了一下,不太喜欢,于是,打开acegi的源码来看了一下,顺便说一下,这里的源码指的是acegi2.0.
当前使用到的用户登录,主要有两种类型,一种输入用户名密码登录,另一种是根据cookie记录进行登录,所以,要针对这两个Filter进行修改.
通常,我们使用的登录验证器是这个:AuthenticationProcessingFilter
所做的配置为:
<beanid="authenticationProcessingFilter"
class="org.springframework.security.ui.webapp.AuthenticationProcessingFilter">
....
</bean>
那么,在这里,就需要对这个类进行一下重载
在这个类中,要看其父类中的:AbstractProcessingFilter的doFilterHttp方法
整体方法如下:
01.
public
void
doFilterHttp(HttpServletRequestrequest,HttpServletResponseresponse,FilterChainchain)
throws
IOException,
02.
ServletException{
03.
if
(requiresAuthentication(request,response)){
04.
if
(logger.isDebugEnabled()){
05.
logger.debug(
"Requestistoprocessauthentication"
);
06.
}
07.
AuthenticationauthResult;
08.
try
{
09.
onPreAuthentication(request,response);
10.
authResult=attemptAuthentication(request);
11.
}
12.
catch
(AuthenticationExceptionfailed){
13.
//Authenticationfailed
14.
unsuccessfulAuthentication(request,response,failed);
15.
return
;
16.
}
17.
//Authenticationsuccess
18.
if
(continueChainBeforeSuccessfulAuthentication){
19.
chain.doFilter(request,response);
20.
}
21.
successfulAuthentication(request,response,authResult);
22.
return
;
23.
}
24.
chain.doFilter(request,response);
25.
}
在这里,acegi已经给我们预留了登录成功后置事件接口,successfulAuthentication(...)
在这个方法里面,调用了一个空方法:
onSuccessfulAuthentication(request,response,authResult);
这个方法,在acegi的代码中,是一个懒汉型的,它只会在用户登录成功后被调用,如果用户登录失败,会相应的调用方法:
unsuccessfulAuthentication(HttpServletRequestrequest,HttpServletResponseresponse,AuthenticationExceptionfailed)
其中对应的后置方法为:
onUnsuccessfulAuthentication(request,response,failed);
这两个方法,都为懒汉型的,要对用户的登录动作(成功,失败)进行记录,只需要重载这两个方法即可.
所以,进行如下实现:
01.
/**
02.
*
03.
*
04.
*@author:haipeng
05.
*@CopyRight:www.faceye.com
06.
*@System:www.faceye.com
07.
*@Create2009-7-20
08.
*@Packagecom.faceye.components.security.intercept
09.
*@Description:
10.
*/
11.
public
class
UserAuthenticationProcessingFilter
extends
AuthenticationProcessingFilter
12.
{
13.
private
IUserServiceuserService=
null
;
14.
private
IUserLoginLogServiceuserLoginLogService=
null
;
15.
public
IUserLoginLogServicegetUserLoginLogService()
16.
{
17.
return
userLoginLogService;
18.
}
19.
20.
public
void
setUserLoginLogService(IUserLoginLogServiceuserLoginLogService)
21.
{
22.
this
.userLoginLogService=userLoginLogService;
23.
}
24.
public
IUserServicegetUserService()
25.
{
26.
return
userService;
27.
}
28.
29.
public
void
setUserService(IUserServiceuserService)
30.
{
31.
this
.userService=userService;
32.
}
33.
34.
protected
void
onSuccessfulAuthentication(HttpServletRequestrequest,HttpServletResponseresponse,AuthenticationauthResult)
throws
IOException
35.
{
36.
if
(
null
!=authResult)
37.
{
38.
Stringusername=
null
;
39.
Objectobj=authResult.getPrincipal();
40.
if
(obj
instanceof
UserDetails){
41.
username=((UserDetails)obj).getUsername();
42.
}
else
{
43.
username=obj.toString();
44.
}
45.
WebAuthenticationDetailswebDetails=(WebAuthenticationDetails)authResult.getDetails();
46.
Stringip=webDetails.getRemoteAddress();
47.
if
(StringUtils.isNotEmpty(username))
48.
{
49.
Useruser=(User)((UserDetailsService)
this
.getUserService()).loadUserByUsername(username);
50.
if
(
null
!=user)
51.
{
52.
UserLoginLogentity=
new
UserLoginLog();
53.
entity.setUser(user);
54.
entity.setIp(ip);
55.
this
.getUserLoginLogService().save(entity);
56.
}
57.
}
58.
}
59.
}
60.
}
以此来记录用户的登录日志,当然,还可以实现相应的:
onUnsuccessfulAuthentication(request,response,failed);
与上述代码类似.
同时,用户还可能通过RemeberMe功能进行自动登录,这时,就需要对另外一个进行重载,代码如下:
01.
/**
02.
*
03.
*
04.
*@author:haipeng
05.
*@CopyRight:www.faceye.com
06.
*@System:www.faceye.com
07.
*@Create2009-7-20
08.
*@Packagecom.faceye.components.security.intercept
09.
*@Description:
10.
*/
11.
public
class
UserRememberMeProcessingFilter
extends
RememberMeProcessingFilter
12.
{
13.
private
IUserServiceuserService=
null
;
14.
private
IUserLoginLogServiceuserLoginLogService=
null
;
15.
public
IUserServicegetUserService()
16.
{
17.
return
userService;
18.
}
19.
public
void
setUserService(IUserServiceuserService)
20.
{
21.
this
.userService=userService;
22.
}
23.
public
IUserLoginLogServicegetUserLoginLogService()
24.
{
25.
return
userLoginLogService;
26.
}
27.
public
void
setUserLoginLogService(IUserLoginLogServiceuserLoginLogService)
28.
{
29.
this
.userLoginLogService=userLoginLogService;
30.
}
31.
protected
void
onSuccessfulAuthentication(HttpServletRequestrequest,HttpServletResponseresponse,
32.
AuthenticationauthResult){
33.
34.
if
(
null
!=authResult)
35.
{
36.
Stringusername=
null
;
37.
Objectobj=authResult.getPrincipal();
38.
if
(obj
instanceof
UserDetails){
39.
username=((UserDetails)obj).getUsername();
40.
}
else
{
41.
username=obj.toString();
42.
}
43.
WebAuthenticationDetailswebDetails=(WebAuthenticationDetails)authResult.getDetails();
44.
Stringip=webDetails.getRemoteAddress();
45.
if
(StringUtils.isNotEmpty(username))
46.
{
47.
Useruser=(User)((UserDetailsService)
this
.getUserService()).loadUserByUsername(username);
48.
if
(
null
!=user)
49.
{
50.
UserLoginLogentity=
new
UserLoginLog();
51.
entity.setUser(user);
52.
entity.setIp(ip);
53.
this
.getUserLoginLogService().save(entity);
54.
}
55.
}
56.
}
57.
}
58.
}
至此,便可以完整的记录用户的登录日志了.
相关文章推荐
- acegi 用户登录成功后记录用户登录日志
- 记录用户登录日志
- 按时按登录IP记录Linux所有用户操作日志
- 记录远程用户登录日志
- 在Linux下记录所有用户的登录和操作日志
- 按时按登录IP记录Linux所有用户操作日志的方法(附脚本)
- 通过登入IP记录Linux所有用户登录所操作的日志
- 登录记录以及操作登记,每个用户登录的操作均被记录在日志!
- Postgres日志记录用户登录退出信息
- 使用触发器实现记录oracle用户登录失败信息到alert.log日志文件
- 按登录IP记录Linux所有用户操作日志
- 按时按登录IP记录Linux所有用户操作日志的方法(附脚本)
- 记录远程桌面连接登录日志(去DOS黑窗) | 让远程桌面支持多用户
- 在Linux下记录所有用户的登录和操作日志
- 按时按登录IP记录Linux所有用户操作日志的方法
- spring security3 记录用户登录成功后的登录时间
- 通过cmd脚本记录Windows远程桌面用户登录日志
- 通过登入IP记录Linux所有用户登录所操作的日志
- Linux 记录所有用户登录和操作的详细日志
- ssh密钥登录,所选的用户密钥未在远程主机上注册;ssh登录日志,成功登录,失败登录