Last updated: July 28, 2025
Mastering the OpenTelemetry Attributes Processor
The OpenTelemetry Collector plays a central role in shaping and managing observability data across modern systems.
Among its many components, the attributes processor is one you’ll often reach out for when you need to enrich, redact, or standardize the data flowing through your pipelines.
While the official documentation provides a foundational understanding, this guide aims to go beyond the basics by offering a comprehensive and practical deep dive.
By the end of this article, you’ll be able to wield the attributes
processor with confidence to tailor your telemetry and drive clearer insights.
Let's get started!
What are OpenTelemetry attributes?
In OpenTelemetry, attributes are key-value pairs that describe specific characteristics of the events, operations, or entities being observed.
They add context to your telemetry data, making it searchable, filterable, and ultimately more actionable. For example, a span representing an HTTP request might include attributes like http.request.method
, http.route
, and http.response.status_code
.
In the OpenTelemetry model, you’ll encounter attributes in several places including Resources, Instrumentation Scopes, Metric Points, Spans, Span Events, Span Links, and Log Records.
In the OpenTelemetry debug exporter, attributes appear like this:
When to use the attributes processor
The attributes
processor is useful anytime you need to clean up, enrich, or standardize telemetry data in-flight. Common use cases include:
- Standardizing attribute keys across your services and teams.
- Injecting metadata from various sources.
- Removing or obfuscating personally identifiable information (PII) before it leaves your systems.
- Fixing misnamed or malformed attributes from sources you don’t control.
- Driving pipeline logic based on attribute values.
Note that the attributes
processor operates on span, log, and metric attributes alone (shown as Attributes
in the debug exporter). For attribute manipulation beyond this scope, other specialized processors in the OpenTelemetry Collector are available:
- resource processor: For modifying attributes at the resource level (
Resource attributes
). - metricstransform processor: For metric-specific transformations, including renaming metrics, deleting data points, or performing aggregations.
- transform processor: For general data shaping or complex schema transformations with the OpenTelemetry Transform Language (OTTL).
Quick Start: adding the attributes processor
To begin using the attributes
processor, define it in the processors
section of your Collector configuration, then reference it in the pipelines
where you want it applied:
otelcol.yaml12345678910111213141516171819202122processors:attributes:actions:# Your attribute modification actions will go here- key: some_attributevalue: some_valueaction: upsertservice:pipelines:traces:receivers: [otlp]processors: [attributes] # Apply to tracesexporters: [otlp]metrics:receivers: [otlp]processors: [attributes] # Apply to metricsexporters: [otlp]logs:receivers: [otlp]processors: [attributes] # Apply to logsexporters: [otlp]
You can apply different sets of attribute modifications to various pipelines or for distinct purposes, by defining multiple instances of the attributes processor, each with a unique name:
otelcol.yaml12345678910111213processors:attributes/my_enricher:actions:- key: some_attributevalue: some_valueaction: insertattributes/my_redactor:actions:- key: user.emailaction: hash- pattern: ".*password.*"action: delete
Understanding attribute processor actions
The attributes
processor supports a variety of actions for modifying telemetry data. These actions are executed in the order they appear in your configuration, allowing predictable control over how attributes are handled.
Adding and modifying attributes
The following actions are provided for managing attribute values:
insert
This adds an attribute only if it does not already exist:
otelcol.yaml123- key: new_attributevalue: "some_value"action: insert # Adds `new_attribute` only if it's missing
update
Modifies an attribute only if it already exists:
otelcol.yaml123- key: existing_attributevalue: "updated_value"action: update # Updates `existing_attribute` if it exists
upsert
Adds or updates an attribute (whichever is needed). This is often the most convenient and commonly used action:
otelcol.yaml123- key: some_attributevalue: some_valueaction: upsert # Ensures `some_attribute` is set to `some_value`
Populating attribute values
When using the insert
, update
, or upsert
actions, you have three ways to populate the attribute value:
value
This lets you provide a literal value whose type is inferred automatically:
otelcol.yaml1234567891011121314attributes:actions:- key: string_examplevalue: This is a string attributeaction: upsert- key: int_examplevalue: 12345action: upsert- key: bool_examplevalue: trueaction: upsert- key: double_examplevalue: 98.765action: upsert
from_attribute
This copies the new attribute value from an existing attribute in the same telemetry signal:
otelcol.yaml12345# Copy `http.method` to `http.request.method`actions:- key: http.request.methodfrom_attribute: http.methodaction: upsert
A common pattern is using from_attribute
to copy a value to a new attribute, and then deleting the original:
otelcol.yaml1234567# Copy `http.method` to `http.request.method`actions:- key: http.request.methodfrom_attribute: http.methodaction: upsert- key: http.methodaction: delete
If the source attribute (http.method
in this case) doesn’t exist, the action is skipped.
from_context
This extracts values from the OpenTelemetry Collector’s internal context, such as gRPC metadata, HTTP headers, client address, or authentication info. Here are the available patterns:
metadata.<key>
: To extract HTTP headers or gRPC metadata, you must use themetadata
prefix. You’ll need to enableinclude_metadata: true
on your OTLP receiver before you can access these attributes:
otelcol.yaml1234567891011121314receivers:otlp:protocols:grpc:include_metadata: true # Essential for 'from_context: metadata.*'http:include_metadata: true # Essential for 'from_context: metadata.*'processors:attributes/headers:actions:- key: user_agentfrom_context: metadata.user-agent # Extract User-Agent headeraction: upsert
auth.<key>
: Accesses authentication details provided by server authenticators. The specific keys depend on the authenticator used, so you’ll need to refer to its documentation.
otelcol.yaml123- key: auth.client_idfrom_context: auth.client.id # If an authenticator exposes client.idaction: upsert
client.address
: Captures the IP address of the client sending data to the Collector.
otelcol.yaml123- key: client_addressfrom_context: client.addressaction: upsert
Removing unwanted attributes
The delete
action removes attributes by name or pattern. Use key
for an exact match, or pattern
for regex-based deletion:
otelcol.yaml1234567# Delete a specific attribute- key: sensitive_dataaction: delete# Delete all attributes starting with "internal."- pattern: ^internal\..*action: delete
Redacting sensitive information
The hash
action replaces an attribute’s value with its SHA-256 hash. This allows you to redact sensitive information while preserving uniqueness for correlation or grouping.
As with delete
, you can provide a specific key
or a regular expression pattern
:
otelcol.yaml1234567# Hash a specific attribute- key: user.emailaction: hash# Hash any attribute containing "email" in its name- pattern: .*email.*action: hash
For a deeper dive, see our guide on scrubbing sensitive data from logs, traces, and metrics.
Parsing values with regular expressions
The extract
action lets you parse parts of an attribute’s value using a regular expression and populate the results into new attributes.
For example, consider an unstructured log like this:
1log.record.original: "User 'jane.doe@example.com' with session ID 'ABC123XYZ' failed to authenticate from IP: 203.0.113.42 due to invalid credentials. ErrorCode: 401"
You can extract the email, session ID, client IP address, and error code into discrete attributes using the following configuration:
otelcol.yaml12345attributes/add_various_types:actions:- key: log.record.originalpattern: "^User '(?P<user_email>[^']+)' with session ID '(?P<session_id>[^']+)' failed to authenticate from IP: (?P<client_ip>\\d{1,3}\\.\\d{1,3}\\.\\d{1,3}\\.\\d{1,3}) due to invalid credentials\\. ErrorCode: (?P<error_code>\\d+)"action: extract
The extract action requires both a key
and a regex patter
n that must use named capture groups. In this example:
(?P<user_email>[^']+)
captures the email address into a newuser_email
attribute.(?P<session_id>[^']+)
captures the session ID into a newsession_id
attribute.(?P<client_ip>\\d{1,3}\\.\\d{1,3}\\.\\d{1,3}\\.\\d{1,3})
captures the IPv4 address into a newclient_ip
attribute.(?P<error_code>\\d+)
captures the numeric error code into a newerror_code
attribute.
The extracted values are automatically added as attributes on the signal. If any of the target attributes already exist, they will be overwritten.
Changing attribute types
The convert action allows you to change the type of an attribute’s value to one of the supported types: int
, double
, or string
. This is useful when normalizing data to meet semantic conventions or backend requirements.
otelcol.yaml123- key: response_time_msaction: convertconverted_type: double # Converts a string '123.45' to a float
If the value cannot be converted (e.g., trying to convert “abc” to an int
), the original value remains unchanged.
Tailoring attribute modifications with filters
So far, we’ve focused on how to modify attributes. But in practice, you often don’t want these actions applied to every signal in your pipeline.
That’s where include
and exclude
filters come in. They let you precisely control which traces, metrics, or logs your attribute actions apply to.
How filtering works
If both include
and exclude
are specified, the include
rules are evaluated first, and exclude
is then applied to the result of the include
set.
You must also specify a match_type
which determines how values are matched. It can be set to either strict
for exact string comparisons, or regexp
for more flexible pattern matching using regular expressions.
Filtering by telemetry type
Within the include and exclude fields, the available filtering options depend on the telemetry signal.
For spans, you can filter by services
, span_names
, span_kinds
, attributes
, resources
, and libraries
:
otelcol.yaml123456processors:attributes/filter_spans:include:match_type: strictservices: [my-backend-service] # Only process spans from this servicespan_names: [/api/v1/users] # Only process this specific span name
For log records, the valid fields are log_bodies
, log_severity_texts
, log_severity_number
, attributes
, resources
, and libraries
:
otelcol.yaml12345678processors:attributes/filter_logs:exclude:match_type: regexplog_bodies: [.*healthcheck.*] # Exclude logs containing "healthcheck"log_severity_number:min: 21match_undefined: false # Do not match logs with undefined severity
Finally, for metrics, only metric_names
and resources
are supported for filtering:
otelcol.yaml12345678processors:attributes:include:match_type: regexpregexp:cacheenabled: truecachemaxnumentries: 1000 # Cache up to 1000 regex matchesspan_names: ["^/api/v\\d+/.*"]
Caching regular expression matches
When match_type
is regexp
, you can enable optional regex result caching to improve performance, especially in high-throughput environments or when patterns repeat frequently.
otelcol.yaml12345678processors:attributes:include:match_type: regexpregexp:cacheenabled: truecachemaxnumentries: 1000 # Cache up to 1000 regex matchesspan_names: ["^/api/v\\d+/.*"]
By setting cacheenabled: true
and optionally cachemaxnumentries
(to limit the cache size), the processor caches results of regex matches. This avoids redundant regex evaluations and helps reduce CPU usage while increasing throughput.
Attributes processor tips and best practices
- Action order matters: Actions are executed in the order they’re defined. For example, if you’re copying an attribute and then deleting the original, make sure the copy comes first.
- Test before deploying: Use the debug exporter to validate your configuration and confirm attribute changes behave as expected before rolling out to production.
- Watch for performance impact: While the attributes processor is generally efficient, complex regex patterns or a very large number of rules can introduce significant overhead. Be sure to keep tabs on your collector’s performance metrics accordingly.
- Avoid unintended metric identity changes: If you change attributes that define a metric’s identity, you could inadvertently create new metric streams or cause data loss if the backend expects a specific identity.
Final thoughts
The OpenTelemetry attributes processor is a powerful tool for shaping high-quality telemetry. With a solid grasp of its actions, filtering logic, and best practices, you can clean, enrich, and standardize your traces, metrics, and logs before they reach your observability backend.
Once your data is clean and your attributes are well defined, the next step is sending it to an OpenTelemetry-native platform like Dash0 to help you transform them into actionable insights.
Take control of your observability data and try Dash0 today by signing up for a free trial.
