Skip to main content
New: LLM Observability is now GA

Send data with OpenTelemetry

The OTLP endpoints, the authentication header, and a first request you can verify — for logs, metrics, and traces.

Before you start

  • A license key
  • A service instrumented with OpenTelemetry, or curl to send a test payload

aiAxonIQ speaks standard OTLP. Any OpenTelemetry SDK or the OpenTelemetry Collector can export to it without an aiAxonIQ-specific plugin.

Endpoints

The receiver exposes one path per signal over OTLP/HTTP:

  • POST /v1/logs
  • POST /v1/metrics
  • POST /v1/traces

These are the standard OTLP/HTTP paths, so an SDK configured with a base endpoint appends the right one automatically.

bash
export OIQ_ENDPOINT="<the base endpoint from Get Started>"
export OTEL_EXPORTER_OTLP_ENDPOINT="$OIQ_ENDPOINT"

Authenticate

Every ingest request needs your license key in the X-License-Key header. For SDKs, set it through the standard headers variable:

bash
export OTEL_EXPORTER_OTLP_ENDPOINT="$OIQ_ENDPOINT"
export OTEL_EXPORTER_OTLP_HEADERS="X-License-Key=oiq_4f3c2b1a9e8d7c6b5a4f3e2d1c0b9a8e"
export OTEL_SERVICE_NAME="checkout"

OTEL_SERVICE_NAME is not required by the receiver, but set it anyway — without it every signal arrives attributed to an unknown service and the service-level views have nothing to group by.

Send a first request

The fastest way to prove the path end to end, before touching your application's instrumentation, is a single OTLP/JSON log record.

curl -i "$OIQ_ENDPOINT/v1/logs" \
  -H "Content-Type: application/json" \
  -H "X-License-Key: $OIQ_LICENSE_KEY" \
  -d '{
    "resourceLogs": [{
      "resource": { "attributes": [
        { "key": "service.name", "value": { "stringValue": "docs-smoke-test" } }
      ]},
      "scopeLogs": [{
        "logRecords": [{
          "timeUnixNano": "'"$(date +%s)000000000"'",
          "severityText": "INFO",
          "body": { "stringValue": "hello from the aiAxonIQ docs" }
        }]
      }]
    }]
  }'

A successful request returns 202 Accepted. That means the batch was published to the pipeline; it becomes queryable a few seconds later. If you get anything else, the error reference lists every status the receiver returns and what causes it.

Encodings and compression

The receiver accepts both OTLP encodings over HTTP:

  • application/json
  • application/x-protobuf (also accepted as application/octet-stream)

Request bodies may be compressed with gzip, deflate, or brotli via Content-Encoding. OpenTelemetry SDKs default to gzip, which works without configuration.

OTLP over gRPC

The receiver also listens for OTLP over gRPC on port 4317, registering the standard logs, metrics, and trace services.

gRPC takes the same license key as HTTP — a key created in Settings → License Keys works on both transports. Send it as x-license-key metadata:

bash
export OTEL_EXPORTER_OTLP_PROTOCOL="grpc"
export OTEL_EXPORTER_OTLP_ENDPOINT="$OIQ_GRPC_ENDPOINT"
export OTEL_EXPORTER_OTLP_HEADERS="x-license-key=$OIQ_LICENSE_KEY"

gRPC metadata keys are lower-case by protocol, so x-license-key rather than X-License-Key. Everything else — rate limits, plan quotas, per-signal entitlements — is enforced identically on both transports.

The gRPC base endpoint is a separate value from the HTTP one, because a reverse proxy terminating HTTP/1.1 cannot also carry gRPC on the same listener. Get Started shows both.

Confirm it arrived

Two checks, in order:

  1. Did the receiver accept it? A 202 response means yes. A 401 means the key was missing, malformed, or revoked; a 400 means the payload did not decode.
  2. Did it land? Open the Logs Explorer and search for the service name you sent — for the curl example above, service:docs-smoke-test. See Searching logs for the query syntax.

If the receiver returned 202 and nothing appears after a minute, the problem is downstream of ingest rather than in your instrumentation, which is a useful thing to know before you start rereading your exporter config.

Next steps