Inventory every compatibility contract before choosing a migration mechanism.
Assess API, Mapping, Query, Security, Plugin, Snapshot, and Client Compatibility Before Migration
Turn Elasticsearch↔OpenSearch migration into an evidence-based compatibility program covering APIs, mappings, queries, clients, plugins, snapshots, security, managed-service boundaries, data sync, relevance and rollback.
Learning outcomes
Build a migration compatibility inventory that separates syntax similarity from semantic compatibility.
Test mappings, analyzers, query behavior, security, plugins, snapshots, and clients as independent migration surfaces.
Classify each feature as portable, translatable, replaceable, or blocking instead of assuming drop-in compatibility.
Create automated evidence for data parity, relevance, latency, authorization, and rollback readiness.
Explain why current Elasticsearch 9.5.3 to OpenSearch 3.8.0 migration needs explicit validation rather than a product-name shortcut.
Run mutating, destructive, security, lifecycle, snapshot, failure-injection, and load-test commands only in the disposable AtlasMart lab or an equivalently isolated environment. Verify the target cluster, index, tenant, credentials, and rollback path before execution; treat shown output as an expected invariant unless the lesson explicitly labels it as captured evidence.
1. AtlasMart problem: “the APIs look familiar” is not a migration plan
AtlasMart has accumulated catalog mappings, analyzers, Query DSL
templates, an Elasticsearch API-key model, Kibana saved objects,
an ILM retention policy, client retry logic, and a relevance
test set. A project manager sees similar JSON syntax in
OpenSearch and asks for a weekend endpoint switch. The
engineering risk is not whether both products expose
/_search; it is whether every
behavior the application depends on still means the
same thing after the move.
A compatibility program is a versioned inventory of contracts. Each contract has a source behavior, target behavior, evidence, owner, migration action, and rollback trigger. Shared historical ancestry is useful context, not a guarantee.
2. Start with seven independent compatibility surfaces
| Surface | Evidence to collect | Typical hidden drift |
|---|---|---|
| REST/API | request/response fixtures, error codes, defaults | parameter names, defaults, deprecations, response metadata |
| Mappings/analysis | mapping JSON, analyzer tests, token outputs | field types, normalizers, vector fields, dynamic behavior |
| Queries/relevance | golden queries, top-k IDs, NDCG/MRR/Recall | scoring implementation, unsupported queries, hybrid semantics |
| Security | identity, role, API-key, DLS/FLS negative tests | privilege names, role mapping, tenant/space semantics |
| Plugins/features | plugin inventory, API probes, feature status | plugin absence, version coupling, license/subscription boundaries |
| Snapshots/lifecycle | repository metadata, restore matrix, ILM/ISM state | index-version rules, product boundary, lifecycle non-equivalence |
| Clients/SDKs | integration tests, retry/error/auth behavior | version checks, serializers, namespaces, removed APIs |
3. Compatibility classification: portable is the rarest and safest label
| Class | Meaning | AtlasMart example |
|---|---|---|
| Portable | same intent and tested behavior with no translation |
basic keyword/text product
fields
|
| Translatable | same business intent, different platform construct | Elastic ILM retention intent → OpenSearch ISM policy |
| Replaceable | feature is not equivalent; use a different design | ES|QL workflow → PPL/SQL or Query DSL/aggregations |
| Blocking | no acceptable target behavior within project constraints | required plugin/managed feature absent on target |
The classification is per version pair. A construct marked “translatable” for Elasticsearch 9.5.3 → OpenSearch 3.8.0 might change when either product version changes.
4. Inventory the exact running systems
All Chapter 29 labs preserve the established local endpoints and
security assumptions: Elasticsearch 9.5.3 at
https://localhost:9200 with
ELASTIC_PASSWORD and the copied CA file
atlasmart-es-http-ca; OpenSearch 3.8.0 at
https://localhost:9201 with
OPENSEARCH_INITIAL_ADMIN_PASSWORD. The shared
Docker network remains atlasmart-search.
OpenSearch's demo certificate trust bypass (-k) is
acceptable only for this disposable local lab. The migration
fixture uses one primary and zero replicas to fit a single
workstation; production redundancy, recovery headroom, and
managed-service networking must be designed separately.
# Elasticsearch
curl --cacert atlasmart-es-http-ca -u "elastic:$ELASTIC_PASSWORD" \
https://localhost:9200/
curl --cacert atlasmart-es-http-ca -u "elastic:$ELASTIC_PASSWORD" \
https://localhost:9200/_cat/plugins?v
# OpenSearch disposable lab only; -k trusts the demo certificate.
curl -k -u "admin:$OPENSEARCH_INITIAL_ADMIN_PASSWORD" \
https://localhost:9201/
curl -k -u "admin:$OPENSEARCH_INITIAL_ADMIN_PASSWORD" \
https://localhost:9201/_cat/plugins?v
Store these responses with the migration report. “Elasticsearch 9” and “OpenSearch 3” are too coarse for plugin/client/managed-service compatibility decisions.
5. Mapping and analyzer compatibility is observable
PUT atlasmart-migrate-source-v1
{
"settings": {
"number_of_shards": 1,
"number_of_replicas": 0
},
"mappings": {
"dynamic": "strict",
"properties": {
"sku": {"type":"keyword"},
"tenant_id": {"type":"keyword"},
"name": {"type":"text", "fields":{"raw":{"type":"keyword"}}},
"category": {"type":"keyword"},
"price": {"type":"scaled_float", "scaling_factor":100},
"available": {"type":"boolean"},
"updated_at": {"type":"date"}
}
}
}
POST _bulk?refresh=wait_for
{"index":{"_index":"atlasmart-migrate-source-v1","_id":"P-1001"}}
{"sku":"P-1001","tenant_id":"tenant-a","name":"Waterproof Hiking Boot","category":"footwear","price":129.90,"available":true,"updated_at":"2026-09-12T10:00:00Z"}
{"index":{"_index":"atlasmart-migrate-source-v1","_id":"P-1002"}}
{"sku":"P-1002","tenant_id":"tenant-a","name":"Trail Running Shoe","category":"footwear","price":99.50,"available":true,"updated_at":"2026-09-12T10:01:00Z"}
{"index":{"_index":"atlasmart-migrate-source-v1","_id":"P-1003"}}
{"sku":"P-1003","tenant_id":"tenant-a","name":"Insulated Water Bottle","category":"outdoor","price":32.00,"available":true,"updated_at":"2026-09-12T10:02:00Z"}
{"index":{"_index":"atlasmart-migrate-source-v1","_id":"P-1004"}}
{"sku":"P-1004","tenant_id":"tenant-b","name":"Lightweight Hiking Pack","category":"outdoor","price":74.00,"available":false,"updated_at":"2026-09-12T10:03:00Z"}
{"index":{"_index":"atlasmart-migrate-source-v1","_id":"P-1005"}}
{"sku":"P-1005","tenant_id":"tenant-b","name":"Merino Hiking Sock","category":"apparel","price":18.50,"available":true,"updated_at":"2026-09-12T10:04:00Z"}
POST atlasmart-migrate-source-v1/_analyze
{
"field": "name",
"text": ["Waterproof hiking boots"]
}
Record the token sequence, positions, offsets, and any normalization that affects matching. Recreate the destination mapping deliberately, then run the same probe. Do not rely on copying an entire source mapping if it contains platform-specific settings or fields.
6. Query compatibility means result semantics, not HTTP 200
POST atlasmart-migrate-source-v1/_search
{
"size": 3,
"query": {
"bool": {
"filter": [
{"term":{"tenant_id":"tenant-a"}},
{"term":{"available":true}}
],
"must": [
{"match":{"name":"hiking"}}
]
}
},
"sort": [
{"_score":"desc"},
{"sku":"asc"}
]
}
Persist top IDs and judged relevance labels, not raw score equality. BM25 and product-specific scoring details can diverge; the migration acceptance question is whether user-visible relevance remains within the agreed quality envelope.
7. Security and UI are separate migration projects
Elasticsearch roles, realms, API keys, Kibana Spaces, and subscription-gated DLS/FLS/audit controls do not map one-to-one to the OpenSearch Security plugin’s internal users, role mappings, tenants, DLS/FLS, audit configuration, and API keys. A successful document copy says nothing about authorization parity. Build negative tests: a reader can search tenant-a, cannot index, cannot read tenant-b, and cannot administer snapshots.
Likewise, Kibana saved objects are not a generic portable dashboard format for OpenSearch Dashboards. Recreate or convert dashboards only after the underlying data views/index patterns, query language, security, and field contracts have been validated.
8. Snapshots are not a cross-product interchange format
Elastic documents snapshot restore compatibility within Elasticsearch version/index-version rules. OpenSearch documents its own snapshot and migration rules. Do not restore an arbitrary Elasticsearch snapshot directly into OpenSearch or the reverse unless the exact source/target/service workflow explicitly documents it. OpenSearch Migration Assistant uses Reindex-from-Snapshot as a migration mechanism, which reads source snapshot shard data and reindexes it into the target—it is not evidence that an Elasticsearch repository is a universally restorable OpenSearch repository.
9. Client compatibility must be tested as code
Elastic’s current Python client documentation says the 9.x client family is for Elasticsearch 9.x (and forward to 10.x under its documented compatibility policy), while an 8.x client can span Elasticsearch 8.x→9.x during upgrades but does not expose new 9.x features. OpenSearch explicitly warns that Elasticsearch clients are not fully compatible with OpenSearch 2.0 and later and recommends OpenSearch clients for OpenSearch clusters. Do not preserve a single “Elasticsearch client” abstraction by merely changing the URL.
10. Compatibility matrix artifact
{
"source": {"product":"Elasticsearch","version":"9.5.3"},
"target": {"product":"OpenSearch","version":"3.8.0"},
"contract": "catalog-search-v3",
"items": [
{"surface":"mapping", "feature":"text+keyword", "class":"portable", "test":"mapping-001"},
{"surface":"lifecycle", "feature":"ILM", "class":"translatable", "target":"ISM", "test":"lifecycle-003"},
{"surface":"analytics", "feature":"ES|QL", "class":"replaceable", "target":"PPL/DSL", "test":"analytics-007"},
{"surface":"security", "feature":"API-key role descriptors", "class":"translatable", "test":"auth-004"}
]
}
Migration approval requires every production dependency to have a class and a test. “Unknown” is a blocking state, not a harmless omission.
11. Wrong approach → repaired approach
Check your understanding
- Why is REST similarity insufficient evidence?
- What should raw score equality be replaced with?
- Why are snapshots a separate compatibility surface?
- What is the current Migration Assistant caveat for this course baseline?
- What does Lesson 2 decide?
Review the answers
1. Because the same-looking endpoint can differ in defaults, response shape, feature support, scoring, security, plugins, or version semantics.
2. Judged relevance evidence such as top-k IDs, Recall@k, NDCG, or MRR-like metrics plus deterministic tie-breaking where needed.
3. Snapshot restore is constrained by product and version/index compatibility rules; it is not a universal cross-product serialization format.
4. Its current documented OpenSearch 3.x source matrix lists Elasticsearch through 8.x, not Elasticsearch 9.5.3.
5. Which data-movement pattern—snapshot-supported path, remote reindex, ETL/full copy, dual write, or incremental sync—matches the compatibility and downtime constraints.
Summary and next step
Preserve the evidence, assumptions, version boundaries, and safety checks established in this lesson. Carry them into the next lesson—or, at the end of the capstone, into the production runbook—rather than treating this lesson as an isolated recipe.
References and current-version checks
- Elastic Stack 9.5.3 release
- Elasticsearch snapshot and restore compatibility
- Elasticsearch restore snapshot guidance
- Elasticsearch reindex and reindex-from-remote
- Elasticsearch reindex settings
- Elasticsearch Python client compatibility
- Elasticsearch Python client release notes
- OpenSearch 3.8 version history
- OpenSearch upgrade or migrate guidance
- OpenSearch Reindex Documents API
- OpenSearch reindex data guidance
- OpenSearch language clients and compatibility
- OpenSearch Migration Assistant
- Migration Assistant supported migration paths
- Amazon OpenSearch Service snapshot migration