現象:
1.如下兩個url,被解析到同一台服務器,由Istio的Gateway及VirtualService完成軟路由:
https://dev-test.pconline.com.cn/login.html
2.在瀏覽器中始終無法同時訪問這兩個url,總有一個會報404,該現象與網絡無關,普遍存在
3.清除緩存后,或者過足夠時間長后,原本訪問結果為404的url可以恢復訪問
4.掛上代理、使用curl、使用postman時該問題不存在
5.部分瀏覽器如誇克瀏覽器,也存在相同情況,但是只需要等待數分鍾,便可恢復訪問
6.部分瀏覽器如老版本的Chrome瀏覽器,等待足夠長時間后,便可恢復訪問
問題分析:
1.我認為,極有可能是keep-alive之類的東西,印象了Istio的軟路由
實驗設計:
1.刪除所有的ingress pod,等待k8s重新建立pod,此時兩個url優先訪問的能正常訪問(已證實)
2.同時監聽兩個pod的端口,並過濾ip地址為公司公網ip,此時如果未用公司電腦進行訪問,應該是不會有任何信息的(已證實)
3.使用一台電腦訪問url,並查看端口,過濾ip地址,應該可以看到一條記錄(已證實)
4.抵用第二胎電腦訪問url,並查看端口,過濾ip地址,應該可以看到兩條記錄(已證實)
5.此時兩個url中必然存在一個不可以訪問的(現象)
6.刪除所有pod,等待k8s重建,立即訪問之前不可訪問的url,發現其可以訪問, 而另一個不可訪問(已證實)
6_1.如果不刪除所有pod,等待netsta -an結果消失的瞬間,再去訪問,可以肯定是可以正常訪問的(實驗條件苛刻,未實驗)
實驗結論分析:
1.因為沒有辦法直接關閉一個established,所以采用了直接殺掉一個pod的方案,如果具有關閉一個established的方法,相信結果更具備說服力。
2.正如實驗中的圖片中顯示,當netstat -an具有結果的時候,則表示客戶端始終和服務端保持着連接,而這個時候也正是第二個url無法訪問的時候
3.結合之前得到的istio-proxy日志中,request_server_name總是為前一個成功訪問的服務的host名,這兒可以認為就是因為連接始終處於保持狀態,導致二次請求時,istio-proxy配置沒有起到作用
4.另外,在學習istio時,注意到istio是區分tcp請求和http請求的,這兒有一種感覺,我們的http請求總是被當做tcp請求處理了。但是這個絕對不是我們配置產生的問題
問題解決思路:
1.將Istio升級到較新的版本,嘗試能否解決這個問題,避免低版本的Istio存在更多的問題
2.在升級Istio后,如果無法解決問題,可以考慮安排時間研究envoy,嘗試在envoy上解決這個問題。同時,較好的掌握envoy,也可以提升定位和分析問題的能力
2.為什么會建立一個keep alive,是nginx引發的這個問題么,如果有可能的話,需要對nginx進行配置,或者建立兩個簡單的項目進行試驗。如果是這個層面的原因,解決起來將會很方便。
對問題的進一步分析:
1.在對http進行試驗后,發現兩次訪問,建立了不止一個tcp通道,可以肯定問題的核心原因不在於keep-alive,而在於兩個不同域名的https請求,只建立一個tcp通道,而且還在復用這個通道
進一步實驗:
http部分的實驗:
1.刪除所有ingress,查看端口,並過濾公網IP,此時沒有任何連接;查看客戶端連接,過濾slb ip,此時沒有任何連接
2.訪問如下鏈接,注意,我用的是http,同時觀察istio-proxy的日志和客戶端的日志,發現兩邊同時建立了兩條tcp通道,這是和期待想符合的(已證實,截圖如下)
3.訪問如下鏈接,注意,我用的是http,同時觀察istio-proxy的日志和客戶端的日志,發現兩邊同時建立了三條tcp通道,這是和期待想符合的(已證實,截圖如下)
http://dev-test.pconline.com.cn/login.html
4.同時刪除pod,並查看客戶端,發現所有的通道都關閉了,這是和期待想符合的(已證實)
https部分的實驗
1.刪除所有ingress,查看端口,並過濾公網IP,此時沒有任何連接;查看客戶端連接,過濾slb ip,此時沒有任何連接
2.訪問如下鏈接,查看客戶端請求,發現建立了一條tcp通道,這是和期待想符合的(已證實,未截圖)
3.訪問如下鏈接,查看客戶端請求,發現建立了兩條tcp通道,這是和期待想符合的,此時觀察服務端的tcp通道發現只有一條(已證實,截圖如下)
https://dev-test.pconline.com.cn/login.html
實驗結論:
1.我們第二次請求是可以正常與istio通信的,這個現象可以從日志中看到,但是通信中request_server_name是一個錯誤的值
2.https請求中服務端tcp通道數與預期不符合,說明我們的通道被中間某個組件給處理過,且它認為我們是在同一個域名下的請求
3.我又做了一部分實驗,得出的結論如下,阿里雲已經開始介入處理這個問題了,我們不打算在這個問題上花費太多的時間: