Введение
PARCEL — вымышленный магазин подарков. Посетители смотрят Arc lamp или Clay vase и сравнивают доставку с самовывозом. Самовывоз уже возвращает оценку, а доставка завершается ошибкой. Ваша задача — проследить новый неудачный запрос от входа до ответившего сервиса и восстановить правильные цены доставки, не нарушая самовывоз.
Достаточно базового знакомства с терминалом. Вы измените два коротких файла Nginx, прочитаете настоящие журналы и проверите реальные ответы. Программирование приложения, SDK, внешняя учётная запись, покупка и личные данные не нужны. Все сервисы работают в одном подготовленном учебном экземпляре: это корреляция запросов, а не полноценная платформа распределённой трассировки.
Просматривайте сайт и запрашивайте оценки в Website. Все команды выполняются в Workstation, изначально в /home/labex/project/parcel. Каждая часть имеет собственную среду. Вход на порту 8081 передаёт каждый запрос одному backend. Доставка слушает 8091, самовывоз — 8092. Порт обозначает сетевой сервис; в Workstation адрес 127.0.0.1 означает этот учебный экземпляр.
Общий идентификатор для нового запроса
На этом шаге вы познакомитесь с нормальным клиентским сценарием, увидите ошибку и свяжете новый запрос в двух настоящих журналах. Начните в Website.
Познакомьтесь с магазином
Откройте Arc lamp в разделе Two good things. Карточка показывает $48 и локальную иллюстрацию. Выберите Estimate collection, оставьте Arc lamp и Near, нажмите Get estimate. Должны появиться $2.00 и HTTP 200. Это рабочая функция, которую нужно сохранить. Вернитесь через PARCEL↗, откройте Delivery и нажмите Get estimate: появятся Estimate unavailable и HTTP 404.
HTTP — протокол запросов и ответов браузера. 200 означает успешный ответ; 404 — что получивший запрос сервис не нашёл запрошенный путь. Ошибка соединения отличается: пригодный ответ сервера не был получен. Сейчас идентификатор указан как not available, поэтому ответ клиента пока трудно сопоставить с журналами.

Поймите доказательства
Подготовленный журнал входа уже записывает идентификатор, который Nginx создаёт для каждого запроса. Backend умеет записывать переданный идентификатор. После соединения этих возможностей один неудачный запрос создаст записи такого вида; точки обозначают ваш идентификатор:
entry: {"id":"...","path":"/api/delivery","status":404,"upstream":"127.0.0.1:8091","upstream_status":"404"}
delivery: {"service":"delivery","id":"...","path":"/v1/shipping","status":404}
Путь входа — тот, который запросил браузер. Путь backend — фактически переданный входом. upstream обозначает адрес получателя, а upstream_status — его реальный статус ответа. Одинаковый идентификатор связывает наблюдения; при большом числе запросов сравнение только времени менее надёжно. Тела запросов и секреты не записываются.
Свяжите идентификатор
Перейдите в Workstation. pwd выводит текущий каталог, cat — содержимое файла:
pwd
Ожидается /home/labex/project/parcel. Если вы вышли из каталога, выполните cd /home/labex/project/parcel; cd меняет текущий каталог. Пути без начального /, например correlation.conf, отсчитываются от этого каталога.
cat correlation.conf
Пока в файле только комментарий. Nginx — подготовленный входной сервер. Его конфигурация состоит из директив, заканчивающихся точкой с запятой. Главная конфигурация включает этот короткий файл; основной каркас менять не нужно.
Заголовок — именованное значение в HTTP-запросе или ответе. proxy_set_header задаёт заголовок, передаваемый backend; add_header добавляет заголовок к ответу клиенту. $request_id — значение, созданное Nginx для этого запроса. always включает заголовок и при ошибках, а не только при успехе. X-Request-ID — принятое здесь общее имя. Вход сам создаёт идентификатор, не доверяя значению посетителя.
cat > correlation.conf заменяет файл с помощью here-документа. Вставьте весь блок, включая последний CONF на отдельной строке. Кавычки в 'CONF' сохраняют буквальный $request_id, чтобы его обработал Nginx, а не оболочка:
cat > correlation.conf <<'CONF'
proxy_set_header X-Request-ID $request_id;
add_header X-Request-ID $request_id always;
CONF
Прочитайте сохранённый файл и примените его предоставленным помощником. bash запускает этот shell-скрипт. Он сначала проверяет синтаксис и перезагружает Nginx только при корректной конфигурации; маршруты не исправляет и цены не оценивает.
cat correlation.conf
bash reload.sh
Ожидайте успешную проверку и Configuration accepted. Send a new request to test it. Если указана ошибка строки, сравните написание, точки с запятой и буквальные знаки доллара с блоком, перезапишите файл и повторите. При ошибке синтаксиса предыдущая конфигурация продолжает работать. Перезагрузка не изменит старый ответ: нужен новый запрос.
Проследите собственную новую ошибку
В Delivery на Website снова нажмите Get estimate. Ошибка остаётся, но Request reference теперь содержит 32 шестнадцатеричных символа. Скопируйте именно новое значение, а не точки из примера или идентификатор со снимка.
Вернитесь в Workstation. Переменная оболочки хранит значение для следующих команд. Замените PASTE_YOUR_NEW_REQUEST_REFERENCE_HERE точным новым идентификатором из Website. Сохраните одинарные кавычки и не ставьте пробелы вокруг =. Кавычки сохраняют буквальное значение; не запускайте неизменённый шаблон:
REQUEST_ID='PASTE_YOUR_NEW_REQUEST_REFERENCE_HERE'
grep выводит совпадающие строки. -F рассматривает значение как обычный текст; двойные кавычки сохраняют значение переменной целиком. Абсолютные пути работают из любого каталога:
grep -F "$REQUEST_ID" /var/log/parcel/entry.jsonl
grep -F "$REQUEST_ID" /var/log/parcel/delivery.jsonl
В обеих записях должны быть точно одинаковый идентификатор, путь backend /v1/shipping и статус 404. Это доказывает, что доставка дошла до отвечающего backend, а не до остановленного сервиса или отсутствующей связи. Пустой вывод часто означает старый или ошибочно скопированный идентификатор: запросите снова в Website, скопируйте новое значение и заново задайте REQUEST_ID. Одного заголовка ответа недостаточно — на backend останется -; нужны обе директивы.
Проверка шага отправляет новые запросы только для чтения. Она не требует конкретной переменной оболочки, истории команд или скопированного файла журнала.
Восстановите маршрут и сохраните обе оценки
На этом шаге вы исправите доставку по двум записям и контракту сервиса. Начните в Workstation.
Разделите адрес и путь
Выведите конфигурацию маршрутов через cat:
cat routes.conf
Блок location = совпадает с точным публичным путём; фигурные скобки группируют директивы. proxy_pass указывает Nginx получателя. В http://127.0.0.1:8091/v1/shipping адрес и порт выбирают сервис, а /v1/shipping — операцию внутри него. Ошибка возможна в любой части. Для этих точных location настроенный путь backend заменяет совпавший публичный путь; параметры запроса продолжают передаваться.
Контракт подготовленных сервисов:
| Публичная операция | Ответственный сервис | Адрес сервиса | Путь backend |
|---|---|---|---|
| Доставка | delivery | http://127.0.0.1:8091 |
/v1/delivery |
| Самовывоз | collection | http://127.0.0.1:8092 |
/v1/collection |
Оба отвечают на /health, но исправный процесс не доказывает правильность маршрута. Журналы показали доставку на 8091 по /v1/shipping. Этот сервис отвечает за доставку, но такого пути не предоставляет. Контракт требует /v1/delivery. Адрес и путь самовывоза уже правильные.
Примените небольшое исправление
Замените только редактируемый файл маршрутов, сохранив самовывоз:
cat > routes.conf <<'CONF'
location = /api/delivery {
proxy_pass http://127.0.0.1:8091/v1/delivery;
}
location = /api/collection {
proxy_pass http://127.0.0.1:8092/v1/collection;
}
CONF
bash reload.sh
Если синтаксис неверен, сравните скобки и точки с запятой, перепишите и повторите. Не меняйте подготовленные backend, сайт, журналы и основной конфигурационный каркас. Возврат 200 без настоящей правильной оценки лишь скроет дефект.
Проверьте реальные цены и корреляцию
В Website откройте Delivery и снова запросите Arc lamp / Near. Ожидаются $6.00, HTTP 200 и новый идентификатор. Для Clay vase / Far ожидается $13.00. В Collection Arc lamp / Near по-прежнему должен давать $2.00, а Clay vase / Far — $4.00. Каждый щелчок создаёт новый запрос, поэтому идентификаторы должны отличаться. Карточки через PARCEL↗ должны сохранять картинки и цены.

