Распределенная трассировка для Kafka с помощью OpenTelemetry в Node

В этом руководстве вы узнаете, как запустить OpenTelemetry в Node для генерации диапазонов для различных операций Kafka (например, потребление и производство) и, в конечном итоге, визуализации трассировки. Мы также коснемся основ Kafka, OpenTelemetry, распределенной трассировки и того, как все они работают вместе.

Если вы уже знакомы с Kafka и OpenTelemetry, смело переходите к практической части этого руководства.

Что вас ожидает

  • Что такое Apache Kafka
  • Что такое OpenTelemetry
  • Что такое распределенная трассировка
  • Что такое инструментарий OpenTelemetry
  • Как использовать Kafka с OpenTelemetry в Node
  • Визуализация трасс OpenTelemetry
  • Устранение проблем с установкой узла OpenTelemetry
  • Дополнительные ресурсы по OpenTelemetry

Что такое Apache Kafka?

Kafka — это платформа распределенного потока событий с открытым исходным кодом, с помощью которой мы можем отправлять события в темы и потреблять их. Вы можете узнать больше о Kafka здесь.

Что такое OpenTelemetry?

OpenTelemetry — это проект с открытым исходным кодом, представляющий собой набор API и SDK. Под руководством CNCF (Cloud Native Computing Foundation, тот же фонд, который отвечает за Kubernetes), он позволяет нам собирать, экспортировать и генерировать трассировки, журналы и метрики (также известные как три столпа наблюдаемости).

В мире распределенного программного обеспечения системы обмена сообщениями (например, Kafka) являются ключевыми для обеспечения связи между независимыми микросервисами, что облегчает создание сложных систем.

Но понять, какой путь прошло каждое сообщение, куда оно направляется, почему и когда, настолько же важно, насколько и сложно.

Пользователям нужен способ визуализации и устранения неполадок в сложной распределенной архитектуре.

OpenTelemetry — это наш инструмент для сбора данных из различных транзакций в наших сервисах и компонентах (включая различные брокеры сообщений, такие как Kafka) и понимания производительности и поведения нашего программного обеспечения.

В этом конкретном руководстве мы сосредоточимся на распределенной трассировке, а более глубокое погружение в OpenTelemetry вы можете совершить в этом кратком руководстве.

Что такое распределенная трассировка?

Распределенная трассировка определяет диапазоны и трассы. Трассировка отслеживает продвижение запросов через сервисы, брокеры сообщений и другие компоненты нашей системы.

Трасса — это дерево пролетов. Пролет — это характеристика действия/процесса, который произошел между нашими сервисами. Например, обращение к базе данных, внешней службе, отправка сообщений в тему Kafka и т.д.

Трассировки информируют нас о длительности каждого запроса, о том, с какими компонентами и сервисами он взаимодействовал, о задержке, возникающей на каждом этапе, и о другой ценной информации о характере этой активности.

Что такое инструментарий OpenTelemetry?

Инструментарий — это часть кода, отвечающая за генерацию пролетов (из которых состоят трассы) и отправку их на специальный бэкенд по вашему выбору. В дальнейшем, в зависимости от используемого вами инструмента, конечной целью является их визуализация и использование этой визуализации для устранения неполадок в нашей системе.

Для этого мы используем SDK, предоставляемые OpenTelemetry, в котором собраны полезные инструменты.

OpenTelemetry включает инструментарий для различных библиотек на разных языках, в том числе инструментарий Kafka, отвечающий за создание пролетов Kafka.

Как использовать Kafka с OpenTelemetry в Node

К этому моменту у вас уже должна быть вся необходимая теория, так что давайте начнем писать код. Прежде чем мы начнем — это руководство предполагает, что вы запускаете Kafka на локальной машине — если это не так, посетите это краткое руководство (оно показывает, как запустить Kafka с помощью docker в самом начале).

Практическая часть

Сначала создадим совершенно новое приложение Express app & установим соответствующие пакеты:

npx express-generator kafkaotel
npm install
npm install kafkajs
npm install @opentelemetry/exporter-collector
npm install @opentelemetry/auto-instrumentations-node
npm install @opentelemetry/sdk-node @opentelemetry/api opentelemetry-instrumentation-kafkajs
Войдите в полноэкранный режим Выйти из полноэкранного режима

Теперь создадим файл трассировки, который будет создавать диапазоны и трассировки для операций Kafka (например, производить и потреблять). Для этого мы используем инструментарий opentelemetry kafkajs:

/* tracing.js */
const { KafkaJsInstrumentation } = require('opentelemetry-instrumentation-kafkajs');
const { NodeTracerProvider } = require('@opentelemetry/sdk-trace-node');
// Require dependencies
const opentelemetry = require("@opentelemetry/sdk-node");
const tracerProvider = new NodeTracerProvider({
 // be sure to disable old plugin
 plugins: {
   kafkajs: { enabled: false, path: 'opentelemetry-plugin-kafkajs' }
 }
});
const sdk = new opentelemetry.NodeSDK({
 tracerProvider,
 traceExporter: new opentelemetry.tracing.ConsoleSpanExporter(),
 instrumentations: [
   new KafkaJsInstrumentation({
     // see kafkajs instrumentation docs for available configuration
   })
 ]
});
sdk.start()
Войдите в полноэкранный режим Выход из полноэкранного режима

