簡評:這是 fly.io 分享的一篇文章,講了他們是怎麼對自家 REST API 作版本控制的。另外還有不少其餘的技術文章,我的感受還不錯,感興趣的同窗能夠看一看。json
API 設計是一個都快被說爛了的主題,已經有太多關於對 Web API 作版本控制很棒的文章了。好比:api
但今天這裏仍是想分享一篇,但願看完能有所收穫。: )bash
雖然尚未一個絕對正確的方式來設計一個 API,可是有幾個關鍵想法是許多開發者都贊成的,一個優秀的 Web API 應該是:restful
爲了能最好的實現這些理念,關於如何實現 API 的不一樣版本目前主要有三種作法:app
在 URI 中標記版本curl
curl https://example.com/api/v2/lists/複製代碼
經過解析 URI 中的版本號,客戶端能夠訪問/v1/或/v2/等不一樣版本API。ide
在 Header 中標記版本url
curl https://example.com/api/lists/3 \
-H 'Accept: application/vnd.example.v2+json'複製代碼
直接不標記版本spa
curl https://example.com/api/lists/3複製代碼
嗯,咱們只有最新版本,趕忙去兼容吧。設計
不進行版本控制頗有可能讓 API 變得混亂,所以如今不多人會不作 API 版本控制了。而這裏,咱們選擇同時在 URI 和 HTTP Header 中標記版本。下面讓咱們來看一個例子:
假設咱們正在爲咱們的 MightyList 應用構建一個 API,能夠經過這個 API 來請求一組數據:
curl https://mightyapp.com/api/v1/lists/3
...
{
"listId": "3",
"shopping": "Shoes, tie, umbrella, snorkel",
"leisure": "Skiing, surfing, snorkeling ",
"food": "bananas, peanut butter, spinach",
"cost": "One hundred dollars"
}複製代碼
咱們先來看一個小的需求變化,在上面的例子中,cost
字段返回的是一個字符串。而如今咱們的開發團隊但願將其變成數值類型。
curl https://mightyapp.com/api/v1/lists/3
...
{
"listId": "3",
"shopping": "Shoes, tie, umbrella, snorkel",
"leisure": "Skiing, surfing, snorkeling ",
"food": "bananas, peanut butter, spinach",
"cost": 100
}複製代碼
這是一個很小的變更,但卻會破壞咱們 API 的向後兼容性。像這種比較小,但卻會形成向後兼容性問題的變更,是應該進行版本號上的變更的。
還有一種就是比較重大的修改,好比:lists 變成了 superlists,又須要加入許多新的字段等等,這種大的升級基本都會破壞兼容性。這時一般作法都是將 URI 中的 /v1/變爲/v2/。
所以理論上只要是影響到向後兼容性的改動都應該反應在版本號上,提供 Change Log 給使用者。但若是不論變更大小都升級 URI 中的版本號,這又會形成過多的版本。
爲了保證咱們應用狀態的清晰,咱們但願在 URI 中有一個表明產品版本的版本號。當產品有了較大,或根本性的改變時,URI 版本將會改變。好比,MightyList V1 使用/api/v1/,MightyList V2 使用/api/v2/。
而對於當前版本內的較小修改,咱們使用自定義的 HTTP Header 來表示。做者使用的自定義 Header 名爲 API-Version,值爲 day-month-year 格式的日期。
這樣咱們就能夠爲 API 提供更新日誌了,用戶也能夠經過配置版本日期來訪問他們須要的 API 版本,就像這樣:
固然 API 設計有許多不一樣的理念和作法,這裏也只是其中一種,或許能對你有所啓發。
知乎專欄:極光日報
極光日報,極光開發者 的 Side Project,天天導讀三篇國外技術類文章,歡迎關注。