← все темы

Сети и HTTP

Вопросов с разбором: 24. В боте эти же карточки приходят по расписанию повторений.

1 Блок 1 из 6: Основы сетей — Что такое модели OSI и TCP/IP и зачем бэкендеру уровни?
Сеть описывают уровнями: каждый решает свою задачу и пользуется уровнем ниже.

TCP/IP (практическая модель):
- Прикладной — HTTP, DNS, SMTP, gRPC. Здесь живёт наш код.
- Транспортный — TCP, UDP: доставка между процессами (порты).
- Сетевой — IP: доставка между хостами (адреса, маршрутизация).
- Канальный/физический — Ethernet, Wi-Fi.

OSI — теоретическая модель из 7 уровней: физический, канальный, сетевой, транспортный, сеансовый, представления, прикладной.

Зачем бэкендеру: понимать, где ломается — DNS не резолвится (L7), порт закрыт (L4), хост недоступен (L3). И различать балансировщики L4 (TCP) и L7 (HTTP).
2 Блок 1 из 6: Основы сетей — Что такое IP-адрес, порт и сокет?
- IP-адрес — адрес хоста в сети: 93.184.216.34 (IPv4) или 2606:2800::1 (IPv6).
- Порт — номер 0–65535, который определяет процесс на хосте: 80 — HTTP, 443 — HTTPS, 5432 — PostgreSQL, 6379 — Redis.
- Сокет — конечная точка соединения: IP + порт. TCP-соединение однозначно задаётся четвёркой (src_ip, src_port, dst_ip, dst_port) и протоколом.

Важно:
- сервер слушает один порт, но держит тысячи соединений — они различаются портом и адресом клиента;
- 127.0.0.1 (localhost) доступен только с этой машины, 0.0.0.0 — слушать на всех интерфейсах. Классическая ошибка в Docker: сервер слушает 127.0.0.1 внутри контейнера, и снаружи до него не достучаться.
3 Блок 1 из 6: Основы сетей — Чем TCP отличается от UDP? 🔥
TCP — надёжный поток байтов с установкой соединения:
- гарантирует доставку, порядок и отсутствие дублей;
- управляет потоком и перегрузкой;
- цена — задержки на рукопожатие и повторные передачи.
Применение: HTTP/1.1 и HTTP/2, базы данных, SSH, почта.

UDP — отдельные датаграммы без соединения:
- без гарантий доставки и порядка, без повторов;
- минимальные накладные расходы и задержка.
Применение: DNS, видео- и голосовые звонки, игры, метрики (StatsD), а также QUIC (HTTP/3), который строит надёжность поверх UDP сам.

Коротко: TCP — когда важна каждая байт-за-байтом доставка, UDP — когда важнее скорость и потеря пакета не критична.
4 Блок 1 из 6: Основы сетей — Как устанавливается и закрывается TCP-соединение? 🔥
Установка — трёхстороннее рукопожатие (3-way handshake):
клиент → SYN           (хочу соединиться, мой seq = x)
сервер → SYN-ACK (ок, мой seq = y, жду x+1)
клиент → ACK (жду y+1) — соединение установлено


Это 1 RTT (время туда-обратно) до первого байта данных. Для HTTPS добавляется ещё TLS-рукопожатие.

Закрытие — четыре шага: каждая сторона отправляет FIN и получает ACK. Сторона, закрывшая первой, переходит в TIME_WAIT (обычно до 2 минут), чтобы опоздавшие пакеты не попали в новое соединение.

Практика:
- установка соединения дорогая → нужны keep-alive и пулы соединений (к БД, к HTTP-сервисам);
- тысячи сокетов в TIME_WAIT — признак, что соединения открываются на каждый запрос.
5 Блок 1 из 6: Основы сетей — Как TCP обеспечивает надёжную доставку?
- Sequence numbers — каждый байт пронумерован, получатель собирает данные по порядку и отбрасывает дубли.
- ACK и повторная передача — получатель подтверждает принятое; не пришло подтверждение за таймаут — сегмент отправляется заново.
- Контрольная сумма — повреждённые сегменты отбрасываются.
- Flow control (окно получателя) — отправитель не шлёт больше, чем получатель успевает принять.
- Congestion control (slow start, CUBIC, BBR) — отправитель снижает скорость, если сеть перегружена.

Следствие — head-of-line blocking: если потерялся один сегмент, все следующие ждут его повторной передачи, даже если уже пришли. Это одна из причин появления HTTP/3 поверх UDP.
6 Блок 1 из 6: Основы сетей — Как работает DNS? 🔥
DNS переводит доменное имя в IP-адрес.

