BetterstackLogger is the Logger component’s Better Stack backend. It wraps the official @logtail/node client to ship structured logs to Better Stack’s Logs (Logtail) platform, attaching your data object to every entry and flattening exception details onto the payload. It implements the framework’s ILogger interface, so call sites stay provider-agnostic and you can swap the backend without touching the code that emits logs.
What you get
Logs ship to Better Stack for search, dashboards, and alerting, so you don’t run your own pipeline. Pass adata object and it’s sent alongside the message as structured fields. error() accepts an IException and flattens its name, status, and stack trace onto the payload. You can point at a custom ingesting endpoint or fall back to the Logtail default. The client batches logs, and flush() drains the buffer before the process exits. Registration happens through @decorator.logger(), and the logger resolves from the container.
Installation
BetterstackLogger ships with @talosjs/logger and depends on the Logtail Node client.
Environment variables
BetterstackLogger is constructed, so a missing token fails fast at startup.
How it works
On construction, the backend creates a singleLogtail client with your source token (and endpoint, if set). Each level method forwards the message and data to the matching Logtail method, error, warn, info, or debug, while log and success map to info with a level field (LOG / SUCCESS) so the original level is preserved. When an IException is passed to error(), its name, status, and JSON stack trace are extracted and merged into the payload. Delivery is buffered, so call flush() to drain it.
Usage
error() accepts a plain message or an IException. Given an exception, it flattens the name, status, and stack trace onto the payload:
Use in the app
In an@talosjs/app application, register BetterstackLogger by adding it to the loggers array of your App config. The loggers slot of AppConfigType is typed as LoggerClassType[], so you pass the class itself and the framework registers it with the container at startup.
loggers accepts an array, so you can ship to Better Stack while also printing to the terminal in development:
BETTERSTACK_LOGGER_SOURCE_TOKEN (and optionally BETTERSTACK_LOGGER_INGESTING_HOST) in your .env.yml (or environment), then inject the logger into a service or controller:
Exceptions
BetterstackLogger throws LoggerException on misconfiguration, carrying a machine-readable key.
Working with it day to day
Drain the buffer withflush() before the process terminates, or the last logs never leave. Keep the message string stable and push variable detail into the data object; interpolated strings are harder to search later. When you catch an exception, pass the IException itself to error() so the name, status, and stack trace come through. The source token lives in .env, never in source. And if your source uses a region-specific endpoint, set BETTERSTACK_LOGGER_INGESTING_HOST to match it.
For error and exception tracking specifically, see Better Stack Exceptions. See the Logger component for the provider interface and how logs flow through the framework.