URL結構、組成、query、hash、axios數組傳遞錯誤、HTTP 請求
伴隨着微信消息的提示音 小四
發來一段代碼說 不知道爲何請求不到頁面數據
:javascript
axios.get('users', { params: { ids: [1, 2, 3] } })
小二一看大機率是 query
中數組
傳遞方式引發的,因爲後端實現解析數組 ids:[5, 6, 100]
可能有如下幾種方式:html
ids[]=1&ids[]=2&ids[]=3
ids[0]=1&ids[1]=2&ids[3]=3
ids=1,2,3
ids=1&ids=2&ids=3
小四分別測試後便把問題解決了,這也讓小二想起 小熊貓哥哥
在開發的時候,也遇到過這個問題網上一搜發現別人用 qs 庫中的 stringify
直接代碼一試沒報錯能運行
,無論它的原理是什麼,如今想一想挺可怕的。前端
雖然每天和URL
打交道但並非全部人都懂它。對於爲何代碼能運行也不是全部人都會去
深究它
。html5
利用 URL()
對象能夠快速的把一個 url地址
打回原形:java
const url = new URL('http://www.pushme.top/users?sort_by=asc#page=userlist') console.log(url)
{ hash: "#page=userlist" host: "www.pushme.top" hostname: "www.pushme.top" href: "http://www.pushme.top/users?sort_by=asc#page=userlist" origin: "http://www.pushme.top" password: "" pathname: "/users" port: "" protocol: "http:" search: "?sort_by=asc" searchParams: URLSearchParams {} username: "" }
沒想到吧 小小的一段 url地址
裏面竟然有這麼多屬性,在這裏主要會講解的 hash
和 search
。ios
推薦打開控制檯把腳本運行一下,這樣閱讀的時候就不須要上下對照查看了。
眼尖的同窗確定發現了 host
和 hostname
竟然如出一轍這是爲何呢?git
回憶一下開發常常在見到的 localhost:8080
,這裏出現了端口號 8080
而平時使用訪問一些網站的時候卻沒有帶上端口號。這是由於 url地址
會默認端口號爲 80
,因此你仔細看看會發現上面 port
的值爲空。github
而 host
和 hostname
的區別即是有 port
的時候 host
會包含端口號,而 hostname
不會包含。npm
protocol
指的即是 協議
最多見的有 http
和 https
,固然如今瀏覽器再不輸入協議時會自動幫你加上,不過在 URL()
不帶上協議但是會報錯的哦。origin
則爲 protocel
和 host
拼接組成。json
?search=a
中 query
以第一個?
開始至行尾
或#
結束。用於向後端傳遞一些數據,數據使用 &
進行分隔,值使用 =
分隔。經過一段代碼來理解一下:
const query = 'id=1&sort=asc&hello=world'; // 對 & 分割取得數據對 const data = query.split('&').reduce((data,keyValue) => { const [ key, value ] = keyValue.split('='); return (data[key] = value, data); }, {}); // 輸出 {id: "1", sort: "asc", hello: "world"} console.log(data);
這就是 query
最基礎的數據對的組合方式,固然開頭的四種 數組
的表達方式須要進行另外的處理,無外乎就是對 key
的收集 和 value
的判斷。不過這部分基本上後端的框架都幫咱們處理好了,前端也可使用 qs
、query-string
、qss
等庫來完成。
題外話:這幾個庫代碼都挺少的,值得一讀說不定有新收穫。
天天使用的 百度
和 谷歌
中不知道你們有沒有主要到這幾個細節:
https://www.baidu.com/s?wd=小二+pushmetop
搜索框中出現的是小二 pushmetop
,地址欄中url地址的 +
神奇的變成了 空格
。https://www.baidu.com/s?wd=小二 pushmetop
搜索框中出現的是小二 pushmetop
,地址欄中url地址的 空格
的變成 %20
。https://www.baidu.com/s?wd=小二%2Bpushmetop
搜索框中出現的是小二+pushmetop
,地址欄中url地址的 %2B
的變成 +
。具體緣由能夠查看 維基百科 關於 保留字符的百分號編碼
。
在 掘金
等網站點擊連接都會快速的閃現相似 http://www.pushmetop.com?redirect=xxxxx
的 url地址
,會發現 redirect
對應的重定向地址會是一堆夾帶 %
的亂碼這是爲何呢?
讓咱們假設須要跳轉的連接是 www.test.com?hello=world&id=1
,把整個連接拼接起來則爲:
http://www.pushmetop.com?redirect=www.test.com?hello=world&id=1
根據一開始的定義 解析值
和 預期值
徹底不一樣了:
{ "redirect": "www.test.com?hello=world", "id": "1" }
{ "redirect": "www.test.com?hello=world&id=1" }
爲了解決這個問題便誕生了 URL編碼
來解決問題:
encodeURIComponent()
和 decodeURIComponent()
推薦使用。encodeURI()
和 decodeURI()
對比前者不會對 "; / ? : @ & = + $ , #"
這些字符編碼。escape()
和 unescape()
不推薦使用。let redirect = 'www.test.com?hello=world&id=1'; redirect = encodeURIComponent(redirect); let url = `http://www.pushmetop.com?redirect=${redirect}`; url = new URL(url) // 輸出: www.test.com?hello=world&id=1 console.log(url.searchParams.get('redirect'))
#hash
中 fragment
以 #
爲開始 行尾
爲結束。在 回到頂部 中有提到過利用hash錨點來進行跳轉,若是你們注意觀察的話會發現 hash
的改變不會引發頁面的刷新。
在 Angular.js
、Vue Router
等庫中,會利用在 html5
中提供了 history
的一系列操做,來幫助咱們不刷新頁面管理 url
。可是在一些舊的瀏覽器上並不兼容時,會利用 hash
不會主動觸發瀏覽器 reload
的特性來修改 location.hash
來管理路由。 固然 hash
的另一個特色是能夠被保存爲書籤,也是一大優勢。
hash
的小妙用也能夠像 query
那樣利用 &
和 =
來存取數據,固然你也能夠定製屬於你的規則。
href
爲整個 url地址
。而 pathname
屬性包含 URL 的整個路徑部分。它跟在 host
(包括 port
)後面,排在 query
或 hash
組成部分的前面且被 ASCII 問號(?)或哈希字符(#)分隔。
username
和 password
在平常使用中不多用,它們能夠合稱爲 auth
。該字符串跟在 protocol
和雙斜槓(若是有)的後面,排在 host
部分的前面且被一個 ASCII 的 at 符號(@)分隔:
http://username:password@www.pushme.top/test/blah?something=123
原本只是想討論 hash
和 search
,結果全都過一遍,今天就辛苦你們了。
在困惑的城市裏總少不了並肩同行的
夥伴
讓咱們一塊兒成長。
點贊
。小星星
。m353839115
。
本文原稿來自 PushMeTop