Как резолвится api.example.com:
1. Кэш приложения/ОС и файл /etc/hosts.
2. Рекурсивный резолвер (провайдера, 8.8.8.8, 1.1.1.1), у него тоже кэш.
3. Если в кэше нет — резолвер идёт по цепочке: корневой сервер → сервер зоны .com → авторитетный сервер example.com.
4. Ответ кэшируется на время TTL.

Основные записи: A (IPv4), AAAA (IPv6), CNAME (псевдоним), MX (почта), TXT (проверки, SPF), NS (авторитетные серверы).

Практика: из-за TTL смена IP распространяется не мгновенно. Перед переездом TTL заранее снижают. В Docker и Kubernetes сервисы находят друг друга по имени через встроенный DNS.
7 Блок 2 из 6: HTTP — Что такое HTTP и из чего состоят запрос и ответ?
HTTP — прикладной протокол «запрос — ответ» без состояния (stateless): каждый запрос самодостаточен, сервер не помнит предыдущих. Состояние передают явно: cookie, токены.

Запрос:
POST /api/orders HTTP/1.1
Host: shop.example.com
Content-Type: application/json
Authorization: Bearer eyJhbGci...

{"product_id": 42, "qty": 2}

Стартовая строка (метод, путь, версия), заголовки, пустая строка, тело.

Ответ:
HTTP/1.1 201 Created
Content-Type: application/json
Location: /api/orders/1001

{"id": 1001, "status": "new"}

Статусная строка (версия, код, фраза), заголовки, тело.
8 Блок 2 из 6: HTTP — Какие есть HTTP-методы и для чего они? 🔥
- GET — получить ресурс. Без тела, без побочных эффектов.
- POST — создать ресурс или выполнить действие.
- PUT — заменить ресурс целиком (или создать по известному URL).
- PATCH — частично изменить ресурс.
- DELETE — удалить ресурс.
- HEAD — как GET, но только заголовки (проверить существование, размер).
- OPTIONS — какие методы поддерживаются; используется в CORS preflight.

Важно: метод — это контракт. Если GET что-то меняет, его могут повторить браузер, прокси, краулер или prefetch, и изменение случится несколько раз.
9 Блок 2 из 6: HTTP — Какие HTTP-методы безопасные и какие идемпотентные? 🔥
- Безопасный (safe) — не меняет состояние сервера: GET, HEAD, OPTIONS.
- Идемпотентный — повтор запроса даёт тот же эффект на сервере, что и один вызов: GET, HEAD, OPTIONS, PUT, DELETE.
- Не идемпотентные: POST (два вызова — два заказа) и в общем случае PATCH ({"balance": "+100"}).

Тонкость: идемпотентность — про состояние, а не про ответ. Второй DELETE /orders/1 может вернуть 404 вместо 204, но ресурс в обоих случаях удалён.

Почему это важно: идемпотентные запросы можно безопасно повторять при таймауте — так делают клиенты, прокси и балансировщики. Для POST повтор безопасен только с ключом идемпотентности (Idempotency-Key).
10 Блок 2 из 6: HTTP — Какие бывают коды ответа HTTP? 🔥
- 1xx — информационные: 101 Switching Protocols (переход на WebSocket).
- 2xx — успех: 200 OK, 201 Created, 202 Accepted (принято в обработку), 204 No Content.
- 3xx — перенаправление: 301 (навсегда), 302/307 (временно), 304 Not Modified (кэш актуален).
- 4xx — ошибка клиента: 400 (плохой запрос), 401 (не аутентифицирован), 403 (нет прав), 404, 405 (метод не поддерживается), 409 Conflict, 422 (не прошла валидация), 429 Too Many Requests.
- 5xx — ошибка сервера: 500, 502 Bad Gateway, 503 Service Unavailable, 504 Gateway Timeout.

Частый вопрос: 401 — «кто вы?» (нет или неверные учётные данные), 403 — «я знаю, кто вы, но нельзя».

Правило: 4xx — повторять тот же запрос бессмысленно, нужно его исправить; 5xx и 429 — можно повторить позже.
11 Блок 2 из 6: HTTP — Какие HTTP-заголовки нужно знать бэкендеру?
Содержимое: Content-Type (формат тела), Content-Length, Accept (что клиент готов принять), Content-Encoding: gzip.

Аутентификация: Authorization: Bearer ..., Cookie / Set-Cookie.

Кэширование: Cache-Control, ETag / If-None-Match, Last-Modified.

