Перейти к содержимому

Node SDK настраивается целиком в коде, через init(). Вкладка Настройки → Скрипт загрузчика проекта формирует только браузерный бандл с CDN — ни один её переключатель к @buglapse/node не относится.

ts
import { init } from '@buglapse/node'
import { httpServerIntegration } from '@buglapse/node/integrations'

init({
    dsn: process.env.BUGLAPSE_DSN,
    environment: process.env.NODE_ENV,
    release: process.env.GIT_SHA,
    tracesSampleRate: 0.2,
    debug: process.env.BUGLAPSE_DEBUG === 'true',
    integrations: [httpServerIntegration()],
})

Все опции ​

  • dsn — DSN проекта, https://{key}@{host}, из Настройки → Общие. Обязателен, если не передан свой transport. Отсутствующий или некорректный DSN не бросает исключение: SDK один раз пишет предупреждение [Buglapse] Missing or invalid "dsn" и отбрасывает события.
  • environment — записывается как contexts.environment в каждое событие (production, staging, ...). По нему работают фильтр environment: в поиске панели и условия на окружение в выражении фильтра.
  • release — записывается как contexts.release в каждое событие. Хорошо подходит git SHA или тег версии; с ним же сопоставляются source maps, если вы собираете или минифицируете серверный код.
  • debug — пишет в консоль, что делает SDK ([Buglapse] ...): регистрацию интеграций, пойманные и отброшенные события, отправленные и неудачные пачки. В продакшене не включайте.
  • integrations — интеграции для регистрации, сливаются со встроенными по name (см. ниже).
  • tracesSampleRate — вероятность (0–1), что трейс будет отправлен. По умолчанию 1. Решается один раз на трейс, так что трейс приходит со всеми спанами или не приходит вовсе. См. Трейсинг → Сэмплирование.
  • transport — фабрика транспорта, которая заменяет пакетный fetch-транспорт по умолчанию, например makeConsoleTransport для локальной разработки. См. Транспорты.
  • transportOptions — настройка транспорта по умолчанию: timeout, retries, maxBatchSize, flushInterval, immediateTypes, onError. См. Транспорты.
  • tracePropagationTargets — какие исходящие запросы получают заголовки трейса (traceparent, tracestate) от httpTracingIntegration: строки (подстрока адреса) или RegExp. По умолчанию — все запросы; задайте, чтобы сузить. См. Распределённый трейсинг.
  • propagateSentryTrace — отправлять тем же адресатам ещё и заголовки Sentry sentry-trace и baggage, для сервиса на Sentry SDK, который отправляет в Buglapse. По умолчанию false.
  • sendDefaultPii — можно ли встроенным интеграциям SDK записывать персональные данные, которые они собирают автоматически. По умолчанию false: в адресах, которые SDK записывает сам, сохраняются путь и имена параметров, но каждое значение параметра query/fragment становится [Filtered] (/search?q=[Filtered]&page=[Filtered]) — в крошках и логах ошибок исходящих запросов, http.url у спанов и request.url/request.referrer входящего запроса. true записывает всё как есть. То, что передаёт ваш код (setUser(), сообщения, атрибуты), не меняется никогда — см. Чувствительные данные.
  • beforeSend(event, hint) — последний взгляд на каждое событие, после всех интеграций и препроцессоров: верните событие (изменённое или нет), чтобы отправить, или null, чтобы отбросить. hint.originalException — Error, переданный в captureException(). Если функция бросит исключение, событие отбрасывается.
  • beforeBreadcrumb(breadcrumb) — вызывается для каждой хлебной крошки, автоматической или из addBreadcrumb(), до того как она попадёт в след: верните её, чтобы оставить, или null, чтобы отбросить. Если функция бросит исключение, крошка отбрасывается.
  • storage — где хранятся область запроса, активный спан и хлебные крошки. init() использует AsyncLocalStorageContext на основе AsyncLocalStorage, который разделяет параллельные запросы; менять его обычно незачем (см. Теги и контекст).
  • resolveTraceId — даёт id трейса для нового корневого спана. По умолчанию каждый корневой спан начинает свой трейс — один на входящий запрос с HttpServerIntegration. Переопределяйте, только чтобы самим сгруппировать несколько корневых операций в один трейс.

Интеграции ​

UncaughtExceptionIntegration и ContextLinesIntegration включены по умолчанию. Всё остальное подключается и импортируется из @buglapse/node/integrations:

ИнтеграцияЧто делает
httpServerIntegrationСвоя область, хлебные крошки и спан http.server на каждый входящий запрос
httpTracingIntegrationИсходящие запросы — спанами http.client
httpErrorsIntegrationНеудачные исходящие запросы — логами ошибок
breadcrumbsIntegrationВызовы консоли и исходящие запросы — хлебными крошками
nodeContextIntegrationВерсия Node, ОС и имя хоста в каждом событии
eventLoopBlockIntegrationЛог-предупреждение, когда event loop останавливается
consoleIntegrationВызовы console.* — событиями логов
dedupeIntegrationОтбрасывает исключение, идентичное предыдущему
inboundFiltersIntegrationОтбрасывает исключения по сообщению

Управлять ими можно тремя способами:

ts
import { disable, init, use } from '@buglapse/node'
import { consoleIntegration, nodeContextIntegration } from '@buglapse/node/integrations'

// 1. Заранее, в init() — сливается со встроенными; элемент с именем встроенной заменяет её.
init({ dsn: process.env.BUGLAPSE_DSN, integrations: [nodeContextIntegration()] })

// 2. Позже, через use() — работает и до init(): вызов встаёт в очередь до него.
use(consoleIntegration())

// 3. Выключить по имени — до init() не даёт встроенной зарегистрироваться вовсе.
disable('uncaught-exception')

use() никогда не заменяет интеграцию, уже зарегистрированную под тем же именем, — сначала вызовите disable(name). Как написать свою — на странице Своя интеграция.

Вызовы до init() ​

Каждый вызов до init() — captureException(), log.*(), setTag(), use(), ... — встаёт в очередь и применяется, когда появится клиент, так что модули, импортированные раньше вашего init(), всё равно могут сообщать. Исключения — span(), asyncSpan(), startInactiveSpan() и withScope(): они оборачивают код, который должен выполниться сейчас, поэтому до init() просто выполняют его без трейсинга.

Вызывайте init() один раз. Второй вызов заменяет клиент, и всё, что первый ещё держал в буфере, теряется.

Несколько клиентов ​

Плоский API работает с одним общим клиентом. Если один процесс должен отправлять в несколько проектов (например, многоарендный воркер), создайте дополнительные клиенты через createClient():

ts
import { AsyncLocalStorageContext, createClient } from '@buglapse/node'
import { nodeContextIntegration } from '@buglapse/node/integrations'

const billing = createClient({
    dsn: process.env.BUGLAPSE_BILLING_DSN,
    storage: new AsyncLocalStorageContext(),
    integrations: [nodeContextIntegration()],
})

billing.captureException(error)
await billing.flush()

Клиент, созданный так, не получает встроенных интеграций: передайте storage: new AsyncLocalStorageContext() сами (иначе параллельные операции разделят одну область) и перечислите все нужные интеграции. Не давайте второму клиенту httpServerIntegration или uncaughtExceptionIntegration, если они есть у общего, — оба подключились бы к одним и тем же событиям процесса.