Сиздин Compose кызматы ошол эле машинанын браузери эч кандай нааразылыксыз ачкан API-ге карата убакыт чегинен өтүп кетет. Ушул айырма — белги: иштеген суроо VPN туннели бар хосттон чыгат, ал эми илинип калган суроо өзүнүн желе стектүү контейнерден чыгат. Контейнердин ичинде эч нерсе туннелдин маршруттарын билбейт, ошондуктан ат кандай жазылбасын жеке дарек жеткиликсиз бойдон калат. Чечим — хост аркылуу атайын жасалган секирик, акылдуураак маршруттоо таблицасы эмес.

Эки жолдун эмне үчүн айырмаланганынан башта, анан туннель кайда жашоосу керектигин чеч.

Эмне үчүн хост иштейт, ал эми контейнер иштебейт

Туннелди көтөрүү хостко интерфейс, маршруттар топтомун жана адатта VPN берген резолвер жазуусун берет. Контейнер булардын эч бирин мураска албайт: ал кыймылдаткычтын көпүрөсүндөгү бир интерфейс жана ошол көпүрөгө багытталган демейки маршрут менен башталат. Хостко орнотулган маршруттар ошол ат мейкиндигинин ичинде жүгүргөн эч нерсеге көрүнбөйт.

Ошондуктан симптомдор жөн гана бузулган эмес, туура эмес көрүнөт. Хост жеке атты чечип, туташат, анткени ал жерде ат да, маршрут да бар. Контейнер пакетин көпүрө жолунда эч нерсе жете албаган жеке дарекке жиберет, ал эми суроо убакыт чегинен өтөт. Атты контейнердин hosts файлына кошуу эч нерсени өзгөртпөйт, анткени даректин өзү контейнер отурган жерден жеткиликсиз.

Контейнердин ичинен хостко жет

Контейнердеги localhost аркылуу чалган процесс контейнерге чалат. Docker Desktop host.docker.internal атын кыймылдаткычты жүргүзгөн машинага кайра багыттайт; Linux кыймылдаткычтары кызмат сурабаса, аны аныкталбаган бойдон калтырат, төмөнкү салыштыруу так ушундай кылат. Ошону менен колдонмо жеке даректин ордуна ат менен портту максат кылат.

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

Туннель секириктин хост жагында калат, ал эми ошол өзгөрмөдөгү порт — прокси уга турган порт. Туннелден ажыраган контейнер эми эч качан болбогон маршрутту сынап көрүүнүн ордуна бир белгилүү секирикте ишенип кетет.

Туннель кайда жашаарын танда

Жеке API керек болгон Compose кызматы үчүн үч форма мүмкүн, алар туннелди кайсы процесс ээлегени менен айырмаланат. VPN кардары контейнер образынын ичинде иштей алат, бул туннель түзмөгүн ачып, ага коштоочу тармактык башкаруу мүмкүнчүлүгүн берүүнү талап кылат. Колдонмо өзүнчө туннель контейнеринин тармактык ат мейкиндигин бөлүшө алат, ошондо эки процесс те бир стекти жана бир маршруттоо таблицасын көрөт. Же туннель хостто кала алат, хосттон контейнерге тар өткөргүч менен.

Алгачкы экөө профиль файлдарын, кайра туташуу жүрүм-турумун жана резолвер саясатын долбоорго тартат жана файлдагы ар бир кызматты туннелдин ден соолугуна көз каранды кылат. Бир API чакыруу үчүн бул өтө көп байланыш. Бир ички акыркы чекитти окуган иштеп чыгуу стеги үчүн хост жагындагы өткөргүч — каттоо маалыматтарын платформа командасы башкарган жерде сактаган эң кичине өзгөртүү.

Хостто бир тар жолду жарыяла

Өткөргүч мураска алган нерседен башта: аны туннелди ээлеген эсеп менен иштет, ошондо анын чыгуучу сокеттери хосттун маршруттарын жана хосттун резолверин алат. nginx-тин бир location блогу бир жолду камтыйт.

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

Даректи жана портту убактылуу деп карап, API чындап уккан жупту кой. Ар бир кошумча upstream өзүнүн location блогун алат, ал эми ар бир блок ушул кызмат чакырган жолдорго гана жол берүүсү керек, ошондо прокси жеке тармакка жалпы эшик болуп калбайт. Угуучуну host-gateway аркылуу келген кардарлар үчүн көпүрө дарегине, кардар хосттун тармактык ат мейкиндигин бөлүшкөндө гана loopback-ко байланыштыр, ал эми 0.0.0.0 ге эч качан байланыштырба. Дагы бош портту танда: мурун ээленген номер проксини укпай калтырат, ал эми контейнер убакыт чегинен өтө берет, муну сен баштаган тармактык бузулуудан ажыратуу мүмкүн эмес.

Порттор, аттар жана TLS чечими

Аттарды чечүү маршруттоо сыяктуу эле бөлүнөт. Контейнердин ачык издөөлөрү кыймылдаткычтын резолвери аркылуу өтөт, ошондуктан хостто чечилген жеке ат контейнердин ичинде чечилбейт. Прокси — жеке атты чечүүчү компонент, анткени ал хосттун резолверин мураска алат.

TLS — кийинкиге калтырылып, анан кийинки ишсиздикти түшүндүргөн чечим. Эгер прокси байттарды тийбестен өткөрсө, контейнер API-нин өзүнүн сертификатын көрөт жана ишеним кампасында ички CA керек болот. Эгер прокси TLS-ти бүтүрсө, ал ишеним хостко өтөт жана колдонмо алган host аталышынан шилтемелерди кура баштайт. Бир жайгашууну тандап, аны ар бир ресурска колдон, анткени экинчиси чыгарган кайра багыттоо контейнер чече албаган хост атына көрсөтөт.

Кызматтын ичинен текшер

Суроону хосттон эмес, контейнерден жибер: прокси жолуна жөнөкөй curl, анан колдонмонун өзүнүн ден соолук текшерүүсү. Прокси жооп берсе да колдонмо дагы эле иштебей жатса, үч нерсени салыштыр: ал кураган негизги URL, анын чөйрөсүндөгү каалаган прокси өзгөрмөсү жана ал ишенген CA. Баары контейнердин чөйрөсүндө жана журналдарында, ал эми кайсы бирин оңдосоң да VPN ге тийбейт.

Тандалган жайгашууну долбоордун README файлына дагы жаңы кезинде жаз. Болбосо бул убакыт чегине туш болгон кийинки адам ошол түштөн кийинки убакытты туннелдин хостто жашаарын кайра ачууга жумшайт.

Тектеш макалалар