2016-12-05 58 views
0

我正在使用攔截器來使用標誌變量獲取mongodb連接的狀態。 MongoDB正試圖在應用程序啓動時進行連接,並且正在設置一個布爾標誌。此標誌值已經在登錄時在會話範圍中設置。我使用攔截器從會話中獲取標誌值,如果標誌爲false,則不想將請求路由到控制器。希望我簡要解釋了我的問題。編寫inteceptor以防止請求在特定條件下路由到控制器

因此,我編寫了一個攔截器,它只根據標記變量攔截一些請求映射URL。如果flag變量爲true,則控制器方法執行並填充模型數據,如果flag爲false,則請求URL頁面時應顯示一些錯誤消息給請求的URL頁面。

我正面臨着在prehandle()中返回false條件的情況,因爲prehandle方法的返回類型是布爾值,所以我無法從那裏返回新的ModelAndView對象,如果我使用response.sendError(),那麼錯誤頁面發出請求的URL,但我想呈現我的請求URL的視圖頁面,但也確保控制器方法不應該拋出。

是否有可能通過添加自定義對象來編寫一個攔截器來呈現請求URL頁面,但不傳遞給控制器​​以進行相同的URL映射。

我也嘗試了response.sendRedirect,但它導致攔截器方法入口方法的無限循環,因爲調用了相同的攔截器。

對我來說,一個解決方法是在每個控制器類中添加單獨的URL映射(如// errorMessage映射),無論哪一個使用攔截器,但它都會使用該攔截器的方法。

我也附上參考代碼。

package com.renovite.ripps.ap.interceptor; 

import javax.servlet.http.HttpServletRequest; 
import javax.servlet.http.HttpServletResponse; 

import org.slf4j.Logger; 
import org.slf4j.LoggerFactory; 
import org.springframework.web.method.HandlerMethod; 
import org.springframework.web.servlet.ModelAndView; 
import org.springframework.web.servlet.handler.HandlerInterceptorAdapter; 

import com.renovite.ripps.ap.common.AdminPortalMsgsPropFileReader; 
import com.renovite.ripps.ap.common.Constants; 
import com.renovite.ripps.ap.common.ErrorCodes; 
import com.renovite.ripps.ap.ui.controller.AdminController; 

/** 
* The Class MongoDBConnectionInterceptor. 
*/ 


/** 
* @author Satyam Kaushik 
* 
* 
*/ 
public class MongoDBConnectionInterceptor extends HandlerInterceptorAdapter { 

    /* (non-Javadoc) 
    * @see org.springframework.web.servlet.handler.HandlerInterceptorAdapter#preHandle(javax.servlet.http.HttpServletRequest, javax.servlet.http.HttpServletResponse, java.lang.Object) 
    */ 

    private final static Logger logger = LoggerFactory.getLogger(MongoDBConnectionInterceptor.class); 

    @Override 
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception { 

     Boolean isMongoDBConnected = (Boolean)request.getSession().getAttribute(Constants.IS_MONGODB_CONNECTED_SESSION); 
     if(!isMongoDBConnected){ 
      logger.error(Constants.IS_MONGODB_CONNECTED_SESSION); 


     String url = ((HttpServletRequest)request).getRequestURI().toString(); 
     String targetMappingURL = url.split("/")[2]; // 



response.sendRedirect(targetMappingURL); //it results an infinite loop 
    //response.sendError("Connection failed to MongoDB"); // Error page on the requesting URL. 
     }return isMongoDBConnected; 
    }} 

回答

0

這裏攔截器可能不是最明智的選擇,因爲它在標註的控制器機制之外太遠了。相反,我建議使用@ControllerAdvice,是這樣的:

@ControllerAdvice(basePackages="com.yourcompany") 
public class MyAdvice { 

    @InitBinder 
    // add params as needed, but return type must be void 
    public void dispatch(){ 
     if(somethingIsBad()) throw new SomethingIsBadException(); 
    } 

    @ExceptionHandler(SomethingIsBadException.class) 
    // this method can have any parameter or return type that 
    // a @RequestMapping method can. 
    public SomeBusinessObject recover(){ 
     return new SomeBusinessObject(); 
    } 

} 

這樣,您就可以使用所有註解和返回異常處理程序通過@RequestMapping支持的類型。

參考: @ControllerAdviceDocsJavaDocs

+0

它太遠外註釋控制器機構裝置?? – Satyam

+0

當然沒有。你是談論攔截器的人,而且這些人甚至遠離註釋過的控制器,但是可以肯定的是,你也可以在控制器類中完成所有這些工作 –

+0

我不想將請求路由到某些控制器(這需要MongoDB連接)如果應用程序沒有連接到MongoDB.This不是我的情況的解決方案。 – Satyam

相關問題