public static function searchES(array $params = [])
{
extract($params);
$count = config('osu.beatmaps.max', 50);
$offset = max(0, $page - 1) * $count;
$current_user = Auth::user();
$searchParams = ['index' => config('osu.elasticsearch.index'), 'type' => 'beatmaps', 'size' => $count, 'from' => $offset, 'body' => ['sort' => [$sort_field => ['order' => $sort_order]]], 'fields' => 'id'];
$matchParams = [];
$shouldParams = [];
if (presence($genre) !== null) {
$matchParams[] = ['match' => ['genre_id' => (int) $genre]];
}
if (presence($language) !== null) {
$matchParams[] = ['match' => ['language_id' => (int) $language]];
}
if (is_array($extra) && !empty($extra)) {
foreach ($extra as $val) {
switch ($val) {
case 0:
// video
$matchParams[] = ['match' => ['video' => 1]];
break;
case 1:
// storyboard
$matchParams[] = ['match' => ['storyboard' => 1]];
break;
}
}
}
if (presence($query) !== null) {
$matchParams[] = ['query_string' => ['query' => $query]];
}
if (!empty($rank)) {
$klass = presence($mode) !== null ? Score\Best\Model::getClass(intval($mode)) : Score\Best\Combined::class;
$scores = model_pluck($klass::forUser($current_user)->whereIn('rank', $rank), 'beatmapset_id');
$matchParams[] = ['ids' => ['type' => 'beatmaps', 'values' => $scores]];
}
// TODO: This logic probably shouldn't be at the model level... maybe?
if (presence($status) !== null) {
switch ((int) $status) {
case 0:
// Ranked & Approved
$shouldParams[] = [['match' => ['approved' => self::STATES['ranked']]], ['match' => ['approved' => self::STATES['approved']]]];
break;
case 1:
// Approved
$matchParams[] = ['match' => ['approved' => self::STATES['approved']]];
break;
case 8:
// Loved
$matchParams[] = ['match' => ['approved' => self::STATES['loved']]];
break;
case 2:
// Favourites
$favs = model_pluck($current_user->favouriteBeatmapsets(), 'beatmapset_id');
$matchParams[] = ['ids' => ['type' => 'beatmaps', 'values' => $favs]];
break;
case 3:
// Mod Requests
$maps = model_pluck(ModQueue::select(), 'beatmapset_id');
$matchParams[] = ['ids' => ['type' => 'beatmaps', 'values' => $maps]];
$matchParams[] = ['match' => ['approved' => self::STATES['pending']]];
break;
case 4:
// Pending
$shouldParams[] = [['match' => ['approved' => self::STATES['wip']]], ['match' => ['approved' => self::STATES['pending']]]];
break;
case 5:
// Graveyard
$matchParams[] = ['match' => ['approved' => self::STATES['graveyard']]];
break;
case 6:
// My Maps
$maps = model_pluck($current_user->beatmapsets(), 'beatmapset_id');
$matchParams[] = ['ids' => ['type' => 'beatmaps', 'values' => $maps]];
break;
case 7:
// Explicit Any
break;
default:
// null, etc
break;
}
} else {
$matchParams[] = ['range' => ['approved' => ['gte' => self::STATES['pending']]]];
}
if (presence($mode) !== null) {
$matchParams[] = ['match' => ['playmode' => (int) $mode]];
}
if (!empty($matchParams)) {
$searchParams['body']['query']['bool']['must'] = $matchParams;
}
if (!empty($shouldParams)) {
$searchParams['body']['query']['bool']['should'] = $shouldParams;
$searchParams['body']['query']['bool']['minimum_should_match'] = 1;
}
try {
$results = Es::search($searchParams);
$beatmap_ids = array_map(function ($e) {
return $e['_id'];
}, $results['hits']['hits']);
} catch (\Exception $e) {
$beatmap_ids = [];
}
return $beatmap_ids;
}