簡體   English   中英

HttpUrlConnection 出現 503 錯誤,但在瀏覽器上加載網站

[英]Getting 503 error with HttpUrlConnection but site loading on browser

     url = "https://www.lmcu.org/?__cf_chl_jschl_tk__=9c114404052361017d9cfe1247981e24813649c7-1592389426-0-AfP07ha5TxZHf64q5tb5nJf9BJguC4U553-OJzJWivTqfgwYLqUODkXj-XsOjZTwpC71ROxHWx4Xhdp2S0LgAVlKgXpy7KWOex7lkoGBm8mNpBsCeJapdYNWty-X2oHE6gp_TtMfH0dcBabvWr_mXV1djsVR_IGlYJA-wCuZpPTGOozyzN9TFwjMPxU-3o6BIUxTh6DDcHmJ_Bw48EYKGpq6n57bVdeLezEs9PduataW1JUcF4GqLE2EHiUxWGubtS8YgcxkkGin4zitHXENMbFi1kMhxI77LsORzKyhkAD1OkG8fGmV--Cgd3EpxWHtHD5vpoIFFIwX0uGQywPnegs";

     HttpURLConnection connection = pingHttpUrl(url);
     responseCode = connection.getResponseCode();

     public HttpURLConnection pingHttpUrl(String url) throws IOException {

        HttpURLConnection conn = null;
        try {
            conn = (HttpURLConnection) new URL(url).openConnection();
            conn.setRequestMethod("GET");

            conn.addRequestProperty("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76 Safari/537.36");
            conn.setConnectTimeout(2000);
            conn.setInstanceFollowRedirects(false);
            conn.setReadTimeout(10000);
            conn.connect();
            Thread.sleep(1000);
        } catch (Exception e) {
            logger.error("Caught exception : {}", e.getMessage());
            throw new IOException();
        }

        return conn;
     }

這給出了 503 的響應代碼。但是該站點正在瀏覽器上正確加載。 這可能是什么問題?

問題在於請求的標頭。 我發現這個托管在 cloudflare 上的解決方案需要兩個標頭,否則您將收到503響應:

  • 用戶代理- 您的 header 指定 chrome 版本76 ,顯然服務器對此有問題。 我在這個User-Agent值上取得了成功: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/83.0.4103.97 Safari/537.36
  • cookie - 我發現需要設置 cookie 值cf_clearance ,並且可能需要設置第一個請求時返回的其他set-cookie值。 此值與 cloudflare 對隱私通行證 ( https://blog.cloudflare.com/cloudflare-supports-privacy-pass/ ) 的支持有關。 它似乎是一種驗證用戶是人而不是機器的方法。 這反過來對你在這里的努力來說是個壞消息。

我在下面有一個可行的解決方案,但它很難自動化 - 因為它需要您建立一個瀏覽器 session,並使用代碼中設置的 cookie。 cf_clearance cookie 到期后,您將再次訪問該站點並重置代碼中的 cookie 值。

我還推測請求的用戶代理 header 用於生成所需的 cf_clearance cookie。 使劫持 cookie 變得更加困難,因為當 cloudflare 生成 cf_clearance cookie 時,您必須使用用於請求的瀏覽器的匹配用戶代理。

我在這里記錄了我的調查:

在我的瀏覽器中訪問 URL 時:

https://www.lmcu.org/? cf_chl_jschl_tk =9c114404052361017d9cfe1247981e24813649c7-1592389426-0-AfP07ha5TxZHf64q5tb5nJf9BJguC4U553-OJzJWivTqfgwYLqUODkXj-XsOjZTwpC71ROxHWx4Xhdp2S0LgAVlKgXpy7KWOex7lkoGBm8mNpBsCeJapdYNWty-X2oHE6gp_TtMfH0dcBabvWr_mXV1djsVR_IGlYJA-wCuZpPTGOozyzN9TFwjMPxU-3o6BIUxTh6DDcHmJ_Bw48EYKGpq6n57bVdeLezEs9PduataW1JUcF4GqLE2EHiUxWGubtS8YgcxkkGin4zitHXENMbFi1kMhxI77LsORzKyhkAD1OkG8fGmV--Cgd3EpxWHtHD5vpoIFFIwX0uGQywPnegs

並檢查服務器給出的響應,結果發現它實際上也返回了503

瀏覽器開發者控制台的圖像,帶有網絡輸出

對於一些我無法理解的原因,瀏覽器被重定向到下面的 URL 。 我看不到位置 header 在響應中被傳回,或者在響應中的任何地方都找不到這個 URL。

https://www.lmcu.org/? cf_chl_jschl_tk =fe835fdc1e7e2f5b2857ab5eb4be84e67d0e8c42-1592506549-0-AQ3E1piNGHg7O7lxgRyItR1U5BzB52q7GmCHe_HPJBsUHv8RcZCgqLPPtyngPmDjvy7pZDprPNK6ihKVEgQ7HqmbDSPXZ1aHPkBDs9re49u_Q_jI04etmtK7E0GIdxhKWCd-p4TR7b_b0JdnwzJOF6z4XaJQOgNU8kazJr5Mo96zxQpUlsKWPSumEmSfynkGeMDgkM-O1mN59LKp0p4kt-2O2IIFrlc8289ZbCSO6JghtvDsLsFDA3VxLV3Irn2W3KQ8sHg_TdwB-0g0WX9J-WTwedVYzj2a7uNtH377ZIritTXKqRw1qeQ6mkpxQ0h_OVMIl8XUiEC0Zj1KP50tUK8

我檢查了 Postman,果然 - 我也收到了 503 錯誤。 據我所知,服務器(或它前面的反向代理)正在檢查請求的標頭,並根據它們使請求無效。 我玩弄了一下,將瀏覽器請求中的標頭移動到 Postman 中,最后發現它是設置的cookieUser-Agent標頭的組合,允許服務請求。

不允許User-Agent header 具有指定的 chrome 版本,我在這里使用版本 83。 cookkie是我第一次訪問瀏覽器中的站點時瀏覽器將填充的東西。 所以在你的代碼中處理起來有點困難。 我嘗試使用connection.getHeaderField("set-cookie")在代碼中獲取它,但該 cookie 似乎沒有削減它。

但是,當我從瀏覽器中獲取cookie並在代碼中手動設置它時,我能夠使代碼工作,以及User-Agent

    public HttpURLConnection pingHttpUrl(String url) throws IOException {

        HttpURLConnection conn = null;
        try {
            conn = (HttpURLConnection) new URL(url).openConnection();
            conn.setRequestMethod("GET");

            // This one does not work for the reason of the chrome version apparently
            // conn.addRequestProperty("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76 Safari/537.36");
            conn.addRequestProperty("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/83.0.4103.97 Safari/537.36");
            conn.addRequestProperty("cookie", "<cookie value from the browser, from the header on a successful request>");

            conn.setConnectTimeout(2000);
            conn.setInstanceFollowRedirects(false);
            conn.setReadTimeout(10000);
            conn.connect();
            Thread.sleep(1000);
        } catch (Exception e) {
            System.out.println(String.format("Caught exception : %s", e.getMessage()));
            throw new IOException();
        }

        return conn;
    }

后來我發現這是 cookie 中cf_clearance鍵中的 cookie 值造成了差異。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM