2013-04-03 39 views
2

我正在使用GWT 2.4來構建一個應用程序,該應用程序完全運行客戶端並使用我控制但託管在不同服務器上的Web服務。在此Java Servlet的Web服務,我已經實現doOptions像這樣:GWT HTTP請求響應代碼0與CORS工作

protected void doOptions(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { 
    response.addHeader("Access-Control-Allow-Origin", "*"); 
    response.addHeader("Access-Control-Allow-Methods", "POST, GET"); 
} 

和客戶端的GWT我提交申請的標準方法,例如

public static void makeHttpGetRequest(String query, RequestCallback callback) { 
    String url = "http://example.webservice.com/endpoint" + "?q=" + query; 

    RequestBuilder builder = new RequestBuilder(RequestBuilder.GET, URL.encode(url)); 
    try { 
     builder.sendRequest(query, callback); 
    } catch (RequestException e) { 
     Window.alert("Server encountered an error: \n" + e.getMessage()); 
     e.printStackTrace(); 
    } 
} 

然後我的回調實現onResponseReceived這樣的:

@Override 
public void onResponseReceived(Request request, Response response) { 
    if (response.getStatusCode() == 200) { 
     System.out.println("HTTP request successful, received " 
       + response.getText()); 
     processResponse(response.getText()); 
    } else { 
     System.out.println("HTTP error code " + 
       response.getStatusCode() + ":" + 
       response.getStatusText()); 
    } 
} 

每當我在Chrome或Firefox的後期版本上運行的應用程序,併發送請求,onResponseReceived被調用,但響應代碼爲0,沒有錯誤信息。研究表明,這個問題的大多數其他情況都是由SOP限制引起的。然而,當看着Fiddler中的HTTP流量時,我發現當這個被執行時,瀏覽器確實發送了預期的HTTP請求,並且web服務確實返回了預期的響應,並帶有200個響應代碼。不知何故,瀏覽器只是沒有正確處理它。

更新:當我查看Fiddler中的流量時,它表示發送了請求並收到了響應,但是當我在Chrome的開發人員控制檯中查看相同的請求時,它顯示請求已被取消。如果請求實際發生,那麼在這種情況下這意味着什麼?

有沒有人遇到過這個問題?任何關於可能發生的事情的建議?

回答

1

錯誤代碼0意味着CORS已經中止,請檢查你的servlet實現所有的權利,我認爲你必須發送Allow而不是Access-Control-Allow-Methods,還必須添加的Access-Control-Allow-Headers因爲GWT增加了額外的頭阿賈克斯要求。

嘗試從工作正常的gwt-query example此實現:

private static final String ALLOWED_DOMAINS_REGEXP = ".*"; 

HttpServletRequest req = (HttpServletRequest) servletRequest; 
HttpServletResponse resp = (HttpServletResponse) servletResponse; 

String origin = req.getHeader("Origin"); 
if (origin != null && origin.matches(ALLOWED_DOMAINS_REGEXP)) { 
    resp.addHeader("Access-Control-Allow-Origin", origin); 
    resp.setHeader("Allow", "GET, HEAD, POST, PUT, DELETE, TRACE, OPTIONS"); 
    if (origin != null) { 
     String headers = req.getHeader("Access-Control-Request-Headers"); 
     String method = req.getHeader("Access-Control-Request-Method"); 
     resp.addHeader("Access-Control-Allow-Methods", method); 
     resp.addHeader("Access-Control-Allow-Headers", headers); 
     resp.setContentType("text/plain"); 
    } 
} 

我寧願一個過濾器,而不是一個servlet,就像在上面的鏈接進行了說明,但。

+1

謝謝!這工作。我之前做的和這個過濾器效果之間的具體區別在於,我只是從OPTIONS請求中返回'access-control-origin'頭部,而此頭部也需要添加到GET請求中。 – rjgage

+0

@Manolo req.getHeader(「Origin」)在我的情況下返回null值。請幫忙。 – Kumar

+0

'原始標題僅發送給支持CORS的瀏覽器,IE9不起作用,這是你的情況嗎? –