一 url和uri的區別:
uri: uniform resource identifier,統一資源標識符。
url: uniform resource locator,統一資源定位符。
做一個類比,人可以通過身份證唯一的標識出來,這個身份證ID就相當於uri,但是人也可以某個具體的地址如: 中國/南京/棲霞區/南京大學/宿舍樓/宿舍號/某某某 唯一的標識出來。也就是說,不管是編碼的方式還是定位的方式,我們都可以唯一的確定一個資源。現在的網址我更傾向於叫它URL,因為提供了具體的位置信息,但是如果網址是通過號碼來標識,如741236985.html,那么叫它URI更合適。
URI一般由三部組成:
①訪問資源的命名機制
②存放資源的主機名
③資源自身的名稱,由路徑表示,着重強調於資源。
URL一般由三部組成:
①協議(或稱為服務方式)
②存有該資源的主機IP地址(有時也包括端口號)
③主機資源的具體地址。如目錄和文件名等
二 url中包含特殊字符如何處理
不管是以何種方式傳遞url時,如果要傳遞的url中包含特殊字符,如想要傳遞一個+,但是這個+會被url會被編碼成空格,想要傳遞&,被url處理成分隔符。
尤其是當傳遞的url是經過Base64加密或者RSA加密后的,存在特殊字符時,這里的特殊字符一旦被url處理,就不是原先你加密的結果了。
url特殊符號及對應的編碼:
| 符號 | url中的含義 | 編碼 |
|---|---|---|
| + | URL 中+號表示空格 | %2B |
| 空格 | URL中的空格可以用+號或者編碼 | %20 |
| / | 分隔目錄和子目錄 | %2F |
| ? | 分隔實際的URL和參數 | %3F |
| % | 指定特殊字符 | %25 |
| # | 表示書簽 | %23 |
| & | URL中指定的參數間的分隔符 | %26 |
| = | URL中指定參數的值 | %3D |
1. js的處理方式:
(1)替換
function URLencode(sStr) { return sStr .replace(/\+/g, '%2B').replace(/\"/g,'%22').replace(/\'/g, '%27').replace(/\//g,'%2F'); }
(2)使用encodeURI(url)和encodeURIComponent(url)
encodeURIComponent(URIstring): 假定其參數是URI一部分(比如協議、主機名、路徑或查詢字符串),因此 encodeURIComponent() 函數將轉義用於分隔 URI 各個部分的標點符號(? # 等)。
encodeURI(URIstring): 不會對URI中的分隔符編碼,如 ? # 等。
2. java的處理方式
java.net.URLEncoder.encode(String s)和java.net.URLDecoder.decode(String s);
三 UriComponentsBuilder和UriComponents
SpringMVC使用UriComponentsBuilder和UriComponents兩個類來提供一種構造和加密URI的機制。
擴大和編碼URI模板字符串:
@RequestMapping(value = "/user/{name}")
public ResponseEntity<String> uri(HttpServletRequest req, @PathVariable String name, @RequestParam int id) {
UriComponents uriComponents = null;
//通過URL模板字符串來填充並加密一個URI
uriComponents = UriComponentsBuilder.fromUriString(
"http://example.com/hotels/{hotel}/bookings/{booking}").build();
URI uri = uriComponents.expand("42", "21").encode().toUri();
System.out.println(uri.toString());
//通過URI組件實例對象來填充並加密一個URI
uriComponents = UriComponentsBuilder.newInstance()
.scheme("http").host("example.com").path("/hotels/{hotel}/bookings/{booking}").build()
.expand("42", "21")
.encode();
System.out.println(uriComponents.toUri().toString());
return null;
}
