最近公司的網站須要添加用戶訪問記錄功能,因爲使用了nginx請求轉發直接經過HttpServletRequest沒法獲取用戶真實Iphtml
關於nginx獲取真實IP的資料 http://www.javashuo.com/article/p-tvzjkzsk-kr.htmlnginx
在nginx.conf配置文件中web
location / {
proxy_pass ip;
index ak47.html index.html index.htm;
proxy_redirect off;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
# 動態請求的轉發
location ~ \.(jsp|do)$ {
proxy_pass http://10.30.100.126:8080;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
而後在代碼中加入如下spring
public final class NetworkUtil {
public static String getIpAddr(HttpServletRequest request) {
String fromSource = "X-Real-IP";
String ip = request.getHeader("X-Real-IP");
if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
ip = request.getHeader("X-Forwarded-For");
fromSource = "X-Forwarded-For";
}
if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
ip = request.getHeader("Proxy-Client-IP");
fromSource = "Proxy-Client-IP";
}
if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
ip = request.getHeader("WL-Proxy-Client-IP");
fromSource = "WL-Proxy-Client-IP";
}
if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
ip = request.getRemoteAddr();
fromSource = "request.getRemoteAddr";
}
return ip;
}
}
用戶登陸時間就是subject.login(token);成功的時間數據庫
退出時間就是執行logout的時間,可是shiro封裝的很完美,怎麼在執行logout以後往數據庫中插入退出時間呢apache
shiro執行logout時會調用LogoutFilter,咱們能夠寫一個繼承它就能夠進行相關操做了session
@Component
public class SystemLogoutFilter extends LogoutFilter {
@Override
protected boolean preHandle(ServletRequest request, ServletResponse response) throws Exception {
//在這裏執行退出系統前須要清空的數據
Subject subject=getSubject(request,response);
//Session session = subject.getSession();
String redirectUrl=getRedirectUrl(request,response,subject);
ServletContext context= request.getServletContext();
try {
subject.logout();
context.removeAttribute("error");
}catch (SessionException e){
e.printStackTrace();
}
issueRedirect(request,response,redirectUrl);
return false;
}
}
而後在xml配置文件中jsp
<!--Spring整合shiro--> <bean id="SystemLogoutFilter" class="com.smart.service.SystemLogoutFilter"> <property name="redirectUrl" value="/login.do" /> </bean> <!-- 配置shiro的過濾器工廠類,id- shiroFilter要和咱們在web.xml中配置的過濾器一致 --> <bean id="shiroFilter" class="org.apache.shiro.spring.web.ShiroFilterFactoryBean"> <!-- 調用咱們配置的權限管理器 --> <property name="securityManager" ref="securityManager" /> <!-- 配置咱們的登陸請求地址 --> <property name="loginUrl" value="/login.do" /> <!-- 配置咱們在登陸頁登陸成功後的跳轉地址,若是你訪問的是非/login地址,則跳到您訪問的地址 --> <property name="successUrl" value="/maSystem.do" /> <!-- 若是您請求的資源再也不您的權限範圍,則跳轉到/403請求地址 --> <property name="unauthorizedUrl" value="/error.do" /> <property name="filters"> <map> <entry key="logout" value-ref="SystemLogoutFilter" /> </map> </property> <!-- 權限配置 --> <property name="filterChainDefinitions"> <value> <!-- anon表示此地址不須要任何權限便可訪問 --> /error.jsp=anon /login.do=anon /logout=logout <!--全部的請求(除去配置的靜態資源請求或請求地址爲anon的請求)都要經過登陸驗證,若是未登陸則跳到/login --> /** = authc </value> </property> </bean> <bean id="logoutFilter" class="org.apache.shiro.web.filter.authc.LogoutFilter"> <property name="redirectUrl" value="/login.do" /> </bean>
用戶退出登陸時間都有了,根據sessionId做爲惟一標識便可ide