Давайте обновим package.json и потребуем файл трассировки, чтобы opentelemetry мог выполнять инструментацию:

"scripts": {
 "start": "node --require './tracing.js' ./bin/www"
},
Войти в полноэкранный режим Выход из полноэкранного режима

Теперь давайте обновим нашу основную конечную точку, чтобы она могла создавать и потреблять сообщения Kafka:

const express = require('express');
const router = express.Router();
const { Kafka } = require('kafkajs');
const kafka = new Kafka({
 clientId: 'my-app',
 brokers: ['localhost:9092'],
})
const sendKafkaMessage = async () => {
 const producer = kafka.producer();
 await producer.connect();
 await producer.send({
   topic: 'test-topic',
   messages: [
     { value: 'Hello KafkaJS user!' },
   ],
 })
 await producer.disconnect();
}
const consumeMessages = async () => {
 const consumer = kafka.consumer({ groupId: 'test-group' });
 await consumer.connect();
 await consumer.subscribe({ topic: 'test-topic', fromBeginning: true });
 await consumer.run({
   eachMessage: async ({ topic, partition, message }) => {
     console.log({
       value: message.value.toString(),
     })
   },
 })
}
/* GET home page. */
router.get('/', async function(req, res, next) {
 await sendKafkaMessage();
 await consumeMessages();
 res.render('index', { title: 'Express' });
});
module.exports = router;
Войти в полноэкранный режим Выйти из полноэкранного режима

Теперь вы можете запустить npm start и запустить go to localhost:3000 в вашем любимом браузере.

После этого вы сможете увидеть в консоли продюсерский пролет, как показано здесь:

{
  traceId: '003cd8ece100e4bed2d05867d3a98dc0',
  parentId: undefined,
  name: 'test-topic',
  id: 'c83af592be261547',
  kind: 3,
  timestamp: 1646386704369183,
  duration: 28633,
  attributes: {
    'messaging.system': 'kafka',
    'messaging.destination': 'test-topic',
    'messaging.destination_kind': 'topic'
  },
  status: { code: 0 },
  events: []
}

Войти в полноэкранный режим Выход из полноэкранного режима

А также пролет потребителя:

{
  traceId: '003cd8ece100e4bed2d05867d3a98dc0',
  parentId: 'c83af592be261547',
  name: 'test-topic',
  id: '875ea3c9e2b0dbdf',
  kind: 4,
  timestamp: 1646386726625784,
  duration: 562,
  attributes: {
    'messaging.system': 'kafka',
    'messaging.destination': 'test-topic',
    'messaging.destination_kind': 'topic',
    'messaging.operation': 'process'
  },
  status: { code: 0 },
  events: []
}
Войти в полноэкранный режим Выйти из полноэкранного режима

Вот и все! Теперь вы знаете, как использовать Kafka и OpenTelemetry вместе, и можете создавать диапазоны для операций Kafka, которые происходят в ваших микросервисах.

До сих пор мы только выводили данные в консоль. Но OpenTelemetry может многое предложить в плане визуализации, поэтому давайте посмотрим, как этого можно добиться.

Визуализация трасс OpenTelemetry в Node

Для целей данного руководства я решил использовать Aspecto в качестве инструмента визуализации. Это связано с тем, что Aspecto предоставляет встроенную поддержку для визуализации систем обмена сообщениями, таких как Kafka (и, конечно, любой другой части наших микросервисных архитектур).

Прежде чем приступить к работе, вы можете попробовать сами, воспользовавшись бесплатным планом, который не имеет ограниченных возможностей.

Попробуйте эту Live Playground, чтобы получить лучшее представление.

Вот как это будет выглядеть в конце процесса:

Вы также можете нажать на конкретный узел и просмотреть данные трассировки:

Вы можете проследить за этим, создав бесплатный аккаунт, затем получить API-ключ Aspecto и изменить файл tracing.js:

const { NodeTracerProvider } = require('@opentelemetry/sdk-trace-node');
const { Resource } = require('@opentelemetry/resources');
const { SemanticResourceAttributes } = require('@opentelemetry/semantic-conventions');
const { SimpleSpanProcessor } = require('@opentelemetry/sdk-trace-base');
const { CollectorTraceExporter } = require('@opentelemetry/exporter-collector');
const { registerInstrumentations } = require('@opentelemetry/instrumentation');
const { KafkaJsInstrumentation } = require("opentelemetry-instrumentation-kafkajs");
const provider = new NodeTracerProvider({
 resource: new Resource({
   [SemanticResourceAttributes.SERVICE_NAME]: 'kafka-service' // service name is required
 }),
});
provider.register();
provider.addSpanProcessor(
 new SimpleSpanProcessor(
   new CollectorTraceExporter({
     url: 'https://otelcol.aspecto.io/v1/trace',
     headers: {
       // Aspecto API-Key is required
       Authorization: process.env.ASPECTO_API_KEY
     }
   })
 )
);
registerInstrumentations({
 instrumentations: [
   // add other instrumentations here for packages your app uses
   new KafkaJsInstrumentation({})
 ],
});
Вход в полноэкранный режим Выйти из полноэкранного режима

