Use built-in text and geospatial index families with their exact restrictions while separating them from MongoDB Search/Vector Search and recording 8.3 geospatial compatibility.

Text and Geospatial Index Families: Capabilities, Restrictions, and Dedicated Search Alternatives

Batch heterogeneous writes safely, interpret partial success, compare ordered and unordered execution, and use modern cross-namespace bulk APIs without assuming all-or-nothing behavior.

Intermediate120–165 minutesText + 2dsphere/2d boundary labMongoDB 8.3.8 · mongosh 2.10.0Last reviewed: September 2026

Learning objectives

01

Use self-managed text indexes for basic $text search while understanding their one-index, storage, hint, sort, and language limitations.

02

Differentiate built-in text indexes from MongoDB Search and Vector Search rather than treating them as interchangeable names.

03

Create a 2dsphere index on GeoJSON and use longitude/latitude order correctly for spherical proximity queries.

04

Explain why 2d indexes belong to legacy flat-plane coordinate pairs and should not be used for GeoJSON spherical workloads.

05

Record the MongoDB 8.3 2dsphereIndexVersion 4 compatibility boundary in upgrade/downgrade planning.

Reproducible lab baseline

This lesson pins MongoDB Community Server 8.3.8 with mongodb/mongodb-community-server:8.3.8-ubuntu2204-slim and mongosh 2.10.0. The server is a disposable standalone published only on loopback 127.0.0.1:27071. Authentication and TLS are disabled only for this isolated lab. Feature Compatibility Version (FCV) is observed but never changed. Default read/write concern and primary read preference apply. Atlas, KMS, and Enterprise Advanced are not mandatory. MongoDB Search and Vector Search are discussed as separate modern search capabilities, but they are not required for the mandatory local lab. The local lab uses the built-in self-managed text and 2dsphere index families only. Runtime output shown as “expected” is documentation-derived because this generation environment has no Docker/mongod/mongosh runtime.

Evidence before index enthusiasm

Specialized indexes are useful only when their eligibility rules match the workload. Every lab therefore inspects index metadata, matching and non-matching query shapes, explain evidence, and state transitions. Tiny fixtures prove semantics—not production latency, cache behavior, or sharded-cluster distribution.

1. “Search index” can mean different subsystems

The built-in text index supports the $text operator on string content in self-managed MongoDB. It performs language-aware tokenization/stemming and has important limits: only one text index per collection (though it may contain multiple fields), text queries cannot be hinted, text indexes cannot cover queries, and they add an entry per unique stemmed term. Current MongoDB documentation recommends MongoDB Search or MongoDB Vector Search for richer full-text, semantic, hybrid, and generative-search workloads. Those use a different search subsystem and are taught later in Chapter 21.

Capability Built-in text MongoDB Search / Vector Search
Mandatory local availability Yes on Community self-managed Separate deployment/service capability; not required here.
Query API $text / textScore Search/vector aggregation operators and dedicated search indexes.
Index count At most one text index per collection Multiple dedicated search indexes are supported depending on deployment.
Semantic/vector retrieval No Vector Search is designed for vector similarity; Search offers richer full-text features.

2. Build and query a basic self-managed text index

bash · isolated Chapter 11 Lesson 5 lab setup
docker rm -f atlasmart-mongo-ch11-l5 2>/dev/null || truedocker volume rm atlasmart-mongo-ch11-l5-data 2>/dev/null || truedocker run -d --name atlasmart-mongo-ch11-l5 \  -p 127.0.0.1:27071:27017 \  -v atlasmart-mongo-ch11-l5-data:/data/db \  mongodb/mongodb-community-server:8.3.8-ubuntu2204-slimmongosh "mongodb://127.0.0.1:27071/atlasmart?directConnection=true" --quiet --eval \'printjson({server:db.version(),hello:db.hello().isWritablePrimary}); printjson(db.getSiblingDB("admin").runCommand({getParameter:1,featureCompatibilityVersion:1}))' 
javascript · seed searchable products and build weighted text index
const p=db.products_ch11_l5;p.drop();p.insertMany([ {_id:1,sku:"P1",name:"Travel USB Charger",description:"compact fast charger for travel and phone",category:"electronics"}, {_id:2,sku:"P2",name:"USB-C Cable",description:"durable braided charging cable",category:"electronics"}, {_id:3,sku:"P3",name:"Travel Backpack",description:"lightweight carry-on backpack for travel",category:"bags"}, {_id:4,sku:"P4",name:"Desk Lamp",description:"adjustable warm desk light",category:"home"}]);print(p.createIndex({name:"text",description:"text"},{name:"txt_name_description",weights:{name:5,description:1},default_language:"english"}));printjson(p.getIndexes());
javascript · run text search and expose hint restriction
const p=db.products_ch11_l5;printjson(p.find( {$text:{$search:"travel charger"}}, {_id:0,sku:1,name:1,score:{$meta:"textScore"}}).sort({score:{$meta:"textScore"}}).toArray());try{ printjson(p.find({$text:{$search:"usb"}}).hint({category:1}).toArray());}catch(e){ printjson({name:e.name,code:e.code,message:e.message}); }
Write/storage cost

Text indexes can be substantially larger and more expensive to update than ordered scalar indexes because tokenized/stemmed terms create many index entries. Do not add a wildcard text index simply because “search everything” sounds convenient.

3. Geospatial families encode a geometry model

A 2dsphere index supports GeoJSON and spherical calculations appropriate to Earth-like surfaces. A 2d index is intended for legacy coordinate pairs and flat Euclidean calculations. Choosing the wrong family is a semantic error, not merely a performance issue. For GeoJSON longitude/latitude data, coordinates must be listed as [longitude, latitude].

