options(['sort' => …]). * Must match keys in Artwork::toSearchableArray(). */ private const SORTABLE_ATTRIBUTES = [ 'created_at', 'trending_score_24h', 'trending_score_7d', 'favorites_count', 'downloads_count', 'awards_received_count', 'views', 'likes', 'downloads', ]; /** * Fields used in filter expressions (AND category = "…" etc.). */ private const FILTERABLE_ATTRIBUTES = [ 'id', 'is_public', 'is_approved', 'category', 'content_type', 'tags', 'author_id', 'orientation', 'resolution', ]; public function handle(): int { $prefix = config('scout.prefix', ''); $indexName = $prefix . (string) $this->option('index'); /** @var MeilisearchClient $client */ $client = app(MeilisearchClient::class); $index = $client->index($indexName); $this->info("Configuring Meilisearch index: {$indexName}"); // ── Sortable attributes ─────────────────────────────────────────────── $this->line(' → Updating sortableAttributes…'); $task = $index->updateSortableAttributes(self::SORTABLE_ATTRIBUTES); $this->line(" Task uid: {$task['taskUid']}"); // ── Filterable attributes ───────────────────────────────────────────── $this->line(' → Updating filterableAttributes…'); $task2 = $index->updateFilterableAttributes(self::FILTERABLE_ATTRIBUTES); $this->line(" Task uid: {$task2['taskUid']}"); $this->info('Done. Meilisearch will process these tasks asynchronously.'); $this->warn('Re-index artworks if sortable attributes changed: php artisan artworks:search-rebuild'); return self::SUCCESS; } }