Compose xidmətiniz eyni maşındakı brauzerin heç bir şikayət etmədən açdığı API-yə qarşı vaxt aşımına uğrayır. Bu fərq ipucudur: işləyən sorğu VPN tunnelı olan hostdan çıxır, donan sorğu isə öz şəbəkə yığını olan konteynerdən çıxır. Konteynerin içində heç nə tunnelin marşrutlarını bilmir, ona görə şəxsi təyinat adı necə yazılsa da əlçatmaz qalır. Düzəliş hostdan keçən qəsdən bir atlamadır, daha ağıllı marşrut cədvəli deyil.

İki yolun niyə fərqləndiyindən başlayın, sonra tunnelin harada yaşamalı olduğuna qərar verin.

Niyə host işləyir, konteyner isə yox

Tunneli qaldırmaq hosta interfeys, marşrutlar dəsti və adətən VPN tərəfindən verilən resolver qeydi verir. Konteyner bunların heç birini miras almır: o, mühərrikin körpüsündə bir interfeys və həmin körpüyə yönələn defolt marşrutla başlayır. Hostda quraşdırılmış marşrutlar həmin ad məkanında işləyən hər şey üçün görünməzdir.

Semptomların sadəcə xarab deyil, ziddiyyətli görünməsinin səbəbi budur. Host şəxsi adı həll edir və qoşulur, çünki həm ad, həm də marşrut orada mövcuddur. Konteyner paketini körpü yolunda heç nəyin çata bilmədiyi şəxsi ünvana göndərir və sorğu vaxt aşımına uğrayır. Adı konteynerin hosts faylına əlavə etmək heç nəyi dəyişmir, çünki ünvanın özü konteynerin oturduğu yerdən əlçatmazdır.

Konteynerin içindən hosta çatın

Konteynerdə localhost ünvanına qoşulan proses konteynerə qoşulur. Docker Desktop host.docker.internal adını mühərriki işlədən maşına geri yönələn ad kimi yayımlayır; Linux mühərrikləri xidmət istəməsə onu təyin etmir, aşağıdakı xəritələmə də məhz bunu edir. Bununla tətbiq şəxsi ünvan əvəzinə bir ad və port hədəfləyir.

services:
  app:
    extra_hosts:
      - "host.docker.internal:host-gateway"
    environment:
      INTERNAL_API_HOST: "host.docker.internal:8666"

Tunnel atlamanın host tərəfində qalır və həmin dəyişəndəki port proxy-nin dinləyəcəyi portdur. Tunneli itirən konteyner indi heç vaxt malik olmadığı marşrutu sınamaq əvəzinə tək məlum atlamada uğursuz olur.

Tunnelin harada yaşayacağını seçin

Şəxsi API-yə ehtiyac duyan Compose xidməti üçün üç forma mümkündür və onlar tunnelin hansı prosesə aid olması ilə fərqlənir. VPN klienti konteyner obrazının içində işləyə bilər, bu da tunnel cihazını açmağı və onunla birlikdə gələn şəbəkə idarəetmə imkanını verməyi tələb edir. Tətbiq ayrı bir tunnel konteynerinin şəbəkə ad məkanını paylaşa bilər, beləliklə hər iki proses bir yığın və bir marşrut cədvəli görür. Ya da tunnel hostda qala bilər, hostdan konteynerə dar bir yönləndirici ilə.

İlk ikisi profil fayllarını, yenidən qoşulma davranışını və resolver siyasətini layihəyə çəkir və fayldakı hər xidməti tunnelin sağlamlığından asılı vəziyyətə gətirir. Bir API çağırışı üçün bu çox bağlılıqdır. Tək daxili son nöqtəni oxuyan inkişaf yığını üçün host tərəfli yönləndirici, etimad məlumatlarını platforma komandasının idarə etdiyi yerdə saxlayan ən kiçik dəyişiklikdir.

Hostda bir dar yol yayımlayın

Yönləndiricinin miras aldığından başlayın: onu tunneli saxlayan hesabla işlədin, xarici soketləri hostun marşrutlarını və hostun resolverini götürəcək. Bir nginx location bloku bir yolu əhatə edir.

server {
    listen 8666;
    location /search/ {
        proxy_pass http://10.20.30.40:8090/;
        proxy_set_header Host internal-api.example;
        proxy_read_timeout 60s;
    }
}

Ünvanı və portu şərti yer tutucular kimi qəbul edin və API-nin həqiqətən dinlədiyi cütlə əvəz edin. Hər əlavə upstream öz location blokunu qazanır və hər blok yalnız bu xidmətin çağırdığı yolları qəbul etməlidir ki, proxy şəxsi şəbəkəyə ümumi qapıya çevrilməsin. Dinləyicini host-gateway vasitəsilə gələn müştərilər üçün körpü ünvanına, yalnız müştəri host şəbəkə ad məkanını paylaşdıqda loopback-ə bağlayın və heç vaxt 0.0.0.0-a bağlamayın. Həm də hələ boş olan port seçin: artıq tutulmuş nömrə proxy-ni dinləməyən vəziyyətdə qoyur, konteyner isə vaxt aşımına davam edir, bu da başladığınız şəbəkə nasazlığından ayırd edilə bilmir.

Portlar, adlar və TLS qərarı

Ad həlli də marşrutlaşdırma kimi bölünür. Konteynerin ictimai axtarışları mühərrikin resolverindən keçir, ona görə hostda həll olunan şəxsi ad konteynerin içində həll olunmayacaq. Şəxsi adı həll edən komponent proxy-dir, çünki o, host resolverini miras alır.

TLS təxirə salınan və sonra növbəti uğursuzluğu izah edən qərardır. Proxy baytları toxunulmadan ötürürsə, konteyner API-nin öz sertifikatını görür və daxili CA-nı öz etimad anbarına salmalıdır. Proxy TLS-i sonlandırırsa, bu etimad hosta keçir və tətbiq aldığı host başlığından keçidlər qurmağa başlayır. Bir düzülüş seçin və onu hər resursa tətbiq edin, çünki digər düzülüşün verdiyi yönləndirmə konteynerin həll edə bilmədiyi host adına işarə edir.

Xidmətin içindən yoxlayın

Sorğunu hostdan deyil, konteynerdən göndərin: proxy yoluna qarşı sadə curl, sonra tətbiqin öz sağlamlıq yoxlaması. Proxy cavab verir, tətbiq isə hələ də uğursuz olursa, üç şeyi müqayisə edin: qurduğu baza URL-i, mühitindəki hər hansı proxy dəyişəni və etimad etdiyi CA. Hamısı konteynerin mühitində və qeydlərindədir və hər hansı birini düzəltmək VPN-ə toxunmur.

Seçilmiş düzülüşü hələ təzə ikən layihənin README faylına yazın. Əks halda bu vaxt aşımına düşən növbəti şəxs də tunnelin hostda yaşadığını yenidən kəşf etməklə eyni günortanı keçirəcək.

Əlaqəli məqalələr