網站訪問量統計功能的實現


實現方法:攔截器+session存儲

攔截器初始化時,即在@PostConstruct注解的initMethod方法中讀取數據庫的isystem對象,該對象記錄了網站訪問量的信息。

攔截器銷毀時,即在@PreDestroy注解的destroyMethod方法中向數據庫更新isystem對象。

攔截器的初始化和銷毀都只有在應用啟動和關閉的時候才被調用,因此減少了對數據庫的訪問。

SpringMVC中,每一次請求控制器,都會先執行攔截器的preHandle方法,在該方法內先查看session中的一個標志accessedFlag,如果該標志不存在,說明此次會話沒有被統計,因此在isystem對象中增加一次訪問量,並向session添加標志accessedFlag,下一次訪問時,該session不再添加訪問量,即一個session算訪問一次。並且在session中存儲isystem對象,並於網頁顯示數據的調用。

為了保證並發的正確性,局部代碼塊使用同步鎖,見下面紅色部分。

總結:攔截器有一個靜態屬性isystem,用戶第一次請求時,都會更新這個屬性的值。用戶的每一次請求都會把該屬性放入到用戶的session中去。因此,B用戶第一次訪問后,A用戶第二次訪問時(和第一次訪問共享一個session),A用戶的session中的isystem也會被更新。

攔截器類如下:

package com.wuchao.utils.interceptor;

import javax.annotation.PostConstruct;
import javax.annotation.PreDestroy;
import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.log4j.Logger;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.handler.HandlerInterceptorAdapter;
import com.wuchao.blog.system.bo.intf.IsystemBo;
import com.wuchao.blog.system.po.Isystem;
import com.wuchao.blog.user.controller.LoginController;
import com.wuchao.utils.config.SpringContextHolder;

public class RequestInterceptor extends HandlerInterceptorAdapter {
	private static Logger log = Logger.getLogger(LoginController.class);  
	
	@Resource(name="isystemBo")
	public IsystemBo isystemBo;	
	@Resource(name="springContextHolder")
	SpringContextHolder  springContextHolder;
	
	public static Isystem isystem;

	//請求控制器前,處理請求
	@Override
    public boolean preHandle(HttpServletRequest request,
            HttpServletResponse response, Object handler) throws Exception {
		try {
			log.info("RequestInterceptor");
			//網站訪問量+1
			if(isystem==null) {
				log.info("isystem==null");
				isystem = isystemBo.getIsystemByDefault();
			}
			if(isystem!=null) {
				//每一個session理論上只能記一次訪問,因此在session里面存一個訪問標記,如果存在標記,則不再計算此次訪問
				String accessedFlag = "accessedFlag";
				if(request.getSession().getAttribute("accessedFlag")==null) {
					//同步鎖
					synchronized(this) {
						log.info("網站訪問量+1,存入session");
						isystem.setAmountOfAccess(isystem.getAmountOfAccess()+1);
						request.getSession().setAttribute("Isystem", isystem);
						request.getSession().setAttribute("accessedFlag", accessedFlag);
					}
					
				}
			}	
			
		}catch(Exception e) {
			e.printStackTrace();
			throw e;
		}

        return true;
    }

	@Override
	public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler,
			ModelAndView modelAndView) throws Exception {
		
	}

	@Override
	public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex)
			throws Exception {
		
	}
	
	/*
	 * 實例化時執行的操作
	 */
	@PostConstruct  
    public void initMethod() throws Exception {  
        log.info("initMethod 被執行");  
        //加載isystem對象
		if(isystem==null) {
			log.info("加載isystem");
			isystem = isystemBo.getIsystemByDefault();
		}
    } 
	/*
	 * 銷毀前執行的操作
	 */
    @PreDestroy  
    public void destroyMethod() throws Exception {  
    	log.info("destroyMethod 被執行");  
    	//保存isystem
    	if(isystem!=null) {
    		isystemBo.saveIsystem(isystem);
    	}
    }  
}

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM