Advanced features

Geo search

TNTSearch includes a geographic search feature that lets you find locations within a given distance from a point. It uses the haversine formula to compute distances on the Earth's surface and stores precomputed trigonometric values for fast lookups.


Creating a geo index

Geo indexes are separate from text indexes and use their own indexer and search classes. Your source data must include longitude and latitude columns.

use TeamTNT\TNTSearch\Engines\SqliteEngine;
use TeamTNT\TNTSearch\Indexer\TNTGeoIndexer;

$config = [
    'driver'   => 'sqlite',
    'database' => '/path/to/cities.sqlite',
    'host'     => 'localhost',
    'username' => 'user',
    'password' => 'pass',
    'storage'  => '/path/to/indexes/',
];

$engine   = new SqliteEngine;
$geoIndex = new TNTGeoIndexer($engine);
$geoIndex->loadConfig($config);
$geoIndex->createIndex('cities-geo.index');
$geoIndex->query('SELECT id, longitude, latitude FROM cities;');
$geoIndex->run();

The query must select at least three columns: a primary key (id), longitude, and latitude.


Searching for nearby locations

Use TNTGeoSearch to find locations within a radius:

use TeamTNT\TNTSearch\TNTGeoSearch;

$config = [
    'storage' => '/path/to/indexes/',
];

$geoSearch = new TNTGeoSearch();
$geoSearch->loadConfig($config);
$geoSearch->selectIndex('cities-geo.index');

$currentLocation = [
    'longitude' => 11.576124,
    'latitude'  => 48.137154,
];

$distance = 50; // kilometers

$results = $geoSearch->findNearest($currentLocation, $distance, 10);

Parameters

$geoSearch->findNearest($currentLocation, $distance, $limit = 10);
ParameterDescription
$currentLocationArray with longitude and latitude keys
$distanceSearch radius in kilometers
$limitMaximum number of results to return

Result format

[
    'ids'            => [9389, 9407],           // matching document IDs
    'distances'      => [12.34, 45.67],         // distance in km from the search point
    'hits'           => 2,                       // number of results
    'execution_time' => '1.234 ms'              // search time
]

How it works

The geo indexer precomputes and stores trigonometric values (cos_lat, sin_lat, cos_lng, sin_lng) for each location during indexing. At search time, TNTSearch:

  1. Filters locations using a bounding box (fast rectangular filter)
  2. Computes the actual distance using the haversine formula
  3. Returns only locations within the specified radius
  4. Sorts results by distance (nearest first)

The Earth radius used for calculations is 6,371 km.


Managing the geo index

You can insert and delete locations dynamically:

$index = $geoSearch->getIndex();

// Insert a new location
$index->insert([
    'id'        => 12345,
    'longitude' => 11.576124,
    'latitude'  => 48.137154,
]);

// Delete a location
$index->delete(12345);

Note

Geo search uses a separate index from text search. If you need both full-text search and geographic filtering, you'll need to maintain two indexes and combine results in your application logic.

Previous
Filesystem indexing