1. 程式人生 > >URL編碼及Java發起URL請求的問題詳解

URL編碼及Java發起URL請求的問題詳解

前言

今天我們來講一下URL編碼(同時被稱為Percent-encode,百分比編碼)。雖然它相對簡單,但是非常的重要,至於為什麼,通過我後面的介紹也許你就會明白。 雖然叫做URLEncode,但是它普遍用於“統一資源識別符號(URI)”中,熟悉HTTP協議的同學應該知道,URL是URI的一部分。同時,URL編碼還被用在html頁面的表單提交上,通常HTTP協議會先將表單資料進行編碼,然後再執行POST或者GET請求。 實際上我們每天都能夠看到URL編碼和解碼,可能你沒有發現而已。最簡單的一個例子,我們知道表單在傳輸資料的時候是採用鍵值對的方式,即key-value,拼裝引數的時候就是key1=value1&key2=value2。**如果我們的key1=1&value(這是一個整體),然後key2=value2,如果不進行編碼,傳遞的時候就成了key1=1&value&key2=value2,看到了吧,這就會造成語義上的歧義,我們在接收表單資料的時候就無法正常接收。**當然,作為普通使用者來說,一般不會遇到這個問題,那是因為開發人員已經處理過了,但是我們就是這些開發人員,所以必須瞭解。 為了避免出現這種歧義,我們應該怎麼做呢?

URL字元型別

我們在說解決方案之前,還是先來看看W3C是如何規定URL的格式的。 像“&”這種字元,在URL中被作為保留的編碼,和java中的關鍵字保留是一樣的,這些我們都是不能直接使用的,想要使用必須轉義。這種保留符號還有很多,下表中列出的就是這些保留字元。

在這裡插入圖片描述

如果需要在值中用到這些保留字元,則需要將這些值進行百分轉換,這也是百分比編碼的由來。除去保留字元,還有空格字元也需要轉義,轉義後為“%20”。

在這裡插入圖片描述

當然,在一些特定的場合,比如後端需要解析前端經過編碼後的值時,如果傳遞中文,就需要將中文編碼。關於這一點,我會在程式碼中說明。

程式碼轉義

首先,我們肯定不能在傳值的時候去看轉義後的字元,這簡直太麻煩了,好在JDK給我們提供了一個URLEncoder類,讓我們用來URL編碼。 正常的後端程式碼是不會用到URL編碼的,直接接收引數操作就好了,但是特殊的情況,如發起網路連線的時候,新增引數,就需要用到編碼。多用於網路爬蟲一類的應用程式(想起了當年用網路爬蟲爬取內涵圖的經歷,但是那個網站做了反爬蟲,現在沒法用了。。)

最後,我給出一個URLConnection類,拼裝引數,然後發起連線即可。

/**
 * 發起url連線工具類
 *
 * @author 言立慧
 * @date 2018/9/9 10:43
 */
public class UrlConnectionUtil {
    public static void getConnection(String domain, String lastUrl, HashMap<String, Object> params) {
        StringBuffer bufferUrl = new StringBuffer();
        // 拼裝ip地址
        bufferUrl.append(domain);
        bufferUrl.append("/");
        bufferUrl.append(lastUrl);
        bufferUrl.append("?");
        // 拼裝各種引數,使用迭代器進行遍歷
        Iterator it = params.entrySet().iterator();
        while (it.hasNext()) {
            Map.Entry entry = (Map.Entry) it.next();
            String key = entry.getKey().toString();
            String value = entry.getValue().toString();
            bufferUrl.append(key);
            bufferUrl.append("=");
            // 如果需要對中文進行轉義的話,只需要寫成:
            // bufferUrl.append(URLEncoder.encode(value,"UTF-8"));
            bufferUrl.append(value);
            bufferUrl.append("&");
        }
        bufferUrl.delete(bufferUrl.length() - 1, bufferUrl.length());
        System.out.println(bufferUrl.toString());
        // 嘗試建立連線
        try {
            URL url = new URL(bufferUrl.toString());
            //開啟連線
            URLConnection urlConnection = url.openConnection();
            //傳送連線請求
            urlConnection.connect();
            //獲取伺服器響應
            BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(urlConnection.getInputStream(),
                    "utf-8"));
            String lineData = bufferedReader.readLine();
            System.out.println(lineData);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }


    public static void main(String[] args) {
        HashMap<String, Object> params = new HashMap<>();
        params.put("gender",1);
        getConnection("http://192.168.43.170", "history", params);
    }
}

這個類其實非常簡單,getConnection方法用於拼裝引數併發起連線,main函式中是測試程式碼。這個程式碼是我做介面測試用的,僅供參考。 至於引數拼裝的問題,我使用了一個HashMap<String, Object> params = new HashMap<>();,有了這個東西,封裝引數還不是小意思。

結語

感謝您的閱讀,如果你喜歡我的文章,歡迎留言、點贊。也歡迎你關注我的微信公眾號,最高許可權位元流,回覆java領取學習禮包、視訊資料。