> ## Documentation Index
> Fetch the complete documentation index at: https://docs.mirador.org/llms.txt
> Use this file to discover all available pages before exploring further.

# Enrichment Hints

> Track onchain and external actions by emitting reserved OpenTelemetry span events

Mirador enrichment hints connect an OpenTelemetry trace to actions that happen outside your process. Emit a reserved `mirador.*` event on the active user-flow span, and Mirador follows the action and stitches its outcome into that same trace.

Supported actions include EVM, Solana, Canton, Safe, Relay, and Stripe.

<Info>
  The canonical machine-readable contract is published at [`otel.mirador.org/llms.txt`](https://otel.mirador.org/llms.txt). Use it when generating integrations or prompting a coding agent.
</Info>

## Event catalog

| Event name                   | Tracks                                       | Required identity               |
| ---------------------------- | -------------------------------------------- | ------------------------------- |
| `mirador.web3.evm.txhint`    | EVM transaction through receipt              | `tx.hash` + EVM chain           |
| `mirador.web3.solana.txhint` | Solana transaction                           | `tx.signature`                  |
| `mirador.web3.canton.txhint` | Canton transaction                           | `tx.update_id`                  |
| `mirador.web3.safe.txhint`   | Safe multisig confirmation through execution | `safe.tx_hash` + EVM chain      |
| `mirador.web3.safe.msghint`  | Safe EIP-712 message signing                 | `safe.message_hash` + EVM chain |
| `mirador.web3.relayhint`     | Relay bridge deposit through fill            | `relay.request_id`              |
| `mirador.stripe.paymenthint` | Stripe PaymentIntent through payout          | `stripe.payment_intent_id`      |

An EVM chain is identified by `chain.id`, `chain.name`, or both when they agree.

## Attribute reference

| Attribute                  | Type                      | Required for                                       | Example                                        |
| -------------------------- | ------------------------- | -------------------------------------------------- | ---------------------------------------------- |
| `tx.hash`                  | string                    | EVM transaction                                    | `0x` + 64 hexadecimal characters               |
| `chain.id`                 | integer or decimal string | EVM and Safe hints, unless `chain.name` is present | `8453`                                         |
| `chain.name`               | string                    | EVM and Safe hints, unless `chain.id` is present   | `base`                                         |
| `tx.signature`             | string                    | Solana transaction                                 | Base58 transaction signature                   |
| `tx.update_id`             | string                    | Canton transaction                                 | Canton update ID                               |
| `canton.party_id`          | string                    | Optional Canton read-as context                    | `Alice::1220…`                                 |
| `safe.tx_hash`             | string                    | Safe transaction                                   | SafeTxHash, not the executing transaction hash |
| `safe.message_hash`        | string                    | Safe message                                       | Safe message hash                              |
| `relay.request_id`         | string                    | Relay                                              | Request ID returned by the quote               |
| `stripe.payment_intent_id` | string                    | Stripe                                             | `pi_…`                                         |
| `stripe.account_id`        | string                    | Optional Stripe Connect routing                    | `acct_…`                                       |

Extra attributes are preserved as context but do not control tracking.

<Warning>
  Attribute keys are literal flat strings. Emit `'tx.hash'`; do not send a nested object such as `{ tx: { hash: value } }`.
</Warning>

## Emit a hint

Add the event only after the external system returns its identity.

<CodeGroup>
  ```typescript TypeScript theme={null}
  span.addEvent('mirador.web3.evm.txhint', {
    'tx.hash': transactionHash,
    'chain.id': 8453,
    'checkout.step': 'submit',
  });

  span.addEvent('mirador.stripe.paymenthint', {
    'stripe.payment_intent_id': paymentIntent.id,
    'stripe.account_id': connectedAccountId,
  });
  ```

  ```go Go theme={null}
  span.AddEvent("mirador.web3.evm.txhint", trace.WithAttributes(
      attribute.String("tx.hash", transactionHash),
      attribute.Int64("chain.id", 8453),
      attribute.String("checkout.step", "submit"),
  ))

  span.AddEvent("mirador.stripe.paymenthint", trace.WithAttributes(
      attribute.String("stripe.payment_intent_id", paymentIntentID),
  ))
  ```

  ```python Python theme={null}
  span.add_event("mirador.web3.solana.txhint", {
      "tx.signature": signature,
  })

  span.add_event("mirador.web3.canton.txhint", {
      "tx.update_id": update_id,
      "canton.party_id": party_id,
  })
  ```
</CodeGroup>

## Rules that must hold

1. **Emit an event, not a child span.** Add the reserved event to the active user-flow span.
2. **Use the exact event name.** Names are case-sensitive.
3. **Emit one event per action.** Two transactions require two events; do not use an array of hashes.
4. **Use flat attribute keys.** Dots are part of the key name.
5. **Wait for the identity.** Do not emit before the transaction, intent, or payment ID is known.
6. **Keep the span sampled.** A sampled-out span cannot carry a hint to Mirador.
7. **Flush before exit.** Allow the batch exporter to drain or explicitly shut down the provider.

## Chain resolution

The EVM and Safe hints accept these forms:

| Input                                   | Result                                    |
| --------------------------------------- | ----------------------------------------- |
| `chain.id: 8453`                        | Accepted                                  |
| `chain.id: "8453"`                      | Accepted                                  |
| `chain.name: " Base "`                  | Accepted; normalized and resolved to Base |
| `chain.id: 1` with `chain.name: "base"` | Invalid because the values contradict     |
| `chain.name: "unknown"` without an ID   | Invalid                                   |
| `chain.id: 0` or `"0x2105"`             | Invalid                                   |

Known IDs include Ethereum `1`, Optimism `10`, BNB Smart Chain `56`, Polygon `137`, HyperEVM `999`, Base `8453`, and Arbitrum `42161`.

## Invalid hints are preserved

A reserved event that is missing a required attribute or fails chain validation becomes a normal span event. Mirador preserves it instead of dropping it, but enrichment tracking does not start.

This fallback makes typos visible in the trace while preventing Mirador from following the wrong external action.

## Next steps

<CardGroup cols={2}>
  <Card title="Traces over OTLP" icon="route" href="/opentelemetry/traces">
    Configure trace export and understand span mapping
  </Card>

  <Card title="Transaction hints" icon="link" href="/concepts/transaction-hints">
    Learn how Mirador follows and enriches transactions
  </Card>
</CardGroup>
