Installation
composer require nqxcode/zendsearch
Add to config/app.php under providers:
Nqxcode\ZendSearch\ZendSearchServiceProvider::class,
Basic Configuration Publish the config file:
php artisan vendor:publish --provider="Nqxcode\ZendSearch\ZendSearchServiceProvider"
Edit config/zendsearch.php to define your ZendSearch index paths and settings.
First Use Case: Indexing a Model
use Nqxcode\ZendSearch\ZendSearch;
// Index a model (e.g., Article)
ZendSearch::index('articles', [
'id' => $article->id,
'title' => $article->title,
'content' => $article->body,
]);
Searching
$results = ZendSearch::search('articles', 'laravel');
Model Observers for Auto-Indexing
Use Laravel's Observers to index models on saved/created events:
// app/Observers/ArticleObserver.php
public function saved(Article $article)
{
ZendSearch::index('articles', $article->toSearchArray());
}
Batch Indexing For bulk operations (e.g., migrations or imports):
$articles = Article::all();
foreach ($articles as $article) {
ZendSearch::index('articles', $article->toSearchArray());
}
Searching with Filters
$results = ZendSearch::search('articles', 'laravel', [
'filters' => [
'category' => 'tutorial',
'published' => true,
],
]);
Paginated Results
$results = ZendSearch::search('articles', 'laravel', [
'offset' => 0,
'limit' => 10,
]);
published_at in DB, then search text in ZendSearch).$cacheKey = "search:articles:{$query}";
$results = Cache::remember($cacheKey, now()->addHours(1), function () use ($query) {
return ZendSearch::search('articles', $query);
});
Index Paths
index_path in config/zendsearch.php is writable by the web server.storage/zendsearch) may not exist; create them manually:
mkdir -p storage/zendsearch/{articles,data}
Case Sensitivity
ZendSearch::setCaseSensitive(false) globally or per search:
ZendSearch::search('articles', 'Laravel', ['case_sensitive' => false]);
Memory Limits
memory_limit in php.ini.No Full-Text Analyzer
$cleanText = strtolower(preg_replace('/[^a-z0-9\s]/', '', $article->body));
No Native Highlighting
if (!ZendSearch::indexExists('articles')) {
ZendSearch::createIndex('articles');
}
$index = ZendSearch::getIndex('articles');
dump($index->getDocuments());
config/zendsearch.php to log queries:
'debug' => env('ZENDSEARCH_DEBUG', false),
Custom Scoring
Override the default scoring logic by extending the Nqxcode\ZendSearch\Search class:
class CustomSearch extends \Nqxcode\ZendSearch\Search {
protected function scoreDocument($document, $query) {
// Custom scoring logic
}
}
Bind it in the service provider.
Add Fields Dynamically
Extend the Nqxcode\ZendSearch\Index class to support dynamic fields:
$index->addField('dynamic_field', \ZendSearch\Field::TEXT);
Async Indexing Use Laravel Queues to offload indexing:
// Dispatch a job
IndexArticleJob::dispatch($article);
// Job class
public function handle() {
ZendSearch::index('articles', $this->article->toSearchArray());
}
Multi-Index Search Combine results from multiple indexes:
$results = array_merge(
ZendSearch::search('articles', $query),
ZendSearch::search('products', $query)
);
How can I help you explore Laravel packages today?