Query streams
Query streams are virtual, read-only streams defined by an ES|QL query. Unlike classic and wired streams that store ingested data, query streams resolve at query-time — no data is written to storage, and no ingestion pipeline, routing rules, or retention policies are affected.
Use query streams to create persistent, named views of your data that you can attach assets to, organize hierarchically, and reference by name in ES|QL queries.
Query streams can be root-level or nested:
- Root-level query streams reference any existing stream in the
FROMclause and stand alone in the stream hierarchy. - Nested query streams are logically grouped under a parent stream. The ES|QL query must reference the parent stream. Nesting organizes streams visually without affecting data routing or storage.
- Go to Streams in the navigation menu or use the global search field.
- Select Create stream, then choose Query stream.
- Enter a name for the stream.
- Write an ES|QL query that defines the data this stream represents. The query must reference at least one existing stream.
- Preview the query results, then select Save.
- Go to Streams and open a wired stream.
- Go to the Partitioning tab.
- Select Add child stream, then choose Query stream.
- Enter a name and write the ES|QL query. The query should reference the parent stream.
- Select Save.
When you create a query stream named logs.nginx, the system creates an ES|QL view named $.logs.nginx. The $. prefix keeps query stream views in a separate namespace from ingest streams, so they never shadow or interfere with your underlying data streams.
To query a query stream directly in ES|QL, use its prefixed view name:
FROM $.logs.nginx
| WHERE status_code >= 500
When you open a query stream in Discover, the query is pre-populated automatically using the correct prefixed name.
Query streams are read-only views, so features that modify ingestion, storage, or routing aren't available. The following table shows which Streams features apply:
| Feature | Available | |
|---|---|---|
| Significant events | Yes | |
| Schema — add field descriptions | Yes — field types are derived from ES | QL output and can't be changed, but descriptions can be added |
| Attach dashboards, alerts, SLOs | Yes | |
| Partitioning | No — query streams don't route ingested data | |
| Processing | No — query streams don't run ingest pipelines | |
| Retention | No — query streams don't store data | |
| Data quality | No — query streams don't store data |
You can write ES|QL queries directly in Discover without creating a query stream. The right choice depends on whether you need the result to persist as a governed product entity.
| Query stream | ES | QL in Discover | |
|---|---|---|---|
| Persistence | Saved as a named, reusable entity | Session-only unless saved as a saved search | |
| Governance | Named, owned, appears in Streams listing | None | |
| Asset attachment | Dashboards, alerts, SLOs | Not supported | |
| Significant events | Yes | No | |
| Stream hierarchy | Appears in the Streams listing, can be nested under a parent stream | Not part of stream hierarchy | |
| ES | QL reference | Queryable by prefixed name (FROM $.stream-name) |
Not directly referenceable by name |
| Best for | Persistent views you need to monitor, share, or attach alerts to | Exploratory or one-off analysis |
Create a query stream when you need to:
- Attach an alert, SLO, or dashboard to a specific slice of your data.
- Monitor significant events — significant events discovery runs against the query on a schedule.
- Share a reusable data view — teammates can find the stream by name in the Streams listing or reference it in ES|QL.
- Organize data logically — nest the stream under a parent to keep related views grouped without changing ingestion.
Use ES|QL directly in Discover when you're:
- Exploring data to understand its shape before committing to a view.
- Running a one-off analysis you don't need to revisit.
- Iterating on a query before deciding whether to save it as a stream.