заголовок x-b3-sampled всегда имеет значение 0 при доступе к сервису через входной контроллер

#kubernetes #trace #istio

#kubernetes #трассировка #istio

Вопрос:

У меня установлены Kubernetes 1.17.5 и Istio 1.6.8 с демонстрационным профилем.

И вот моя тестовая настройка [nginx-ingress-controller] -> [прокси<-> ServiceA] -> [прокси<-> ServiceB]

  • Прокси для ServiceA и ServiceB автоматически вводятся Istio (istio-injection =включено)
  • У входного контроллера Nginx не включена трассировка и у него нет прокси-сервера envoy в качестве вспомогательного средства
  • ServiceA передает заголовки трассировки в ServiceB
  • Я пытаюсь отслеживать вызовы из ServiceA в ServiceB и на данный момент меня не волнует диапазон Ingress-> ServiceA

Когда я отправляю запросы на входной контроллер, я вижу, что ServiceA получает все необходимые заголовки трассировки от прокси-сервера

 x-b3-traceid: d9bab9b4cdc8d0a7772e27bb7d15332f
x-request-id: 60e82827a270070cfbda38c6f30f478a
x-envoy-internal: true
x-b3-spanid: 772e27bb7d15332f
x-b3-sampled: 0
x-forwarded-proto: http
  

Проблема в том, что для x-b3-sampled всегда установлено значение 0, и никакие интервалы / трассировки не передаются в Jaeger

Несколько вещей, которые я пробовал

  1. Я добавил Gateway и VirtualService в ServiceA, чтобы предоставлять его через Istio ingressgateway. Когда я отправляю трафик через ingressgateway, все работает так, как ожидалось. Я вижу следы [ingress-gateway]->[ServiceA]->[ServiceB] в JaegerUI
  2. Я также пытался установить Istio с пользовательской конфигурацией и поиграть с параметрами, связанными с отслеживанием, но безуспешно.

Вот конфигурация, которую я пытался использовать

 apiVersion: install.istio.io/v1alpha1
kind: IstioOperator
spec:
  meshConfig:
    enableTracing: true
    defaultConfig:
      tracing:
        sampling: 100
  addonComponents:
    tracing:
      enabled: true
    grafana:
      enabled: false
    istiocoredns:
      enabled: false
    kiali:
      enabled: false
    prometheus:
      enabled: false
  values:
    tracing:
      enabled: true
    pilot:
      traceSampling: 100
  

Комментарии:

1. I've added Gateway and VirtualService to ServiceA to expose it through Istio ingressgateway. When I send traffic through ingressgateway everything works as expected. Я бы сказал, что он работает так, как ожидалось, как указано в документации Using the Istio Gateway, rather than Ingress, is recommended to make use of the full feature set that Istio offers, such as rich traffic management and security features. istio, поэтому я предполагаю, что 1 из функций.

2. Да, отправка запросов через ingressgateway работает должным образом. Но мы обслуживаем тонны трафика через ingress controller, и у нас это работает. Замена его на istio ingressgateway для решения проблемы трассировки была бы слишком большим изменением на данный момент.

3. Когда я заменяю входной контроллер любым другим сервисом и инициализирую запрос к ServiceA изнутри кластера, он работает нормально. Поэтому я думаю, что это как-то связано с тем фактом, что запросы пересылаются извне кластера. Я пытаюсь перенастроить входной контроллер, чтобы удалить все заголовки X-Forwarded- * из запроса к вышестоящим службам, чтобы заставить envoy «думать», что запрос локальный. Посмотрим, исправит ли это проблему.

Ответ №1:

После нескольких дней копания я понял это. Проблема заключается в формате x-request-id заголовка, который использует входной контроллер nginx.

Прокси-сервер Envoy ожидает, что это будет UUID (например, x-request-id: 3e21578f-cd04-9246-aa50-67188d790051 ), но контроллер ingrex передает его как неформатированную случайную строку ( x-request-id: 60e82827a270070cfbda38c6f30f478a ). Когда я передаю правильно отформатированный заголовок x-request-id в запросе к входному контроллеру, он передается прокси-серверу envoy, и запрос получает выборку, как и ожидалось. Я также попытался удалить заголовок x-request-id из запроса от входного контроллера к ServiceA с помощью простого EnvoyFilter. И это также работает, как ожидалось. Прокси-сервер Envoy генерирует новый x-request-id, и запрос отслеживается.

Комментарии:

1. У меня похожая проблема, но на ingress-nginx у меня есть Envoy sidecar для использования MTLS между модулем ingress controller pod и другими службами. Заголовок запроса x-request-id, который выходит из ingress-nginx, имеет следующий формат: ‘4668081de0d9e63cae60680710a23cfd’, но разве он не создан Envoy, поскольку ingress-nginx не создает этот заголовок (и другие b3-заголовки) сам по себе? Итак, мне интересно, почему Envoy не форматирует идентификатор запроса в надлежащей форме UUID.

2. Можете ли вы поделиться тем, как вы убедились, что «x-request-id» отформатирован правильно? Есть какой-нибудь документ, в который я могу заглянуть?