Connect an Elasticsearch client
OriginChainDB answers the Elasticsearch REST API and Query DSL. Point the official @elastic client — or anything that speaks the Elasticsearch API — at your instance and index, search, and aggregate against the same data your HTTP API and SQL see. One store, one source of truth — and because the search index commits in the same write as the row, a document is findable the instant it is written.
There is nothing to switch on. Every instance answers the Elasticsearch API at https://<your-instance>/v1/tenants/<your-tenant>/es — that whole path is what a client takes as its node URL, with your API key as the bearer token.
What you can connect.
Any client that speaks the Elasticsearch 7.x REST API. We verify against the official @elastic/elasticsearch Node client — it connects, clears its product check, and runs a full index → search → aggregate → delete lifecycle unchanged. Dashboards and app code that issue the Query DSL keep working; you change the endpoint, not the queries. The cluster reports version 7.14.2, so pin your client to the 7.x line.
Connection details.
Point the client at your endpoint and authenticate with an API key from the console. info() is the handshake — it is what the client uses to confirm it is talking to Elasticsearch.
const { Client } = require('@elastic/elasticsearch')
const es = new Client({
node: 'https://<your-es-endpoint>', // your instance URL + /v1/tenants/<tenant>/es
auth: { apiKey: '<your-api-key>' }
})
await es.info() // clears the product check; reports version 7.14.2Insert data.
Index a single document by _id. It is searchable the instant the call returns — there is no refresh interval to wait on.
await es.index({
index: 'shop.products',
id: 'sku-8842',
document: { name: 'Carbon Marathon', brand: 'Aero', price: 149 }
})Load many at once with _bulk (newline-delimited actions). This is the fast path for backfills and ingest.
await es.bulk({ operations: [
{ index: { _index: 'shop.products', _id: 'sku-1207' } },
{ name: 'Trail 24', brand: 'Aero', price: 89 },
{ index: { _index: 'shop.products', _id: 'sku-3355' } },
{ name: 'City Runner', brand: 'Metro', price: 72 }
]})Or straight over HTTP — the same NDJSON body a stock Elasticsearch cluster takes:
POST /_bulk
{"index":{"_index":"shop.products","_id":"sku-1207"}}
{"name":"Trail 24","brand":"Aero","price":89}_update is a partial merge — the fields you send are updated and every other field is preserved.
await es.update({
index: 'shop.products', id: 'sku-8842',
doc: { price: 139 } // name, brand, ... untouched
})Search and aggregate.
The Query DSL you already write — bool, match, term, filters — with aggregations in the same request.
await es.search({
index: 'shop.products',
query: { bool: {
must: [{ match: { name: 'marathon' } }],
filter: [{ term: { brand: 'Aero' } }]
} },
aggs: { by_brand: { terms: { field: 'brand' } } }
})Also supported: _count, _msearch, _mget, search_after deep paging, collapse, _delete_by_query and _update_by_query (both honor max_docs), and _reindex into a fresh index. Read a document straight back with GET or HEAD /:index/_doc/:id, or /:index/_source/:id for the bare document; ask what a field looks like with _field_caps; and guard a bulk write with if_seq_no — a stale precondition comes back as a per-item 409 and every other item in the batch still lands.
Security comes with the search.
Row-level security and column masking apply to the search itself, not just to the documents it returns. A caller who cannot see a row will not find it through a query, and a query that searches a masked column is refused rather than answered — the match set can't be used to reconstruct a value the mask hides. This is enforcement a bolt-on search cluster can't give you, because it never sees your database's policies.
Limits, stated plainly.
This is a drop-in for the API a real client and its dashboards exercise — not the entire Elasticsearch surface. What we don't answer yet fails closed with an explicit error; it never returns a wrong or silently-partial result.
- Aggregations: terms, metrics, range, histogram, date_histogram, percentiles, top_hits, sub-aggregations and pipeline aggs are in, and so is filters — named buckets, each its own query, with sub-aggregations over exactly that bucket. Send filters in its own request: it is answered with one search per filter. extended_stats, composite and nested are not answered yet, and missing on a metric aggregation is refused rather than filled in with a value you did not choose.
- Suggesters: the term suggester corrects a word against what is actually indexed in a field, with suggest_mode honored. Options carry the corrected text and a score, and no document frequency — that number is not available to this API, and we would rather omit a field than report one we cannot stand behind. The phrase and completion suggesters are refused by name.
- Scoring: function_score and per-field boosts are in; script_score and rescore are refused.
- Deep paging: search_after within a 10,000-hit window; Point-in-Time (PIT) is not offered.
- Cluster management: ILM, snapshots, and index templates are managed by OriginChainDB, not over the ES API. Vector / kNN search lives on a dedicated surface.
- Version: the cluster reports 7.14.2; pin clients to the 7.x line.
Feature coverage is a separate question from scale — see Full-text search for how the index is built and what a single node holds.
Elasticsearch is a trademark of Elasticsearch B.V., registered in the U.S. and in other countries. OriginChainDB is not affiliated with, endorsed by, or sponsored by Elasticsearch B.V. OriginChainDB implements a compatible HTTP API so that existing Elasticsearch clients can talk to it; it does not distribute Elasticsearch software.