Push Your First Event

Push Your First Event

You need a running backend from the Single Node setup, your account ID, and a user with account admin or inflow permissions on the account.

Create an inflow token

In the frontend

  1. Open Account → Settings → Tokens.
  2. Under Inflow, choose Allow all schemas, or Allow specific schemas and pick existing schemas or type a new name and press Enter. A trailing * matches every schema with that prefix, such as kitchen.*.
  3. To let the same token read data, set Query the same way.
  4. Choose a Token Expiry, then select Create Token.
  5. Copy the token. It is shown once.

Through the API

Sign in for a session token, then exchange it for an inflow token.

session=$(curl -s -X POST "http://localhost:5000/auth/token" \
  -H "Content-Type: application/json" \
  -d '{"username":"admin","password":"admin"}' \
  | jq -r .token)

inflow_token=$(curl -s -X POST "http://localhost:5000/auth/pat-token" \
  -H "Authorization: Bearer $session" \
  -H "Content-Type: application/json" \
  -d '{
    "expiration": "2027-01-01T00:00:00Z",
    "accounts": [
      {
        "accountId": "00000000-0000-0000-0000-000000000000",
        "inflow": { "schemas": [ { "schema": "kitchen.sink" } ] }
      }
    ]
  }' | jq -r .token)

echo $inflow_token

inflow.schemas lists the schemas the token may write. { "schema": "*" } allows every schema in the account, and a trailing * such as kitchen.* allows every schema with that prefix. Add a query scope, which accepts the same patterns, to the same account entry when the token also needs to read data:

"query": { "default": { "queryTimeoutSeconds": null }, "schemas": [ { "schema": "kitchen.sink" } ] }

expiration must be in the future. Set it to null for a token that never expires.

⚠️ Warning

Tokens cannot be revoked. A token stays valid until it expires or the backend's JWT signing key changes, so prefer short expirations.

Push an event

Send an array of entries to PUT /inflow/{account_id}. Each entry carries a schema, a timestamp, and a free-form data object. The schema is created on the first write.

curl -X PUT "http://localhost:5000/inflow/00000000-0000-0000-0000-000000000000" \
  -H "Authorization: Bearer $inflow_token" \
  -H "Content-Type: application/json" \
  -d '[{
    "schema": "kitchen.sink",
    "timestamp": "'$(date -u +%Y-%m-%dT%H:%M:%SZ)'",
    "data": {
      "device": "espresso-machine-01",
      "shots_pulled": 42,
      "water_temp_c": 93.5,
      "descale_due": false
    }
  }]'

A successful push returns 200 with an empty body.

Schema and field names accept letters, digits, ., _, and -. Timestamps are ISO-8601; send them in UTC.

⚠️ Warning

Entries whose schema falls outside the token's scope are dropped and the request still returns 200. If a schema never shows up, check the token's inflow.schemas first.

Query it

kitchen.sink
| where timestamp > ago(1h)
| project timestamp, device, shots_pulled, water_temp_c, descale_due

A new schema can take up to a minute to become queryable.

Each entry also carries columns added at ingest: __INFLOW_ID, __INFLOW_TIMESTAMP, __INFLOW_HOST, and __INFLOW_SOURCE_ADDRESS. Uploads from an agent add __INFLOW_AGENT.

Other ingest routes

  • POST /inflow/{account_id}/{schema}/csv and /tsv load delimited files into one schema. The first line is the header, column types are inferred from the first row of values, and rows are timestamped on arrival. These routes reject schema-scoped tokens; they need a token with unrestricted inflow access.
  • The Logship Agent collects host metrics, logs, and traces on the same endpoint.