Соединение и прокси: Host (обязателен, на одном IP много сайтов), Connection: keep-alive, X-Forwarded-For / X-Forwarded-Proto (реальный IP и схема клиента за прокси).

CORS: Origin, Access-Control-Allow-Origin.

Прочее: Location (куда редирект или где создан ресурс), Retry-After (для 429/503), X-Request-ID (сквозной ID запроса для логов и трейсинга).

Подвох: X-Forwarded-For легко подделать, доверять ему можно только если его выставляет ваш прокси.
12 Блок 2 из 6: HTTP — Что такое cookie и какие у них атрибуты безопасности?
Cookie — небольшие данные, которые сервер сохраняет в браузере через Set-Cookie, а браузер автоматически прикладывает к запросам на этот домен. Основное применение — идентификатор сессии.

Set-Cookie: sessionid=abc123; Path=/; Max-Age=1209600; HttpOnly; Secure; SameSite=Lax


- HttpOnly — недоступна из JavaScript. Защищает сессию от кражи через XSS.
- Secure — только по HTTPS.
- SameSite — отправлять ли cookie при запросах с других сайтов: Strict, Lax (по умолчанию в браузерах), None (только вместе с Secure). Основная защита от CSRF.
- Domain / Path — для каких адресов отправлять.
- Expires / Max-Age — срок жизни; без них cookie живёт до закрытия браузера.
13 Блок 2 из 6: HTTP — Что происходит, когда вводишь URL в браузере и нажимаешь Enter? 🔥
1. Разбор URL: схема, домен, порт, путь. Проверка HSTS — сразу идти по HTTPS.
2. DNS: домен → IP (кэши браузера и ОС, резолвер, цепочка до авторитетного сервера).
3. TCP: трёхстороннее рукопожатие с сервером на порту 443 (для HTTP/3 — QUIC поверх UDP).
4. TLS: согласование шифров, проверка сертификата, выработка ключей.
5. HTTP-запрос: GET / с заголовками и cookie.
6. На стороне сервера: CDN или балансировщик → reverse proxy (nginx) → сервер приложения (gunicorn/uvicorn) → Django/FastAPI → БД, кэш → ответ.
7. Ответ: статус, заголовки, HTML; браузер может закэшировать по Cache-Control.
8. Рендеринг: разбор HTML, загрузка CSS/JS/картинок (часто по тому же соединению), построение DOM, отрисовка.

На интервью бэкендера стоит подробнее остановиться на шагах 2–6: что такое RTT, зачем keep-alive и как запрос проходит через инфраструктуру.
14 Блок 3 из 6: Версии HTTP — Чем отличаются HTTP/1.1, HTTP/2 и HTTP/3? 🔥
HTTP/1.1 (1997):
- текстовый протокол, keep-alive по умолчанию — соединение переиспользуется;
- в одном соединении запросы идут по очереди → браузеры открывают по 6 соединений на домен;
- head-of-line blocking на уровне HTTP: медленный ответ задерживает следующие.

HTTP/2 (2015):
- бинарный протокол, мультиплексирование — много параллельных потоков в одном TCP-соединении;
- сжатие заголовков (HPACK);
- на практике всегда поверх TLS;
- остаётся HOL blocking на уровне TCP: потеря одного пакета тормозит все потоки.

HTTP/3 (2022):
- поверх QUIC (UDP), TLS 1.3 встроен в протокол;
- потоки независимы — потеря пакета тормозит только свой поток;
- быстрее установка соединения (1 RTT, при повторном — 0-RTT), переживает смену сети (Wi-Fi → мобильная).

Для бэкенда: обычно HTTP/2 и HTTP/3 терминирует nginx или CDN, а до приложения доходит HTTP/1.1. gRPC работает поверх HTTP/2.
15 Блок 3 из 6: Версии HTTP — Что такое keep-alive и пул соединений?
Keep-alive — TCP-соединение не закрывается после ответа и используется для следующих запросов. Экономит рукопожатия TCP и TLS (несколько RTT на каждый запрос).

Пул соединений — клиент держит набор открытых соединений и раздаёт их запросам.

# плохо: новое соединение (TCP + TLS) на каждый запрос
for user_id in ids:
requests.get(f'https://api.example.com/users/{user_id}')

# хорошо: Session переиспользует соединения
with requests.Session() as session:
for user_id in ids:
session.get(f'https://api.example.com/users/{user_id}', timeout=5)

# async: один клиент на всё приложение, а не на каждый запрос
client = httpx.AsyncClient(timeout=5, limits=httpx.Limits(max_connections=100))