Затем запустите приложение с ключом Aspecto api, как показано ниже:

ASPECTO_API_KEY=YOUR_API_KEY node --require './tracing.js' ./bin/www
Войти в полноэкранный режим Выйти из полноэкранного режима

Когда вы зайдёте на localhost:3000 с помощью браузера, он будет производить и потреблять сообщения Kafka и отправлять соответствующие диапазоны в aspecto. Пройдет минута или две, и вы сможете увидеть это в поиске трассировки в aspecto, как показано на рисунке выше.

Если вы хотите инструментировать библиотеки, отличные от Kafka, обновите файл трассировки следующим образом (используя библиотеку node auto instrumentations, которая по умолчанию включает различные инструменты):

const { NodeTracerProvider } = require('@opentelemetry/sdk-trace-node');
const { Resource } = require('@opentelemetry/resources');
const { SemanticResourceAttributes } = require('@opentelemetry/semantic-conventions');
const { SimpleSpanProcessor } = require('@opentelemetry/sdk-trace-base');
const { CollectorTraceExporter } = require('@opentelemetry/exporter-collector');
const { registerInstrumentations } = require('@opentelemetry/instrumentation');
const { KafkaJsInstrumentation } = require("opentelemetry-instrumentation-kafkajs");
const { getNodeAutoInstrumentations } = require("@opentelemetry/auto-instrumentations-node");
const provider = new NodeTracerProvider({
 resource: new Resource({
   [SemanticResourceAttributes.SERVICE_NAME]: 'kafka-service' // service name is required
 }),
});
provider.register();
provider.addSpanProcessor(
 new SimpleSpanProcessor(
   new CollectorTraceExporter({
     url: 'https://otelcol.aspecto.io/v1/trace',
     headers: {
       // Aspecto API-Key is required
       Authorization: process.env.ASPECTO_API_KEY
     }
   })
 )
);
registerInstrumentations({
 instrumentations: [
   getNodeAutoInstrumentations(),
   new KafkaJsInstrumentation({})
 ],
});
Войдите в полноэкранный режим Выйдите из полноэкранного режима

Но обратите внимание: для Node рекомендуется использовать Aspecto SDK, который использует OpenTelemetry под капотом, но также поддерживает сбор фактической полезной нагрузки.

Если вы возьмете точно такой же сервис с нуля — без всех установок OpenTelemetry (обязательно удалите их, чтобы избежать конфликтов версий), и запустите:

npm install @aspecto/opentelemetry
Войти в полноэкранный режим Выйти из полноэкранного режима

Затем добавьте следующий код в верхнюю часть вашего файла app.js:

require('@aspecto/opentelemetry')({
 aspectoAuth: process.env.ASPECTO_API_KEY
});
Войти в полноэкранный режим Выйти из полноэкранного режима

И теперь вы можете видеть даже полезную нагрузку сообщения Kafka:

P.S. Если вы предпочитаете использовать открытый исходный код для визуализации трассировки, вы можете попробовать Jaeger Tracing. Вы можете следовать этому руководству по развертыванию Jaeger на AWS и обязательно прокрутите страницу до части, посвященной отправке трасс в Jaeger с помощью OpenTelemetry SDK (в NodeJS). Имейте в виду, что на настройку необходимого окружения может потребоваться немного больше времени.

Если вы не знакомы с Jaeger и хотите получить более глубокое представление о нем, мы рекомендуем посетить это руководство.

Я надеюсь, что это было полезное руководство для вас, чтобы узнать, как использовать OpenTelemetry в Node для генерации трасс для операций Kafka. Не стесняйтесь обращаться, если у вас возникнут вопросы!

Устранение проблем с установкой OpenTelemetry Node

Нередко при попытке установить OpenTelemetry возникает несколько проблем. В частности, при попытке установить OpenTelemetry в ваше приложение Node вы не видите никаких следов или некоторые ожидаемые промежутки отсутствуют.

Чтобы помочь вам избежать этих распространенных ловушек, мы рекомендуем просмотреть этот подробный контрольный список проблем и решений. Мы рассмотрим наиболее распространенные ошибки и покажем вам, как их решить.

Дополнительные ресурсы OpenTelemetry

Если вы хотите углубиться в изучение OpenTelemetry, посетите видеотеку The OpenTelemetry Bootcamp. Это бесплатный и не зависящий от поставщика углубленный курс, который поможет вам освоить OpenTelemetry. Мы рассмотрим все, начиная с самых основ и заканчивая безопасностью и внедрением в производство.

Оцените статью
devanswers.ru
Добавить комментарий