Send data from Docker to Axiom
This page explains how to send logs and metrics from Docker containers to Axiom with Vector, the OpenTelemetry Collector, Fluent Bit, Fluentd, or Filebeat.
Docker captures everything your containers write to stdout and stderr and hands it to a logging driver. By default, the json-file driver stores this output on the host. To send container logs to Axiom, run a collector on the host that reads those logs, or point one of Docker’s built-in logging drivers at a forwarder that sends the logs to Axiom.
This page covers the methods that work with Axiom and explains when to use each. For containers that run on Kubernetes, see Send data from Kubernetes. For Amazon ECS and AWS Fargate, see Send data from AWS FireLens.
Prerequisites
- Create an Axiom account.
- Create a dataset in Axiom where you send your data.
- Create an API token in Axiom with permissions to ingest data to the dataset you have created.
- Docker Engine on a Linux host. Depending on the method, the collector needs access to the Docker socket (
/var/run/docker.sock) or to the container log directory (/var/lib/docker/containers).
Choose a method
| Method | How it collects logs | Container metadata |
|---|---|---|
| Vector | The docker_logs source reads container output through the Docker socket. | Container name and ID, image, labels, stream |
| OpenTelemetry Collector | The filelog receiver tails the json-file log files. The docker_stats receiver adds container metrics. | Container ID, stream, and the path of the log file |
| Fluent Bit | Docker’s fluentd logging driver pushes logs to the Fluent Bit forward input. | Container name and ID, stream |
| Fluentd | Docker’s fluentd logging driver pushes logs to the Fluentd forward input. | Container name and ID, stream |
| Filebeat | The filestream input with the container parser tails the json-file log files. | Container ID, name, image, and labels |
Vector, the OpenTelemetry Collector, and Filebeat work with Docker’s default logging configuration. The Fluent Bit and Fluentd methods change the logging driver of your containers. In that case, docker logs still works because Docker keeps a local cache of the latest logs, unless you set the cache-disabled option to true.
Send Docker logs with Vector
Vector’s docker_logs source collects the output of all containers through the Docker socket and adds the container name, ID, image, and labels to each event. The axiom sink sends the events to Axiom. This is the recommended method if you don’t already run another collector.
Run Vector on the host
-
Install Vector on the Docker host. The user that runs Vector must have access to the Docker socket, for example as a member of the
dockergroup. -
Create a configuration file
vector.tomlwith the following content:TOML -
Run Vector with the configuration file:
shell
The docker_time transform moves Vector’s timestamp field to _time. Without it, Axiom assigns the ingest time to each event and stores the Docker timestamp in the timestamp field.
To collect logs from a subset of containers, add include_containers, exclude_containers, include_images, or include_labels to the docker_logs source. Container names and IDs match by prefix. Exclusions take precedence over inclusions.
Run Vector as a container
To run Vector as a container on the same host, mount the Docker socket and the configuration file into the container.
-
Create a configuration file
vector.yamlwith the following content:YAML -
Start Vector:
shellAlternatively, add Vector to your Docker Compose file:
YAML
When Vector runs as a container, it automatically excludes its own logs.
Query Docker logs sent by Vector
Each event contains the log line in message, the output stream in stream, and the container metadata in container_name, container_id, image, container_created_at, and label. For example, to see the latest output of the api container:
Send Docker logs with the OpenTelemetry Collector
The filelog receiver of the OpenTelemetry Collector tails the json-file log files that Docker writes. The container operator parses the Docker log format, and the otlphttp exporter sends the logs to Axiom. The filelog receiver is part of the Contrib distribution of the Collector.
-
Create a configuration file
otel-collector.yamlwith the following content:YAML -
Start the Collector. The Collector needs read access to
/var/lib/docker/containers, which is only readable by root, so run the container as root:shellAlternatively, add the Collector to your Docker Compose file:
YAML
Each event contains the log line as the body, the output stream in log.iostream, the log file in log.file.path, and the container ID in container_id. When a log line is a JSON object, the json_parser operator turns its keys into fields. Docker keeps the trailing newline of each line, so the condition of the operator allows whitespace after the closing brace. Docker doesn’t record container names in the log files. To query by container name, use Vector or the fluentd logging driver instead.
Send container metrics with the OpenTelemetry Collector
The docker_stats receiver collects CPU, memory, network, and block I/O metrics for every running container through the Docker socket. Send these metrics to a dataset of type Metrics, separate from the dataset that holds your logs. The receiver runs on Linux only.
Add the receiver, an exporter for the metrics dataset, and a metrics pipeline to the Collector configuration:
Mount the Docker socket into the Collector container with -v /var/run/docker.sock:/var/run/docker.sock:ro.
Send Docker logs with Fluent Bit
Docker’s built-in fluentd logging driver sends container logs to a Fluentd-compatible forward input. Fluent Bit implements this protocol, so you can run Fluent Bit as a small forwarder and point the logging driver at it. Fluent Bit then sends the logs to Axiom with its http output. Each record contains the log line in log, the output stream in source, and the container metadata in container_id and container_name.
-
Create a configuration file
fluent-bit.confwith the following content:INIThe
JSON_Date_Keyoption writes the timestamp of each record to the_timefield, so Axiom uses the time that Docker recorded. -
Start Fluent Bit and publish port
24224on the host. The Docker daemon, not the container, connects to this port:shell -
Start your containers with the
fluentdlogging driver:shellThe
fluentd-asyncoption lets the container start even when Fluent Bit isn’t reachable yet. Docker buffers the logs until the connection is established.To use the driver for all new containers, set it as the default in
/etc/docker/daemon.jsonand restart Docker:JSONIn Docker Compose, run Fluent Bit as a service and configure the
loggingkey of each service that sends logs:YAML
If your containers write JSON log lines, add a parser filter between the input and the output to turn the keys of the log field into fields of the record:
Send Docker logs with Fluentd
If you already run Fluentd, point Docker’s fluentd logging driver at its forward input and send the logs to Axiom with the http output plugin. The records contain the same log, source, container_id, and container_name fields as with Fluent Bit.
-
Create a configuration file
fluent.confwith the following content:xmlThe
record_transformerfilter adds the event time as the_timefield. Thehttpoutput doesn’t include the event time in the record on its own. -
Start Fluentd and publish port
24224on the host:shell -
Start your containers with the
fluentdlogging driver, as described in Send Docker logs with Fluent Bit.
If your containers write JSON log lines, add a parser filter before the match section to turn the keys of the log field into fields of the record:
Send Docker logs with Filebeat
Filebeat’s filestream input tails the json-file log files, and the container parser extracts the log line and stream from the Docker log format. The add_docker_metadata processor looks up the container ID from the path of the log file and adds the container name, image, and labels to each event. Filebeat sends the events to Axiom’s Elasticsearch-compatible bulk API.
-
Install Filebeat OSS on the Docker host.
-
Create a configuration file
filebeat.ymlwith the following content:YAML -
Run Filebeat as root so it can read the container log files and the Docker socket.
Filebeat stores the log line in the message field, the output stream in stream, and the Docker log timestamp in @timestamp. Axiom’s Elasticsearch-compatible API uses @timestamp as the event time.