То же для БД: пул соединений в SQLAlchemy, CONN_MAX_AGE в Django, PgBouncer перед PostgreSQL.
16 Блок 4 из 6: Безопасность — Как работает HTTPS и TLS-рукопожатие? 🔥
HTTPS = HTTP поверх TLS. Даёт три вещи: шифрование (никто не прочитает), целостность (никто не подменит), аутентификацию сервера (это действительно тот сайт).

Рукопожатие TLS 1.3 (упрощённо):
1. ClientHello: поддерживаемые шифры и ключевой материал клиента (Диффи — Хеллман).
2. ServerHello: выбранный шифр, ключевой материал сервера, сертификат и подпись.
3. Клиент проверяет сертификат: подписан доверенным центром (CA), не истёк, выдан на этот домен.
4. Обе стороны независимо вычисляют общий симметричный ключ — дальше трафик шифруется им (AES, ChaCha20).

TLS 1.3 занимает 1 RTT (TLS 1.2 — 2 RTT), при повторном подключении возможно 0-RTT.

Почему симметричный ключ: асимметричная криптография медленная и используется только чтобы безопасно договориться о ключе.

Практика: TLS обычно терминируется на nginx или балансировщике; сертификаты — Let's Encrypt с автопродлением.
17 Блок 4 из 6: Безопасность — Что такое Same-Origin Policy и CORS? 🔥
Same-Origin Policy — браузер не даёт JavaScript со страницы одного источника (origin = схема + домен + порт) читать ответы от другого источника.

CORS (Cross-Origin Resource Sharing) — механизм, которым сервер разрешает браузеру такие запросы.

Как работает:
- Браузер добавляет заголовок Origin: https://app.example.com.
- Сервер отвечает Access-Control-Allow-Origin: https://app.example.com, и браузер отдаёт ответ скрипту.
- Для «непростых» запросов (PUT/DELETE, JSON, кастомные заголовки) браузер сначала шлёт preflight OPTIONS и проверяет Access-Control-Allow-Methods и Allow-Headers.

Важно понимать:
- CORS проверяет только браузер. curl, Postman и другой бэкенд его игнорируют — это не защита API.
- Allow-Origin: * нельзя сочетать с cookie (Allow-Credentials: true).
- Ошибку CORS чинят на сервере (django-cors-headers, CORSMiddleware в FastAPI), а не на фронтенде.
18 Блок 5 из 6: Кэширование и прокси — Как работает HTTP-кэширование?
Cache-Control задаёт правила:
- max-age=3600 — ответ свежий час, можно не ходить на сервер;
- no-cache — кэшировать можно, но перед использованием проверять на сервере;
- no-store — не кэшировать вообще (личные данные);
- private — только в браузере; public — можно и в CDN/прокси.

Условные запросы (валидация):
ответ:   ETag: "v42"
повтор: If-None-Match: "v42"
сервер: 304 Not Modified (без тела — данные не изменились)

Аналогично Last-Modified / If-Modified-Since.

Практика:
- статику отдают с хэшем в имени (app.3f9a.js) и max-age=31536000, immutable;
- HTML и API — короткий кэш или no-cache;
- ответы, зависящие от пользователя, — private, иначе CDN покажет чужие данные.
19 Блок 5 из 6: Кэширование и прокси — Что такое прокси, reverse proxy и балансировщик L4 и L7? 🔥
- Forward proxy — работает на стороне клиента: клиенты ходят в интернет через него (корпоративный прокси).
- Reverse proxy — стоит перед серверами: клиент думает, что общается с ним. Терминирует TLS, отдаёт статику, сжимает, кэширует, ограничивает частоту запросов, маршрутизирует. Пример — nginx перед gunicorn.
- Балансировщик нагрузки распределяет запросы между инстансами (round-robin, least connections, по хэшу) и убирает упавшие по health check.

L4 и L7:
- L4 — по IP и порту на уровне TCP/UDP, содержимое не видит. Быстрый, подходит для любого протокола.
- L7 — видит HTTP: маршрутизирует по пути, заголовкам и cookie, умеет повторять запросы, делать sticky sessions, терминировать TLS. Примеры: nginx, Envoy, HAProxy в HTTP-режиме, AWS ALB.

Зачем gunicorn за nginx: nginx хорошо держит медленных клиентов и тысячи соединений, а воркеров приложения мало и они дорогие.
20 Блок 5 из 6: Кэширование и прокси — Что такое CDN и когда он нужен?
CDN (Content Delivery Network) — сеть серверов по всему миру, которые кэшируют контент ближе к пользователю.