javascript · create GeoJSON points, 2dsphere index, and proximity query
const s=db.stores_ch11_l5;s.drop();s.insertMany([ {_id:1,name:"AtlasMart Central",location:{type:"Point",coordinates:[-73.9857,40.7484]}}, {_id:2,name:"AtlasMart Park",location:{type:"Point",coordinates:[-73.9712,40.7831]}}, {_id:3,name:"AtlasMart Downtown",location:{type:"Point",coordinates:[-74.0060,40.7128]}}, {_id:4,name:"Warehouse no map"}]);print(s.createIndex({location:"2dsphere"},{name:"geo_location"}));printjson(s.getIndexes());printjson(s.find({location:{$near:{$geometry:{type:"Point",coordinates:[-73.9851,40.7589]},$maxDistance:7000}}},{_id:0,name:1,location:1}).toArray());
text · deterministic geospatial expectations
Expected semantic facts:- GeoJSON Point coordinates are [longitude, latitude], not [latitude, longitude].- $near with GeoJSON requires a 2dsphere index and returns nearest-to-farthest order.- 2d indexes are for legacy coordinate pairs on a flat plane, not GeoJSON objects.- 2dsphere indexes are sparse with respect to the geospatial field; the unmapped warehouse is not indexed by that geo key.- MongoDB 8.3 creates 2dsphere index version 4 by default. A downgrade below FCV 8.3 requires removing version-4 2dsphere indexes first.

4. Deliberately wrong: reverse coordinates and mix 2d with GeoJSON

Reversing latitude/longitude can produce an invalid point or a geographically wrong point. Likewise, a 2d index does not index GeoJSON objects; use 2dsphere for spherical GeoJSON workloads.

javascript · controlled geospatial mismatch demonstrations
const s=db.stores_ch11_l5;try{ printjson(s.find({location:{$near:{$geometry:{type:"Point",coordinates:[40.7589,-73.9851]},$maxDistance:7000}}}).toArray());}catch(e){ printjson({name:e.name,code:e.code,message:e.message}); }try{ db.legacy_geo_ch11_l5.drop(); db.legacy_geo_ch11_l5.insertOne({_id:1,location:{type:"Point",coordinates:[-73.9857,40.7484]}}); db.legacy_geo_ch11_l5.createIndex({location:"2d"});}catch(e){ printjson({name:e.name,code:e.code,message:e.message}); }

5. MongoDB 8.3 compatibility: 2dsphere version 4

MongoDB 8.3 makes 2dsphereIndexVersion:4 the default for newly created 2dsphere indexes. This is not just metadata trivia: the current documentation states that before downgrading FCV below 8.3, version-4 2dsphere indexes must be dropped. Therefore geospatial index inventories belong in upgrade/downgrade runbooks.

Do not override index versions casually

Use the default geospatial index version unless a documented compatibility requirement says otherwise. Pinning an older version without a reason can preserve old behavior and complicate future upgrades.

6. Verification, cleanup, and production judgment

Verification checklist

  • The products collection has exactly one multi-field text index.
  • $text returns scored results and the hint attempt is treated as unsupported.
  • The stores collection uses GeoJSON Point values and a 2dsphere index.
  • The proximity query uses longitude first and meters for GeoJSON maxDistance.
  • The lesson explicitly distinguishes 2d flat-plane legacy coordinates from 2dsphere GeoJSON.
  • The 8.3 default 2dsphere index version and FCV downgrade consequence are recorded.
  • MongoDB Search/Vector Search are described as separate capabilities, not silently substituted into the local lab.

Production judgment. Use built-in text indexes when their basic lexical semantics and self-managed simplicity are sufficient; move to MongoDB Search when analyzers, richer ranking/search features, or multiple search indexes justify the separate subsystem, and to Vector Search for semantic similarity workloads. Use 2dsphere for Earth-like GeoJSON geometry and validate coordinate order/types before indexing. Geospatial and text indexes have substantial storage/write costs and special planner restrictions. Monitor query quality, index size, build time, update latency, and compatibility during upgrades. This completes the specialized-index survey and leads to Chapter 12, where index existence is no longer the question—the focus becomes reading real query plans, candidate selection, plan cache behavior, profiling, and slow-query diagnosis.

bash · cleanup / full reset
docker rm -f atlasmart-mongo-ch11-l5docker volume rm atlasmart-mongo-ch11-l5-data

Check your understanding

  1. How many built-in text indexes can one collection have?
  2. Can a $text query use hint()?
  3. What coordinate order does GeoJSON use for longitude/latitude?
  4. When should you use 2d instead of 2dsphere?
  5. What new 2dsphere compatibility fact matters in MongoDB 8.3?
Review the answers

1. At most one, though that text index can include multiple string fields.

2. No. Text queries do not support hinting an index.

3. [longitude, latitude].

4. For legacy coordinate pairs and flat Euclidean-plane calculations, not GeoJSON spherical workloads.

5. Newly created 2dsphere indexes default to version 4, and downgrading FCV below 8.3 requires removing version-4 2dsphere indexes first.

Authoritative references

Keep knowledge open

Help the academy stay free and grow.

If these tutorials save you time, a small donation supports new lessons, technical review, diagrams, examples, and long-term maintenance.

ETHEthereum / ERC-20 only
0x716c4Ab160C4B66F31a28AE2448BfF68fc3a2ef0

Send only Ethereum or ERC-20 compatible assets to this address.