| 3226 | } |
| 3227 | |
| 3228 | vector<const ExecutorGroup*> AdmissionController::GetExecutorGroupsForQuery( |
| 3229 | const ClusterMembershipMgr::ExecutorGroups& all_groups, |
| 3230 | const TQueryExecRequest& exec_req) { |
| 3231 | vector<const ExecutorGroup*> matching_groups; |
| 3232 | if (scheduler_->IsCoordinatorOnlyQuery(exec_req)) { |
| 3233 | // Coordinator only queries can run regardless of the presence of exec groups. This |
| 3234 | // empty group works as a proxy to schedule coordinator only queries. |
| 3235 | matching_groups.push_back(cluster_membership_mgr_->GetEmptyExecutorGroup()); |
| 3236 | return matching_groups; |
| 3237 | } |
| 3238 | const string& pool_name = exec_req.query_ctx.request_pool; |
| 3239 | string prefix(pool_name + POOL_GROUP_DELIMITER); |
| 3240 | // We search for matching groups before the health check so that we don't fall back to |
| 3241 | // the default group in case there are matching but unhealthy groups. |
| 3242 | for (const auto& it : all_groups) { |
| 3243 | StringPiece name(it.first); |
| 3244 | if (name.starts_with(prefix)) matching_groups.push_back(&it.second); |
| 3245 | } |
| 3246 | if (matching_groups.empty()) { |
| 3247 | auto default_it = all_groups.find(ImpalaServer::DEFAULT_EXECUTOR_GROUP_NAME); |
| 3248 | if (default_it == all_groups.end()) return matching_groups; |
| 3249 | VLOG(3) << "Checking default executor group for pool " << pool_name; |
| 3250 | matching_groups.push_back(&default_it->second); |
| 3251 | } |
| 3252 | // Filter out unhealthy groups. |
| 3253 | auto erase_from = std::remove_if(matching_groups.begin(), matching_groups.end(), |
| 3254 | [](const ExecutorGroup* g) { return !g->IsHealthy(); }); |
| 3255 | matching_groups.erase(erase_from, matching_groups.end()); |
| 3256 | // Sort executor groups by name. |
| 3257 | auto cmp = [](const ExecutorGroup* a, const ExecutorGroup* b) { |
| 3258 | return a->name() < b->name(); |
| 3259 | }; |
| 3260 | sort(matching_groups.begin(), matching_groups.end(), cmp); |
| 3261 | if (FLAGS_balance_queries_across_executor_groups) { |
| 3262 | // Sort executor groups by available memory and slots in descending order, we |
| 3263 | // prioritize executor groups that with more available memory, when their available |
| 3264 | // memory are same we choose the one with more available slots, when their available |
| 3265 | // memory and slots are same we choose on an alphabetical basis. |
| 3266 | auto available_resource_cmp = [this](const ExecutorGroup* a, const ExecutorGroup* b) { |
| 3267 | return GetAvailableMemAndSlots(*a) > GetAvailableMemAndSlots(*b); |
| 3268 | }; |
| 3269 | sort(matching_groups.begin(), matching_groups.end(), available_resource_cmp); |
| 3270 | } |
| 3271 | return matching_groups; |
| 3272 | } |
| 3273 | |
| 3274 | int64_t AdmissionController::GetClusterSize( |
| 3275 | const ClusterMembershipMgr::Snapshot& membership_snapshot) { |
nothing calls this directly
no test coverage detected