Что даёт:
- меньше задержка — ответ приходит из ближайшей точки, а не из вашего дата-центра;
- снимает нагрузку с серверов;
- защищает от DDoS, терминирует TLS, поддерживает HTTP/3.

Что кладут: статику (JS, CSS, картинки, видео), публичные страницы, иногда ответы API с коротким max-age.

Подводные камни:
- инвалидация: обновили файл, а CDN отдаёт старый → версии в имени файла или purge через API;
- персональные ответы без Cache-Control: private закэшируются и уйдут другим пользователям.
21 Блок 6 из 6: Реалтайм и практика — Что такое WebSocket и как он работает? 🔥
WebSocket — двунаправленный канал поверх одного TCP-соединения: и клиент, и сервер могут отправлять сообщения в любой момент.

Установка начинается как HTTP-запрос с апгрейдом:
GET /ws HTTP/1.1
Upgrade: websocket
Connection: Upgrade

HTTP/1.1 101 Switching Protocols

Дальше по соединению идут фреймы WebSocket, а не HTTP.

Применение: чаты, уведомления, совместное редактирование, биржевые котировки, игры.

Что нужно учесть на бэкенде:
- долгоживущие соединения → нужен асинхронный сервер (uvicorn, Django Channels), синхронный воркер на соединение не годится;
- при нескольких инстансах сообщения между ними рассылают через брокер (Redis Pub/Sub);
- реконнект и heartbeat (ping/pong), таймауты на прокси;
- аутентификация при установке соединения.
22 Блок 6 из 6: Реалтайм и практика — Чем отличаются polling, long polling, SSE и WebSocket?
- Polling — клиент спрашивает «есть новое?» каждые N секунд. Просто, но много пустых запросов и задержка до N секунд.
- Long polling — сервер держит запрос открытым, пока не появятся данные или не истечёт таймаут; затем клиент сразу шлёт новый. Почти реалтайм на обычном HTTP.
- SSE (Server-Sent Events) — односторонний поток событий от сервера по одному HTTP-ответу (text/event-stream), браузер сам переподключается. Подходит для уведомлений, прогресса задач, стриминга ответа LLM.
- WebSocket — двунаправленный канал. Нужен, когда клиент тоже часто шлёт данные: чат, игры, совместное редактирование.

Как выбирать: данные идут только от сервера — SSE (проще, работает через обычные прокси); нужен обмен в обе стороны — WebSocket; редкие обновления — обычный polling.
23 Блок 6 из 6: Реалтайм и практика — Какие таймауты нужно выставлять при HTTP-запросах из Python? 🔥
Без таймаута requests ждёт ответа бесконечно: зависший внешний сервис забьёт все воркеры, и ляжет ваш собственный сервис.

# (connect timeout, read timeout)
requests.get(url, timeout=(3, 10))

httpx.get(url, timeout=httpx.Timeout(10, connect=3))


- Connect timeout — сколько ждать установки соединения (обычно 1–5 с).
- Read timeout — сколько ждать данных между байтами ответа.
- Общий дедлайн на всю операцию с повторами (asyncio.timeout).

Вместе с таймаутами:
- ретраи с экспоненциальной задержкой и jitter — только для идемпотентных запросов, 5xx и сетевых ошибок;
- circuit breaker — перестать ходить в лежащий сервис;
- таймаут клиента меньше таймаута того, кто вызывает вас (nginx, upstream-сервис), иначе вы продолжаете работу, ответ на которую уже никто не ждёт.
24 Блок 6 из 6: Реалтайм и практика — Чем отличаются 502 и 504 и как их разбирать?
Оба кода возвращает прокси (nginx, балансировщик), а не ваше приложение.

- 502 Bad Gateway — прокси получил от бэкенда некорректный ответ или обрыв: приложение упало, контейнер перезапускается, порт не слушается, воркер убит по памяти (OOM) посреди запроса.
- 503 Service Unavailable — нет доступных бэкендов или сервис сам сообщает о перегрузке.
- 504 Gateway Timeout — бэкенд не ответил вовремя: долгий SQL-запрос, медленный внешний API, все воркеры заняты.

Как разбирать:
1. Логи прокси (upstream prematurely closed, connect() failed, upstream timed out).
2. Жив ли процесс приложения, не было ли рестартов и OOM (docker ps, dmesg).
3. Для 504 — какие запросы медленные: логи, APM, pg_stat_activity.
4. Согласовать таймауты: proxy_read_timeout у nginx, --timeout у gunicorn, таймауты к БД и внешним API.

Хотите не просто прочитать, а запомнить?

Бот вернёт вам эти вопросы ровно тогда, когда вы начнёте их забывать.