Elasticsearch
Search and analytics engine: full-text, logs and vector search over a REST API
Elasticsearch on Cubeship
Elasticsearch is a search and analytics engine: full-text search, logs and metrics, and vector search, over a JSON REST API.
This template installs one Elasticsearch node on a Cubeship instance, with security on and its indices kept in a volume.
What it creates
- elasticsearch — a single node, from
docker.elastic.co/elasticsearch/elasticsearch:9.5.3, with its REST API on the domain you choose and its data in a volume at/usr/share/elasticsearch/data.
It needs Cubeship 0.7.0 or newer.
What you are asked
| Input | What to give |
|---|---|
| Where the Elasticsearch API answers | A domain you control, pointed at your instance. |
| The password for the elastic superuser | Nothing — the instance generates it and shows it once. Keep a copy. |
After installing
Check it answers, with the generated password:
curl -u elastic:<password> https://<your domain>
Then create a user or an API key per app rather than handing out elastic:
curl -u elastic:<password> -X POST https://<your domain>/_security/api_key \
-H 'Content-Type: application/json' -d '{"name": "my-app"}'
An app on the same instance can skip the public name and reach the node at its
internal address, shown on its page in the dashboard —
http://cubeship-elasticsearch-production-elasticsearch:9200 with the
suggested names.
ELASTIC_PASSWORD only sets the password on the first start. Change it
afterwards with the _security/user/elastic/_password API.
Choices this template makes
- One node.
discovery.typeissingle-node: an app with a volume runs as one copy, so there is no cluster to form, and every index is best created withnumber_of_replicas: 0or it stays yellow. - No memory-mapped indices.
node.store.allow_mmapisfalse, because memory mapping needsvm.max_map_countraised on the host, which a template cannot do. Search is somewhat slower for it. If you raise it yourself (sysctl -w vm.max_map_count=1048576, and in/etc/sysctl.conf), removeES_SETTING_NODE_STORE_ALLOW__MMAPfrom the app and redeploy. - TLS at the instance's proxy. The domain is HTTPS; the node itself speaks
plain HTTP, so the internal address is
http://. - No health check. Every route needs credentials, and a check answered 401 would take the domain down. A deploy counts the node as up once its container stays running.
The volume
The node stops for the length of a deploy, and takes a while to start: search is unavailable until it has. Back the volume up from the app's settings, or use Elasticsearch's own snapshots to an object store.
Resources
The app is limited to 2 CPUs and 2 GiB of memory, and Elasticsearch gives half
of that to its heap. Raise limits in template.yaml for larger indices.
What this creates
elasticsearch
docker.elastic.co/elasticsearch/elasticsearch:9.5.3
/usr/share/elasticsearch/data
Volume of elasticsearch
# yaml-language-server: $schema=https://cubeship.dev/schema/template/v1.json
version: 1
# The first release that gives a volume to the user its image runs as;
# Elasticsearch runs as 1000 and cannot write to one owned by root.
minCubeship: "0.7.0"
project: elasticsearch
inputs:
- key: domain
type: domain
label: Where the Elasticsearch API answers
- key: password
type: secret
label: The password for the elastic superuser
generate: 24
apps:
- key: search
name: elasticsearch
image: docker.elastic.co/elasticsearch/elasticsearch
tag: "9.5.3"
port: 9200
# No health: every route asks for credentials, and a check answered
# 401 would take the domain down.
domains:
- host: ${input.domain}
volumes:
- path: /usr/share/elasticsearch/data
# The heap is sized from this limit: half of it.
limits: { cpu: 2, memory: 2Gi }
env:
# Settings have dots in their names, which a variable cannot: after
# ES_SETTING_ an underscore is a dot and a double one an underscore.
ES_SETTING_DISCOVERY_TYPE: single-node
ES_SETTING_XPACK_SECURITY_ENABLED: "true"
# TLS ends at the instance's proxy, which speaks plain HTTP to the app.
ES_SETTING_XPACK_SECURITY_HTTP_SSL_ENABLED: "false"
# Memory-mapped indices need vm.max_map_count raised on the host,
# which a template cannot do.
ES_SETTING_NODE_STORE_ALLOW__MMAP: "false"
ELASTIC_PASSWORD: ${input.password}