Laravel Scout
Use Sigmie as a Laravel Scout driver — index Eloquent models in Elasticsearch with typo tolerance, highlighting, facets, and custom analyzers.
On this page
sigmie/elasticsearch-scout is a Laravel Scout driver. It plugs into Scout’s model lifecycle so writes and deletes flow into Elasticsearch automatically, and Model::search() runs through Sigmie’s search builder.
Install
Install Scout first:
composer require laravel/scout
Publish its config:
php artisan vendor:publish --provider="Laravel\Scout\ScoutServiceProvider"
Install the Sigmie driver:
composer require sigmie/elasticsearch-scout
Set the Scout driver in your .env:
SCOUT_DRIVER=elasticsearch
Publish the Sigmie config (optional, for customization):
php artisan vendor:publish --provider="Sigmie\ElasticsearchScout\ElasticsearchScoutServiceProvider"
This creates config/elasticsearch-scout.php:
return [ 'hosts' => env('ELASTICSEARCH_HOSTS', '127.0.0.1:9200'), 'auth' => [ 'type' => env('ELASTICSEARCH_AUTH_TYPE', 'none'), 'user' => env('ELASTICSEARCH_USER', ''), 'password' => env('ELASTICSEARCH_PASSWORD', ''), 'token' => env('ELASTICSEARCH_TOKEN', ''), 'headers' => [], ], 'guzzle_config' => [ 'allow_redirects' => false, 'http_errors' => false, 'connect_timeout' => 15, ], 'index-settings' => [ 'shards' => env('ELASTICSEARCH_INDEX_SHARDS', 1), 'replicas' => env('ELASTICSEARCH_INDEX_REPLICAS', 2), ],];
Make a model searchable
Use Sigmie’s Searchable trait instead of Laravel Scout’s. They have the same name; the Sigmie version adds the methods Sigmie needs:
use Sigmie\ElasticsearchScout\Searchable;use Sigmie\Mappings\NewProperties; class Movie extends Model{ use Searchable; public function elasticsearchProperties(NewProperties $properties): void { $properties->title('title'); $properties->name('director'); $properties->category('genre'); $properties->date('created_at'); $properties->date('updated_at'); }}
elasticsearchProperties() is required — it defines the index schema for this model.
Build the index
php artisan scout:index "App\Models\Movie"
Import existing rows
php artisan scout:import "App\Models\Movie"
Update the index settings
Unlike other Scout drivers, Sigmie requires the model name when re-syncing:
php artisan scout:sync-index-settings "App\Models\Movie"
This re-applies your elasticsearchProperties() and elasticsearchIndex() configuration.
Customize the search
Define elasticsearchSearch() to use any NewSearch feature:
use Sigmie\Search\NewSearch; class Movie extends Model{ use Searchable; public function elasticsearchProperties(NewProperties $props): void { $props->title('title'); $props->name('director'); $props->category('genre'); } public function elasticsearchSearch(NewSearch $search): void { $search->typoTolerance(); $search->typoTolerantAttributes(['title', 'director']); $search->retrieve(['title', 'director']); $search->fields(['title', 'director']); $search->highlighting( ['title', 'director'], '<span class="font-bold">', '</span>', ); }}
For one-off customization, pass a closure to Model::search():
use Sigmie\Search\NewSearch; Movie::search('Star Wars', function (NewSearch $search) { $search->weight(['title' => 5]);})->get();
Customize index analysis
use Sigmie\Index\NewIndex; class Movie extends Model{ use Searchable; public function elasticsearchProperties(NewProperties $props): void { /* ... */ } public function elasticsearchSearch(NewSearch $search): void { /* ... */ } public function elasticsearchIndex(NewIndex $index): void { $index->tokenizeOnWordBoundaries() ->lowercase() ->trim() ->shards(3) ->replicas(3); }}
If you don’t define elasticsearchIndex(), Sigmie defaults to tokenizing on word boundaries, lowercase, trim.
Accessing hit metadata
Each model returned by Scout carries the raw Elasticsearch hit on $model->hit:
$movie = Movie::search('Star Wars')->get()->first(); $movie->hit['_score']; // 32.343453$movie->hit['highlight']['title'][0]; // <span class="font-bold">Star Wars</span>
Date formatting
Sigmie expects dates in Y-m-d H:i:s.u. Laravel’s default toSearchableArray converts Eloquent timestamps automatically; if you override toSearchableArray(), do the conversion yourself:
public function toSearchableArray(): array{ $array = $this->toArray(); $array['created_at'] = $this->created_at?->format('Y-m-d H:i:s.u'); $array['updated_at'] = $this->updated_at?->format('Y-m-d H:i:s.u'); return $array;}
Or use a different format and tell Sigmie about it:
public function elasticsearchProperties(NewProperties $props): void{ $props->date('created_at')->format('MM/dd/yyyy'); $props->date('updated_at')->format('MM/dd/yyyy');}
Authentication
Basic auth
ELASTICSEARCH_AUTH_TYPE=basicELASTICSEARCH_USER=elasticELASTICSEARCH_PASSWORD=your-password
Bearer token
ELASTICSEARCH_AUTH_TYPE=tokenELASTICSEARCH_TOKEN=your-token-here
Custom headers
If you need API keys or custom auth headers, populate 'headers' in config/elasticsearch-scout.php:
'headers' => [ 'X-App-Token' => env('APP_TOKEN'), 'Authorization' => 'ApiKey ' . env('ELASTICSEARCH_API_KEY'),],
Multiple hosts
ELASTICSEARCH_HOSTS=10.0.0.1:9200,10.0.0.2:9200,10.0.0.3:9200
Guzzle configuration
Tune the underlying HTTP client in config/elasticsearch-scout.php:
'guzzle_config' => [ 'allow_redirects' => false, 'http_errors' => false, 'connect_timeout' => 15, 'timeout' => 30,],
See Connection Setup for the full list of Guzzle options Sigmie understands.
See also
- Search — every option available in
elasticsearchSearch(). - Mappings & Properties — types available in
elasticsearchProperties(). - Indices — analysis options for
elasticsearchIndex(). - Laravel AI SDK — expose Scout-indexed models as AI agent tools.