Вернитесь в Workstation. curl отправляет HTTP-запрос. -sS скрывает прогресс, но показывает ошибки соединения; -i включает заголовки ответа. Одинарные кавычки оставляют & внутри URL, чтобы оболочка его не интерпретировала. Параметры после ? выбирают товар и расстояние:
curl -sS -i 'http://127.0.0.1:8081/api/delivery?item=vase&zone=far'
Ожидайте HTTP/1.1 200 OK, заголовок X-Request-ID и JSON с "service": "delivery", "amount": 13, "currency": "USD". JSON — текстовый формат именованных значений. request_id в теле должен совпасть с заголовком. Регистр букв имени заголовка может отличаться без изменения смысла.
Возьмите идентификатор этого ответа и заново задайте REQUEST_ID и повторите обе команды grep -F из шага 1. Оба журнала теперь показывают 200, а delivery — /v1/delivery. Старые 404 полезны как история: не удаляйте и не переписывайте их.
Отдельно проверьте сохранённую функцию:
curl -sS -i 'http://127.0.0.1:8081/api/collection?item=lamp&zone=near'
Ожидаются 200, "service": "collection" и "amount": 2. Получение 404 — обычный HTTP-ответ, поэтому curl без опции ошибки по HTTP-статусу может завершиться нормально. Ошибка соединения указывает на недоступный процесс или неверный адрес; проверьте последнюю рабочую конфигурацию, не смешивая это с доказательством ошибки пути выше.
Итоговая проверка запрашивает все сочетания товара и расстояния для обеих операций, сопоставляет новые идентификаторы с настоящими журналами и проверяет весь сайт. Добавляются лишь обычные записи доступа; оценивание не перезагружает конфигурацию, не переписывает файлы и не создаёт заказы.
Резюме
Вы связали журналы входа и backend нового запроса одним сгенерированным идентификатором, отличили отсутствующий путь отвечающего сервиса от ошибки соединения и исправили реальный маршрут. Вы проверили разные бизнес-результаты и сохранили самовывоз. Самостоятельное задание меняет сервис-получатель, используя те же методы адреса, пути и корреляции.



