OpenShift Content Pack
Red Hat OpenShift is a Kubernetes-based application platform that runs across on-premises, cloud, and hybrid environments. This technology pack processes OpenShift/Kubernetes container log messages delivered as JSON. The pack normalizes the JSON envelope and OpenShift/Kubernetes metadata into Graylog schema-compatible fields. This metadata includes container name/ID, namespace, pod, worker node, container image, and cluster ID. It also promotes the human-readable application message to the stored message field and normalizes the log level to a standard event severity. The pack leaves application-specific message bodies (e.g., Spring Boot, Kafka, or Django logs) intact for parsing in a future release, except for Uvicorn HTTP access log lines, which this pack parses now.
This pack focuses on application logs (container stdout/stderr), identified by log_source value container. It does not process OpenShift audit logs (kube-apiserver, openshift-apiserver, OVN, or node auditd) or node and infrastructure logs. These records carry no container metadata, so the pack skips them.
Supported Versions
-
OpenShift 4.0 and later container logs in the OpenShift Logging (ViaQ) JSON data model, as emitted by a Fluentd or Vector collector.
Important: You must configure the collector to forward the ViaQ JSON data model. The OpenTelemetry (OTEL) log data model introduced with OpenShift Logging 6.x (resource attributes, severityText, body) is not supported.
Requirements
-
A Red Hat OpenShift or Kubernetes cluster emitting container logs as JSON.
-
Graylog 7.1 or later.
-
A log collector (e.g. Fluentd or Vector) shipping container logs to Graylog.
Stream Configuration
This technology pack includes 1 stream:
- Illuminate:OpenShift Messages
Index Set Configuration
This technology pack includes 1 index set definition:
- OpenShift Logs
Log Collection
On each node, a log collector such as Fluentd or Vector gathers OpenShift container logs and ships them to Graylog as JSON, using the OpenShift Logging (ViaQ) data model. Graylog supports delivery over syslog.
OpenShift logs are identified by input rather than by payload. Either dedicate a Graylog input to OpenShift and map it to openshift in the core input_routing lookup table, or use a pipeline rule to set a static RoutedFrom field instead, as described in Input Routing Setup below. When the JSON arrives over syslog with a priority header, Graylog strips the header before parsing.
Each record includes:
-
cluster ID
-
metadata for the Kubernetes pod, namespace, container, and node
-
container stream (stdout or stderr)
-
log level
This information is included alongside the application log line.
Important: You must configure the collector to forward the ViaQ JSON data model. The OpenTelemetry (OTEL) log data model introduced with OpenShift Logging 6.x (resource attributes, severityText, body) is not supported.
Input Routing Setup
OpenShift logs are identified by the Graylog input they arrive on rather than by their payload. A dedicated input must be mapped to this pack in the core input_routing lookup table. Map the input ID to openshift so that every message on that input is processed as an OpenShift container log.
-
Create a dedicated Syslog input in Graylog for your OpenShift logs.
-
Select Show received messages to open a search window on the input.
-
Copy the
gl2_source_inputvalue from a received message. -
Navigate to Enterprise > Illuminate, then select the Customization tab.
-
Locate the lookup_adapter_input_routing title, then click Edit.
-
For content_name (key), enter openshift and for input_id (value), enter the
gl2_source_inputID copied earlier. -
Select Configure value.
All logs sent to the configured input are now identified as OpenShift container logs and processed by this pack. Repeat these steps for additional OpenShift inputs as needed.
Alternatively, use pipeline rules to set or create a static field RoutedFrom with the value Route - OpenShift Logs instead of using the input_routing lookup table.
Configure OpenShift Log Forwarding
This pack processes OpenShift/Kubernetes container logs delivered in the OpenShift Logging (ViaQ) JSON data model. These records have log_type set to application and log_source set to container, and carry the kubernetes metadata object and the openshift.cluster_id field.
Configure OpenShift Logging to forward these container (application) logs to the Graylog input you mapped under Input Routing Setup. This pack does not process audit logs (kube-apiserver, openshift-apiserver, OVN, node auditd) or node and infrastructure logs. These logs do not need to be forwarded.
Forward Container Logs from OpenShift Logging
Configure the OpenShift Logging collector to forward logs to Graylog. OpenShift Logging 6.x supports Vector as the only collector, while OpenShift Logging 5.x and earlier support Fluentd and Vector. Refer to Red Hat's OpenShift Logging documentation for the exact procedure for your OpenShift version.
-
Install the Red Hat OpenShift Logging Operator and deploy the collector.
-
Create a Graylog input for the OpenShift logs and map it to
openshiftas described in Input Routing Setup above. -
Create or edit a
ClusterLogForwardercustom resource.Important: Only the ViaQ JSON data model is supported. If the collector forwards the OpenTelemetry (OTEL) data model (resource attributes, severityText, body), the logs will not be parsed by this pack.
-
Define an input that selects the
applicationlog source, which is the container stream (stdoutorstderr) this pack processes. Do not forward theauditorinfrastructuresources. -
Define an output that points at your Graylog input, using a transport supported by that input.
-
Add a pipeline in the
ClusterLogForwarderthat connects theapplicationinput to the Graylog output, then apply the resource. -
Verify that container log records arrive on the Graylog input and that
event_source_productis set toopenshift.
Log Format Examples
Representative OpenShift container log line (JSON).
{"hostname":"ocp-worker-0.example.com","kubernetes":{"container_name":"sample-app","namespace_name":"sample-app-dev","pod_name":"sample-app-7c9f8b6d5c-abcde","container_id":"cri-o://1111111111111111111111111111111111111111111111111111111111111111","container_image":"registry.example.com/sample-app/sample-app:1.0.0","labels":{"app":"sample-app"},"pod_owner":"ReplicaSet/sample-app-7c9f8b6d5c"},"level":"info","container_iostream":"stdout","log_type":"application","log_source":"container","openshift":{"cluster_id":"11111111-1111-1111-1111-111111111111"},"message":"2025-04-15T19:09:17.723Z INFO 1 --- [sample] [ main] com.example.app.SampleApplication : Started SampleApplication in 7.318 seconds"} {"@timestamp":"2025-03-24T14:39:04.750290671Z","hostname":"ocp-worker-0.example.com","kubernetes":{"annotations":{"openshift.io/scc":"confluent-operator"},"container_id":"cri-o://2222222222222222222222222222222222222222222222222222222222222222","container_image":"registry.example.com/sample-web/sample-web-ui:1.0.0","container_image_id":"registry.example.com/sample-web/sample-web-ui@sha256:2222222222222222222222222222222222222222222222222222222222222222","container_iostream":"stdout","container_name":"ui","labels":{"app":"ui","pod-template-hash":"7f784668b8"},"namespace_id":"44444444-4444-4444-4444-444444444444","namespace_labels":{"kubernetes_io_metadata_name":"sample-web-test"},"namespace_name":"sample-web-test","pod_id":"33333333-3333-3333-3333-333333333333","pod_ip":"10.128.2.43","pod_name":"ui-7f784668b8-njz49","pod_owner":"ReplicaSet/ui-7f784668b8"},"level":"default","log_source":"container","log_type":"application","message":"## CONTACT INFORMATION","openshift":{"cluster_id":"11111111-1111-1111-1111-111111111111","sequence":1744821243330547883},"timestamp":"2025-03-24T14:39:04.750290671Z"} {"@timestamp":"2025-04-15T19:09:06.556825292Z","hostname":"ocp-worker-0.example.com","kubernetes":{"annotations":{"dynakube.dynatrace.com/injected":"true","metadata.dynatrace.com/k8s.workload.kind":"deployment","metadata.dynatrace.com/k8s.workload.name":"sample-docs","oneagent.dynatrace.com/injected":"true","openshift.io/scc":"confluent-operator"},"container_iostream":"stdout","container_name":"dynatrace-operator","labels":{"app":"sample-docs","pod-template-hash":"86dc8c7755"},"namespace_id":"55555555-5555-5555-5555-555555555555","namespace_labels":{"kubernetes_io_metadata_name":"sample-docs-dev"},"namespace_name":"sample-docs-dev","pod_id":"66666666-6666-6666-6666-666666666666","pod_ip":"10.128.9.157","pod_name":"sample-docs-86dc8c7755-xq4rw","pod_owner":"ReplicaSet/sample-docs-86dc8c7755"},"level":"info","log_source":"container","log_type":"application","openshift":{"cluster_id":"11111111-1111-1111-1111-111111111111","sequence":1744821243545406784},"structured":{"content":{"apiUrl":"https://dynatrace.example.com/e/11111111-1111-1111-1111-111111111111/api","skipCertCheck":true,"tenantUUID":"11111111-1111-1111-1111-111111111111"},"level":"info","logger":"injection-startup","msg":"contents of secret config","ts":"2025-04-15T19:09:06.556Z"},"timestamp":"2025-04-15T19:09:06.556825292Z"} {"hostname":"ocp-worker-0.example.com","kubernetes":{"container_id":"cri-o://5555555555555555555555555555555555555555555555555555555555555555","container_image":"registry.example.com/model/model:1.0.0","container_iostream":"stdout","container_name":"model","labels":{"app":"model","pod-template-hash":"597bfcd89b"},"namespace_name":"sample-app-dev","pod_id":"6e15e0ed-a04a-4869-920f-69792a0cb6dd","pod_ip":"10.242.15.16","pod_name":"model-597bfcd89b-8cwlh","pod_owner":"ReplicaSet/model-597bfcd89b"},"level":"info","log_source":"container","log_type":"application","openshift":{"cluster_id":"11111111-1111-1111-1111-111111111111"},"message":"INFO: 10.242.16.2:52266 - \"GET /%5C..%5C..%5C..%5C..%5Cwinnt%5Cwin.ini HTTP/1.1\" 404 Not Found"}
What Is Provided
-
Input-based identification of OpenShift/Kubernetes container JSON logs.
-
Normalization of container and OpenShift/Kubernetes metadata into the
container_*schema fields (name, id, namespace, image, iostream, pod name/uid/ip/owner, cluster id, app). -
Worker node mapping to
host_hostname. -
Promotion of the application message to the stored message field, including containers that use structured JSON logging with no top-level message.
-
Log level normalized to
event_severityandevent_severity_level. -
Parsing of Uvicorn HTTP access lines into
http_andsource_fields (source_ip,source_port,http_request_method,http_request_path,http_version,http_response_code).
