This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to calculate total cost, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
Despite the name 'cost.cache_creation.input_tokens', this value is cost in USD, not a token count. For token counts, use gen_ai.usage.cache_creation.input_tokens.
This is a subset of gen_ai.cost.input_tokens, not an independent cost. Do not sum this with gen_ai.cost.input_tokens — it is already included.
{
"key": "gen_ai.cost.cache_creation.input_tokens",
"brief": "The cost of input tokens written to cache in USD.",
"type": "double",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": false,
"visibility": "public",
"example": 12.34,
"additional_context": [
"This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to calculate total cost, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.",
"Despite the name 'cost.cache_creation.input_tokens', this value is cost in USD, not a token count. For token counts, use gen_ai.usage.cache_creation.input_tokens.",
"This is a subset of gen_ai.cost.input_tokens, not an independent cost. Do not sum this with gen_ai.cost.input_tokens — it is already included."
],
"changelog": [
{
"version": "0.16.0",
"prs": [],
"description": "Added gen_ai.cost.cache_creation.input_tokens attribute"
}
]
}
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to calculate total cost, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
Despite the name 'cost.cache_read.input_tokens', this value is cost in USD, not a token count. For token counts, use gen_ai.usage.cache_read.input_tokens.
This is a subset of gen_ai.cost.input_tokens, not an independent cost. Do not sum this with gen_ai.cost.input_tokens — it is already included.
{
"key": "gen_ai.cost.cache_read.input_tokens",
"brief": "The cost of cached input tokens in USD.",
"type": "double",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": false,
"visibility": "public",
"example": 12.34,
"additional_context": [
"This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to calculate total cost, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.",
"Despite the name 'cost.cache_read.input_tokens', this value is cost in USD, not a token count. For token counts, use gen_ai.usage.cache_read.input_tokens.",
"This is a subset of gen_ai.cost.input_tokens, not an independent cost. Do not sum this with gen_ai.cost.input_tokens — it is already included."
],
"changelog": [
{
"version": "0.16.0",
"prs": [],
"description": "Added gen_ai.cost.cache_read.input_tokens attribute"
}
]
}
The total cost of all input tokens in USD (includes cached and cache creation tokens).
Example123.45
Additional Context
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to calculate total cost, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
Despite the name 'cost.input_tokens', this value is cost in USD, not a token count. For token counts, use gen_ai.usage.input_tokens.
This is the total cost of all input tokens, including cached and cache creation tokens at their respective rates. For the cached portion, see gen_ai.cost.cache_read.input_tokens. For the cache creation portion, see gen_ai.cost.cache_creation.input_tokens.
{
"key": "gen_ai.cost.input_tokens",
"brief": "The total cost of all input tokens in USD (includes cached and cache creation tokens).",
"type": "double",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": false,
"visibility": "public",
"example": 123.45,
"additional_context": [
"This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to calculate total cost, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.",
"Despite the name 'cost.input_tokens', this value is cost in USD, not a token count. For token counts, use gen_ai.usage.input_tokens.",
"This is the total cost of all input tokens, including cached and cache creation tokens at their respective rates. For the cached portion, see gen_ai.cost.cache_read.input_tokens. For the cache creation portion, see gen_ai.cost.cache_creation.input_tokens."
],
"changelog": [
{
"version": "0.9.0",
"prs": [
397
],
"description": "Add additional_context"
},
{
"version": "0.4.0",
"prs": [
228
]
},
{
"version": "0.1.0",
"prs": [
112
]
}
]
}
The total cost of all output tokens in USD (includes reasoning tokens).
Example123.45
Additional Context
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to calculate total cost, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
Despite the name 'cost.output_tokens', this value is cost in USD, not a token count. For token counts, use gen_ai.usage.output_tokens.
This is the total cost of all output tokens, including reasoning tokens at their respective rate. For the reasoning portion, see gen_ai.cost.reasoning.output_tokens.
{
"key": "gen_ai.cost.output_tokens",
"brief": "The total cost of all output tokens in USD (includes reasoning tokens).",
"type": "double",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": false,
"visibility": "public",
"example": 123.45,
"additional_context": [
"This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to calculate total cost, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.",
"Despite the name 'cost.output_tokens', this value is cost in USD, not a token count. For token counts, use gen_ai.usage.output_tokens.",
"This is the total cost of all output tokens, including reasoning tokens at their respective rate. For the reasoning portion, see gen_ai.cost.reasoning.output_tokens."
],
"changelog": [
{
"version": "0.9.0",
"prs": [
397
],
"description": "Add additional_context"
},
{
"version": "0.4.0",
"prs": [
228
]
},
{
"version": "0.1.0",
"prs": [
112
]
}
]
}
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to calculate total cost, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
Despite the name 'cost.reasoning.output_tokens', this value is cost in USD, not a token count. For token counts, use gen_ai.usage.reasoning.output_tokens.
This is a subset of gen_ai.cost.output_tokens, not an independent cost. Do not sum this with gen_ai.cost.output_tokens — it is already included.
{
"key": "gen_ai.cost.reasoning.output_tokens",
"brief": "The cost of reasoning output tokens in USD.",
"type": "double",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": false,
"visibility": "public",
"example": 12.34,
"additional_context": [
"This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to calculate total cost, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.",
"Despite the name 'cost.reasoning.output_tokens', this value is cost in USD, not a token count. For token counts, use gen_ai.usage.reasoning.output_tokens.",
"This is a subset of gen_ai.cost.output_tokens, not an independent cost. Do not sum this with gen_ai.cost.output_tokens — it is already included."
],
"changelog": [
{
"version": "0.16.0",
"prs": [],
"description": "Added gen_ai.cost.reasoning.output_tokens attribute"
}
]
}
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to calculate total cost, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
Despite the name 'cost.total_tokens', this value is cost in USD, not a token count. For token counts, use gen_ai.usage.total_tokens.
{
"key": "gen_ai.function_id",
"brief": "Framework-specific tracing label for the execution of a function or other unit of execution in a generative AI system.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": false,
"visibility": "public",
"example": "my-awesome-function",
"changelog": [
{
"version": "0.5.0",
"prs": [
308
],
"description": "Added gen_ai.function_id attribute"
}
]
}
The messages passed to the model. It has to be a stringified version of an array of objects. The role attribute of each object must be "user", "assistant", "tool", or "system". For messages of the role "tool", the content can be a string or an arbitrary object with information about the tool call. For other messages the content can be either a string or a list of objects in the format {type: "text", text:"..."}. The first example shows this shape. Some operations use a different shape. See the additional context.
Examples[{"role": "user", "parts": [{"type": "text", "content": "Weather in Paris?"}]}, {"role": "assistant", "parts": [{"type": "tool_call", "id": "call_VSPygqKTWdrhaFErNvMV18Yl", "name": "get_weather", "arguments": {"location": "Paris"}}]}, {"role": "tool", "parts": [{"type": "tool_call_response", "id": "call_VSPygqKTWdrhaFErNvMV18Yl", "result": "rainy, 57°F"}]}][{"state": "I cannot log in, and I also want a refund for last month.", "questions": {"authIssue": {"type": "noul", "instructions": "Is there a login problem?"}, "department": {"type": "choice", "instructions": "Which team should handle this?", "criteria": {"billing": "Charges and refunds", "technical": "Bugs and outages"}}}}][{"state": "Invoice INV-2291 from Northwind Supply, issued 2026-09-02, net 30. 4 pallets at $250.00 each, shipping $80.00. Contact: Dana Ruiz, Priya Shah.", "fields": {"invoice_number": {"type": "text"}, "due_date": {"type": "date", "instructions": "Issue date plus the net payment days"}, "total": {"type": "number", "decimals": 2, "unit": "USD", "instructions": "Amount due including shipping"}, "contacts": {"type": "list", "items": "text"}, "po_number": {"type": "text", "instructions": "Purchase order number"}, "days_to_pay": {"type": "estimate", "min": 0, "max": 120, "step": 1, "instructions": "Days after issue until this invoice is paid"}}}]
For gen_ai.decide operations, the array holds one object {state: ..., questions: {...}}. state is the evaluated state. questions holds the questions keyed by name, as the caller passed them. Replace binary data in state, including data: URLs, with the string "[Blob substitute]". The second example shows this shape.
For gen_ai.extract operations, the array holds one object {state?: string, fields: {<name>: <field spec>}, images?: string[], reference_date?: string, options?: {...}}. This object is the request body as the caller passed it, without model. Do not change the values, and leave out the keys that the caller did not set. Do not record the image data. Replace each image with the string "[Blob substitute]". state is the text that the model reads. fields holds the field specs keyed by field name. Set the model in gen_ai.request.model. The third example shows this shape.
Changelog
v0.28.0#728Describe the extraction message shape for gen_ai.extract and move operation-specific shapes to additional context
v0.26.0#650Describe the evaluation message shape for gen_ai.evaluate
{
"key": "gen_ai.input.messages",
"brief": "The messages passed to the model. It has to be a stringified version of an array of objects. The `role` attribute of each object must be `\"user\"`, `\"assistant\"`, `\"tool\"`, or `\"system\"`. For messages of the role `\"tool\"`, the `content` can be a string or an arbitrary object with information about the tool call. For other messages the `content` can be either a string or a list of objects in the format `{type: \"text\", text:\"...\"}`. The first example shows this shape. Some operations use a different shape. See the additional context.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"examples": [
"[{\"role\": \"user\", \"parts\": [{\"type\": \"text\", \"content\": \"Weather in Paris?\"}]}, {\"role\": \"assistant\", \"parts\": [{\"type\": \"tool_call\", \"id\": \"call_VSPygqKTWdrhaFErNvMV18Yl\", \"name\": \"get_weather\", \"arguments\": {\"location\": \"Paris\"}}]}, {\"role\": \"tool\", \"parts\": [{\"type\": \"tool_call_response\", \"id\": \"call_VSPygqKTWdrhaFErNvMV18Yl\", \"result\": \"rainy, 57°F\"}]}]",
"[{\"state\": \"I cannot log in, and I also want a refund for last month.\", \"questions\": {\"authIssue\": {\"type\": \"noul\", \"instructions\": \"Is there a login problem?\"}, \"department\": {\"type\": \"choice\", \"instructions\": \"Which team should handle this?\", \"criteria\": {\"billing\": \"Charges and refunds\", \"technical\": \"Bugs and outages\"}}}}]",
"[{\"state\": \"Invoice INV-2291 from Northwind Supply, issued 2026-09-02, net 30. 4 pallets at $250.00 each, shipping $80.00. Contact: Dana Ruiz, Priya Shah.\", \"fields\": {\"invoice_number\": {\"type\": \"text\"}, \"due_date\": {\"type\": \"date\", \"instructions\": \"Issue date plus the net payment days\"}, \"total\": {\"type\": \"number\", \"decimals\": 2, \"unit\": \"USD\", \"instructions\": \"Amount due including shipping\"}, \"contacts\": {\"type\": \"list\", \"items\": \"text\"}, \"po_number\": {\"type\": \"text\", \"instructions\": \"Purchase order number\"}, \"days_to_pay\": {\"type\": \"estimate\", \"min\": 0, \"max\": 120, \"step\": 1, \"instructions\": \"Days after issue until this invoice is paid\"}}}]"
],
"alias": [
"ai.texts",
"ai.prompt.messages",
"gen_ai.prompt",
"ai.prompt"
],
"additional_context": [
"For `gen_ai.decide` operations, the array holds one object `{state: ..., questions: {...}}`. `state` is the evaluated state. `questions` holds the questions keyed by name, as the caller passed them. Replace binary data in `state`, including `data:` URLs, with the string `\"[Blob substitute]\"`. The second example shows this shape.",
"For `gen_ai.extract` operations, the array holds one object `{state?: string, fields: {<name>: <field spec>}, images?: string[], reference_date?: string, options?: {...}}`. This object is the request body as the caller passed it, without `model`. Do not change the values, and leave out the keys that the caller did not set. Do not record the image data. Replace each image with the string `\"[Blob substitute]\"`. `state` is the text that the model reads. `fields` holds the field specs keyed by field name. Set the model in `gen_ai.request.model`. The third example shows this shape."
],
"changelog": [
{
"version": "0.28.0",
"prs": [
728
],
"description": "Describe the extraction message shape for gen_ai.extract and move operation-specific shapes to additional context"
},
{
"version": "0.26.0",
"prs": [
650
],
"description": "Describe the evaluation message shape for gen_ai.evaluate"
},
{
"version": "0.21.0",
"prs": [
583
],
"description": "Added ai.prompt as an alias"
},
{
"version": "0.5.0",
"prs": [
264
]
},
{
"version": "0.4.0",
"prs": [
221
]
}
]
}
The search query used to retrieve memories. Only applicable to 'search_memory'. Opt-in: instrumentations SHOULD NOT capture this by default and SHOULD gate it behind explicit user opt-in, as it may contain sensitive information.
{
"key": "gen_ai.memory.query.text",
"brief": "The search query used to retrieve memories. Only applicable to 'search_memory'. Opt-in: instrumentations SHOULD NOT capture this by default and SHOULD gate it behind explicit user opt-in, as it may contain sensitive information.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"examples": [
"user dietary preferences",
"past flight bookings"
],
"changelog": [
{
"version": "0.27.0",
"prs": [
653
],
"description": "Added gen_ai.memory.query.text attribute"
}
]
}
The number of memory records relevant to the operation. For 'search_memory' this is the number returned; for 'create_memory', 'update_memory', 'upsert_memory' and 'delete_memory' it is the number the operation attempted to create, modify, create-or-update, or delete respectively.
{
"key": "gen_ai.memory.record.count",
"brief": "The number of memory records relevant to the operation. For 'search_memory' this is the number returned; for 'create_memory', 'update_memory', 'upsert_memory' and 'delete_memory' it is the number the operation attempted to create, modify, create-or-update, or delete respectively.",
"type": "integer",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"examples": [
3
],
"changelog": [
{
"version": "0.27.0",
"prs": [
653
],
"description": "Added gen_ai.memory.record.count attribute"
}
]
}
The unique identifier of the memory record. Set when the operation applies to a specific memory record. For 'delete_memory', its absence may indicate the operation intends to delete all memory records in the store.
{
"key": "gen_ai.memory.record.id",
"brief": "The unique identifier of the memory record. Set when the operation applies to a specific memory record. For 'delete_memory', its absence may indicate the operation intends to delete all memory records in the store.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"examples": [
"mem_5j66UpCpwteGg4YSxUnt7lPY"
],
"changelog": [
{
"version": "0.27.0",
"prs": [
653
],
"description": "Added gen_ai.memory.record.id attribute"
}
]
}
The memory records stored or retrieved in a memory operation. Stringified JSON array; each element follows the OTel MemoryRecord schema: {content (required), id, metadata, score}. Opt-in: instrumentations SHOULD NOT capture this by default and SHOULD gate it behind explicit user opt-in, as it may contain sensitive information including user/PII data.
{
"key": "gen_ai.memory.records",
"brief": "The memory records stored or retrieved in a memory operation. Stringified JSON array; each element follows the OTel MemoryRecord schema: {content (required), id, metadata, score}. Opt-in: instrumentations SHOULD NOT capture this by default and SHOULD gate it behind explicit user opt-in, as it may contain sensitive information including user/PII data.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"examples": [
"[{\"content\": \"User prefers dark mode\", \"id\": \"mem_123\", \"score\": 0.95}, {\"content\": {\"preference\": \"vegetarian meals\", \"confidence\": 0.9}, \"metadata\": {\"source\": \"profile\"}}]"
],
"changelog": [
{
"version": "0.27.0",
"prs": [
653
],
"description": "Added gen_ai.memory.records attribute"
}
]
}
The unique identifier of the memory store the operation targets. What this maps to is implementation-specific (e.g. a collection, namespace, or vector index) and SHOULD be documented per integration.
{
"key": "gen_ai.memory.store.id",
"brief": "The unique identifier of the memory store the operation targets. What this maps to is implementation-specific (e.g. a collection, namespace, or vector index) and SHOULD be documented per integration.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"examples": [
"ms_abc123",
"user-preferences-store",
"seer-knowledge"
],
"changelog": [
{
"version": "0.27.0",
"prs": [
653
],
"description": "Added gen_ai.memory.store.id attribute"
}
]
}
The model's response messages. It has to be a stringified version of an array of message objects, which can include text responses and tool calls. The first example shows this shape. Some operations use a different shape. See the additional context.
For gen_ai.decide operations, the array holds one object {answers: {...}}. answers holds the answers keyed by question name, as the provider returned them. The second example shows this shape.
For gen_ai.extract operations, the array holds one object {answers: {<name>: <answer>}, truncated: boolean, state_text?: string}. This object is the response body as the provider returned it, without model and usage. Do not change the values. answers holds one answer for each field in the input, keyed by field name. A field that the model cannot determine has a value of null. span and spans are [start, end] character offsets into state (or into state_text, if the provider returns it), and end is exclusive. Set the model in gen_ai.response.model and the token counts in gen_ai.usage.input_tokens and gen_ai.usage.output_tokens. The third example shows this shape.
Changelog
v0.28.0#728Describe the extraction message shape for gen_ai.extract and move operation-specific shapes to additional context
v0.26.0#650Describe the evaluation message shape for gen_ai.evaluate
{
"key": "gen_ai.output.messages",
"brief": "The model's response messages. It has to be a stringified version of an array of message objects, which can include text responses and tool calls. The first example shows this shape. Some operations use a different shape. See the additional context.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"examples": [
"[{\"role\": \"assistant\", \"parts\": [{\"type\": \"text\", \"content\": \"The weather in Paris is currently rainy with a temperature of 57°F.\"}], \"finish_reason\": \"stop\"}]",
"[{\"answers\": {\"authIssue\": {\"type\": \"noul\", \"noul\": 0.98}, \"department\": {\"type\": \"choice\", \"choice\": \"billing\", \"confidence\": 0.28, \"probabilities\": {\"billing\": 0.64, \"technical\": 0.36}}}}]",
"[{\"answers\": {\"invoice_number\": {\"type\": \"text\", \"p_null\": 3.8e-10, \"span\": [8, 16], \"guess\": \"INV-2291\", \"confidence\": 1, \"value\": \"INV-2291\"}, \"due_date\": {\"type\": \"date\", \"p_null\": 1.9e-08, \"guess\": \"2026-10-02\", \"confidence\": 0.9999, \"value\": \"2026-10-02\"}, \"total\": {\"type\": \"number\", \"p_null\": 2.3e-08, \"guess\": 1080, \"confidence\": 0.9999, \"value\": 1080}, \"contacts\": {\"type\": \"list\", \"value\": [\"Dana Ruiz\", \"Priya Shah\"], \"spans\": [[120, 129], [131, 141]], \"confidence\": 0.9999}, \"po_number\": {\"type\": \"text\", \"p_null\": 1, \"span\": [8, 16], \"guess\": \"INV-2291\", \"confidence\": 0.9995, \"value\": null}, \"days_to_pay\": {\"type\": \"estimate\", \"value\": 30, \"mean\": 29.535, \"median\": 30, \"p10\": 21, \"p90\": 38, \"p_below\": 5.9e-06, \"p_above\": 1.2e-05}}, \"truncated\": false}]"
],
"alias": [
"ai.response.toolCalls",
"ai.response.text"
],
"additional_context": [
"For `gen_ai.decide` operations, the array holds one object `{answers: {...}}`. `answers` holds the answers keyed by question name, as the provider returned them. The second example shows this shape.",
"For `gen_ai.extract` operations, the array holds one object `{answers: {<name>: <answer>}, truncated: boolean, state_text?: string}`. This object is the response body as the provider returned it, without `model` and `usage`. Do not change the values. `answers` holds one answer for each field in the input, keyed by field name. A field that the model cannot determine has a `value` of `null`. `span` and `spans` are `[start, end]` character offsets into `state` (or into `state_text`, if the provider returns it), and `end` is exclusive. Set the model in `gen_ai.response.model` and the token counts in `gen_ai.usage.input_tokens` and `gen_ai.usage.output_tokens`. The third example shows this shape."
],
"changelog": [
{
"version": "0.28.0",
"prs": [
728
],
"description": "Describe the extraction message shape for gen_ai.extract and move operation-specific shapes to additional context"
},
{
"version": "0.26.0",
"prs": [
650
],
"description": "Describe the evaluation message shape for gen_ai.evaluate"
},
{
"version": "0.4.0",
"prs": [
221
]
}
]
}
Dynamic SuffixYes - the key contains dynamic parts
Additional Context
Capture only when the user explicitly opts in to recording prompt inputs. In MCP, these values are the arguments supplied in prompts/get requests.
Changelog
v0.27.0#671Added the OpenTelemetry convention for prompt variables
Raw JSON
{
"key": "gen_ai.prompt.variable.<key>",
"brief": "Variables supplied to the prompt template. The <key> is the variable name, and the value is the variable value serialized as a string.",
"has_dynamic_suffix": true,
"type": "string",
"apply_scrubbing": {
"key": "auto",
"reason": "Prompt variables contain user input and may include sensitive information"
},
"is_in_otel": true,
"visibility": "public",
"examples": [
"gen_ai.prompt.variable.language='French'",
"gen_ai.prompt.variable.topic='weather'"
],
"additional_context": [
"Capture only when the user explicitly opts in to recording prompt inputs. In MCP, these values are the arguments supplied in prompts/get requests."
],
"changelog": [
{
"version": "0.27.0",
"prs": [
671
],
"description": "Added the OpenTelemetry convention for prompt variables"
}
]
}
Used to reduce repetitiveness of generated tokens. The higher the value, the stronger a penalty is applied to previously present tokens, proportional to how many times they have already appeared in the prompt or prior generation.
{
"key": "gen_ai.request.frequency_penalty",
"brief": "Used to reduce repetitiveness of generated tokens. The higher the value, the stronger a penalty is applied to previously present tokens, proportional to how many times they have already appeared in the prompt or prior generation.",
"type": "double",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"example": 0.5,
"alias": [
"ai.frequency_penalty"
],
"changelog": [
{
"version": "0.4.0",
"prs": [
228
]
},
{
"version": "0.1.0",
"prs": [
57
]
}
]
}
Used to reduce repetitiveness of generated tokens. Similar to frequency_penalty, except that this penalty is applied equally to all tokens that have already appeared, regardless of their exact frequencies.
{
"key": "gen_ai.request.seed",
"brief": "The seed, ideally models given the same seed and same other parameters will produce the exact same output.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"example": "1234567890",
"alias": [
"ai.seed"
],
"changelog": [
{
"version": "0.1.0",
"prs": [
57,
127
]
}
]
}
Limits the model to only consider the K most likely next tokens, where K is an integer (e.g., top_k=20 means only the 20 highest probability tokens are considered).
{
"key": "gen_ai.request.top_k",
"brief": "Limits the model to only consider the K most likely next tokens, where K is an integer (e.g., top_k=20 means only the 20 highest probability tokens are considered).",
"type": "integer",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"example": 35,
"alias": [
"ai.top_k"
],
"changelog": [
{
"version": "0.4.0",
"prs": [
228
]
},
{
"version": "0.1.0",
"prs": [
57
]
}
]
}
Limits the model to only consider tokens whose cumulative probability mass adds up to p, where p is a float between 0 and 1 (e.g., top_p=0.7 means only tokens that sum up to 70% of the probability mass are considered).
{
"key": "gen_ai.request.top_p",
"brief": "Limits the model to only consider tokens whose cumulative probability mass adds up to p, where p is a float between 0 and 1 (e.g., top_p=0.7 means only tokens that sum up to 70% of the probability mass are considered).",
"type": "double",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"example": 0.7,
"alias": [
"ai.top_p"
],
"changelog": [
{
"version": "0.4.0",
"prs": [
228
]
},
{
"version": "0.1.0",
"prs": [
57
]
}
]
}
{
"key": "gen_ai.tool.call.arguments",
"brief": "The arguments of the tool call. It has to be a stringified version of the arguments to the tool.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"example": "{\"location\": \"Paris\"}",
"alias": [
"gen_ai.tool.input",
"ai.toolCall.args"
],
"changelog": [
{
"version": "0.5.0",
"prs": [
265
]
},
{
"version": "0.4.0",
"prs": [
221
]
}
]
}
{
"key": "gen_ai.tool.call.result",
"brief": "The result of the tool call. It has to be a stringified version of the result of the tool.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"example": "rainy, 57°F",
"alias": [
"gen_ai.tool.output",
"gen_ai.tool.message",
"mcp.tool.result.content",
"ai.toolCall.result",
"anthropic.tool_result.content"
],
"changelog": [
{
"version": "0.5.0",
"prs": [
265
]
},
{
"version": "0.4.0",
"prs": [
221
]
}
]
}
{
"key": "gen_ai.tool.call.result.size",
"brief": "The UTF-8 byte length of the serialized tool call result, measured before truncation.",
"type": "integer",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": false,
"visibility": "public",
"examples": [
0,
1024
],
"search_alias": {
"name": "gen_ai.tool.call.result.size",
"type": "byte"
},
"additional_context": [
"The value is a non-negative byte count, not a token count, character count, or in-memory object size. It excludes span and envelope overhead.",
"Use 0 for an empty string result. Omit this attribute when the tool result is unavailable; do not treat missing output as zero."
],
"changelog": [
{
"version": "0.28.0",
"prs": [
679
],
"description": "Added gen_ai.tool.call.result.size attribute"
}
]
}
The list of source system tool definitions available to the GenAI agent or model.
Example[{"type": "function", "name": "get_current_weather", "description": "Get the current weather in a given location", "parameters": {"type": "object", "properties": {"location": {"type": "string", "description": "The city and state, e.g. San Francisco, CA"}, "unit": {"type": "string", "enum": ["celsius", "fahrenheit"]}}, "required": ["location", "unit"]}}]
{
"key": "gen_ai.tool.description",
"brief": "The description of the tool being used.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"example": "Searches the web for current information about a topic",
"changelog": [
{
"version": "0.1.0",
"prs": [
62,
127
]
}
]
}
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
Changelog
v0.24.0#582Added gen_ai.usage.cache_creation_input_tokens as an alias
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
This is a subset of gen_ai.usage.input_tokens, not an independent count. Do not sum this with gen_ai.usage.input_tokens — it is already included.
Changelog
v0.24.0#582Added gen_ai.usage.cache_read_input_tokens as an alias
{
"key": "gen_ai.usage.cache_read.input_tokens",
"brief": "The number of cached tokens used to process the AI input (prompt).",
"type": "integer",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"example": 50,
"alias": [
"gen_ai.usage.input_tokens.cached",
"gen_ai.usage.cache_read_input_tokens"
],
"additional_context": [
"This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.",
"This is a subset of gen_ai.usage.input_tokens, not an independent count. Do not sum this with gen_ai.usage.input_tokens — it is already included."
],
"changelog": [
{
"version": "0.24.0",
"prs": [
582
],
"description": "Added gen_ai.usage.cache_read_input_tokens as an alias"
},
{
"version": "0.11.0",
"prs": [
418
],
"description": "Added gen_ai.usage.cache_read.input_tokens attribute"
}
]
}
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
This count includes cached input tokens. gen_ai.usage.cache_read.input_tokens is a subset of this value, not an independent count — do not sum them together.
Changelog
v0.11.0#418Update additional_context to reference gen_ai.usage.cache_read.input_tokens
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
This count includes reasoning tokens. gen_ai.usage.reasoning.output_tokens is a subset of this value, not an independent count — do not sum them together.
Changelog
v0.11.0#418Update additional_context to reference gen_ai.usage.reasoning.output_tokens
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
This is a subset of gen_ai.usage.output_tokens, not an independent count. Do not sum this with gen_ai.usage.output_tokens — it is already included.
{
"key": "gen_ai.usage.reasoning.output_tokens",
"brief": "The number of tokens used for reasoning to create the AI output.",
"type": "integer",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": true,
"visibility": "public",
"example": 75,
"alias": [
"gen_ai.usage.output_tokens.reasoning"
],
"additional_context": [
"This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.",
"This is a subset of gen_ai.usage.output_tokens, not an independent count. Do not sum this with gen_ai.usage.output_tokens — it is already included."
],
"changelog": [
{
"version": "0.11.0",
"prs": [
418
],
"description": "Added gen_ai.usage.reasoning.output_tokens attribute"
}
]
}
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
This is the sum of gen_ai.usage.input_tokens and gen_ai.usage.output_tokens. Do not sum this with either of them — they are already included.
{
"key": "gen_ai.usage.total_tokens",
"brief": "The total number of tokens used to process the prompt. (input tokens plus output todkens)",
"type": "integer",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": false,
"visibility": "public",
"example": 20,
"alias": [
"ai.total_tokens.used",
"ai.usage.tokens"
],
"additional_context": [
"This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.",
"This is the sum of gen_ai.usage.input_tokens and gen_ai.usage.output_tokens. Do not sum this with either of them — they are already included."
],
"changelog": [
{
"version": "0.21.0",
"prs": [
583
],
"description": "Added ai.usage.tokens as an alias"
},
{
"version": "0.9.0",
"prs": [
397
],
"description": "Add additional_context"
},
{
"version": "0.4.0",
"prs": [
228
]
},
{
"version": "0.1.0",
"prs": [
57
]
}
]
}
Deprecated Attributes
These attributes are deprecated and should not be used in new code. See each attribute for migration guidance.
The available tools for the model. It has to be a stringified version of an array of objects.
Example[{"name": "get_weather", "description": "Get the weather for a given location"}, {"name": "get_news", "description": "Get the news for a given topic"}]
{
"key": "gen_ai.request.available_tools",
"brief": "The available tools for the model. It has to be a stringified version of an array of objects.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": false,
"visibility": "public",
"example": "[{\"name\": \"get_weather\", \"description\": \"Get the weather for a given location\"}, {\"name\": \"get_news\", \"description\": \"Get the news for a given topic\"}]",
"deprecation": {
"replacement": "gen_ai.tool.definitions",
"_status": "normalize"
},
"alias": [
"gen_ai.tool.definitions"
],
"changelog": [
{
"version": "0.22.0",
"prs": [
595
],
"description": "Added gen_ai.tool.definitions as an alias"
},
{
"version": "0.4.0",
"prs": [
221
]
},
{
"version": "0.1.0",
"prs": [
63,
127
]
}
]
}
The messages passed to the model. It has to be a stringified version of an array of objects. The role attribute of each object must be "user", "assistant", "tool", or "system". For messages of the role "tool", the content can be a string or an arbitrary object with information about the tool call. For other messages the content can be either a string or a list of objects in the format {type: "text", text:"..."}.
Example[{"role": "system", "content": "Generate a random number."}, {"role": "user", "content": [{"text": "Generate a random number between 0 and 10.", "type": "text"}]}, {"role": "tool", "content": {"toolCallId": "1", "toolName": "Weather", "output": "rainy"}}]
{
"key": "gen_ai.request.messages",
"brief": "The messages passed to the model. It has to be a stringified version of an array of objects. The `role` attribute of each object must be `\"user\"`, `\"assistant\"`, `\"tool\"`, or `\"system\"`. For messages of the role `\"tool\"`, the `content` can be a string or an arbitrary object with information about the tool call. For other messages the `content` can be either a string or a list of objects in the format `{type: \"text\", text:\"...\"}`.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": false,
"visibility": "public",
"example": "[{\"role\": \"system\", \"content\": \"Generate a random number.\"}, {\"role\": \"user\", \"content\": [{\"text\": \"Generate a random number between 0 and 10.\", \"type\": \"text\"}]}, {\"role\": \"tool\", \"content\": {\"toolCallId\": \"1\", \"toolName\": \"Weather\", \"output\": \"rainy\"}}]",
"deprecation": {
"replacement": "gen_ai.input.messages",
"_status": "transform",
"transformation": "gen_ai_request_messages_to_input_messages"
},
"alias": [
"ai.input_messages"
],
"changelog": [
{
"version": "0.4.0",
"prs": [
221
]
},
{
"version": "0.1.0",
"prs": [
63,
74,
108,
119,
122
]
}
]
}
{
"key": "gen_ai.response.object",
"brief": "The type of the object returned by the model.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": false,
"visibility": "public",
"examples": [
"chat.completion"
],
"deprecation": {
"reason": "This attribute is deprecated. The Sentry conventions have no replacement for the raw response object type.",
"_status": null
},
"changelog": [
{
"version": "0.21.0",
"prs": [
583
],
"description": "Added gen_ai.response.object attribute"
}
]
}
The model's response text messages. It has to be a stringified version of an array of response text messages.
Example["The weather in Paris is rainy and overcast, with temperatures around 57°F", "The weather in London is sunny and warm, with temperatures around 65°F"]
{
"key": "gen_ai.response.text",
"brief": "The model's response text messages. It has to be a stringified version of an array of response text messages.",
"type": "string",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": false,
"visibility": "public",
"example": "[\"The weather in Paris is rainy and overcast, with temperatures around 57°F\", \"The weather in London is sunny and warm, with temperatures around 65°F\"]",
"deprecation": {
"replacement": "gen_ai.output.messages",
"_status": "transform",
"transformation": "gen_ai_response_to_output_messages"
},
"alias": [],
"changelog": [
{
"version": "0.4.0",
"prs": [
221
]
},
{
"version": "0.1.0",
"prs": [
63,
74
]
}
]
}
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
Changelog
v0.24.0#582Added gen_ai.usage.cache_creation_input_tokens as an alias
v0.11.0#418Deprecate in favor of gen_ai.usage.cache_creation.input_tokens
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
This is a subset of gen_ai.usage.input_tokens, not an independent count. Do not sum this with gen_ai.usage.input_tokens — it is already included.
Changelog
v0.24.0#582Added gen_ai.usage.cache_read_input_tokens as an alias
v0.11.0#418Deprecate in favor of gen_ai.usage.cache_read.input_tokens
{
"key": "gen_ai.usage.input_tokens.cached",
"brief": "The number of cached tokens used to process the AI input (prompt).",
"type": "integer",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": false,
"visibility": "public",
"example": 50,
"deprecation": {
"replacement": "gen_ai.usage.cache_read.input_tokens",
"_status": "backfill"
},
"alias": [
"gen_ai.usage.cache_read.input_tokens",
"gen_ai.usage.cache_read_input_tokens"
],
"additional_context": [
"This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.",
"This is a subset of gen_ai.usage.input_tokens, not an independent count. Do not sum this with gen_ai.usage.input_tokens — it is already included."
],
"changelog": [
{
"version": "0.24.0",
"prs": [
582
],
"description": "Added gen_ai.usage.cache_read_input_tokens as an alias"
},
{
"version": "0.11.0",
"prs": [
418
],
"description": "Deprecate in favor of gen_ai.usage.cache_read.input_tokens"
},
{
"version": "0.9.0",
"prs": [
397
],
"description": "Add additional_context"
},
{
"version": "0.4.0",
"prs": [
228
]
},
{
"version": "0.1.0",
"prs": [
62,
112
]
}
]
}
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.
This is a subset of gen_ai.usage.output_tokens, not an independent count. Do not sum this with gen_ai.usage.output_tokens — it is already included.
Changelog
v0.11.0#418Deprecate in favor of gen_ai.usage.reasoning.output_tokens
{
"key": "gen_ai.usage.output_tokens.reasoning",
"brief": "The number of tokens used for reasoning to create the AI output.",
"type": "integer",
"apply_scrubbing": {
"key": "manual"
},
"is_in_otel": false,
"visibility": "public",
"example": 75,
"deprecation": {
"replacement": "gen_ai.usage.reasoning.output_tokens",
"_status": "backfill"
},
"alias": [
"gen_ai.usage.reasoning.output_tokens"
],
"additional_context": [
"This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.",
"This is a subset of gen_ai.usage.output_tokens, not an independent count. Do not sum this with gen_ai.usage.output_tokens — it is already included."
],
"changelog": [
{
"version": "0.11.0",
"prs": [
418
],
"description": "Deprecate in favor of gen_ai.usage.reasoning.output_tokens"
},
{
"version": "0.9.0",
"prs": [
397
],
"description": "Add additional_context"
},
{
"version": "0.4.0",
"prs": [
228
]
},
{
"version": "0.1.0",
"prs": [
62,
112
]
}
]
}
This attribute appears on both agent parent spans (aggregated totals) and LLM child spans (per-call values). When using sum() to count tokens, filter to gen_ai.operation.type:ai_client to avoid double-counting hierarchical spans.