use of io.trino.plugin.resourcegroups.ManagerSpec in project trino by trinodb.
the class DbResourceGroupConfigurationManager method load.
@VisibleForTesting
public synchronized void load() {
try {
Map.Entry<ManagerSpec, Map<ResourceGroupIdTemplate, ResourceGroupSpec>> specsFromDb = buildSpecsFromDb();
ManagerSpec managerSpec = specsFromDb.getKey();
Map<ResourceGroupIdTemplate, ResourceGroupSpec> resourceGroupSpecs = specsFromDb.getValue();
Set<ResourceGroupIdTemplate> changedSpecs = new HashSet<>();
Set<ResourceGroupIdTemplate> deletedSpecs = Sets.difference(this.resourceGroupSpecs.keySet(), resourceGroupSpecs.keySet());
for (Map.Entry<ResourceGroupIdTemplate, ResourceGroupSpec> entry : resourceGroupSpecs.entrySet()) {
if (!entry.getValue().sameConfig(this.resourceGroupSpecs.get(entry.getKey()))) {
changedSpecs.add(entry.getKey());
}
}
this.resourceGroupSpecs = resourceGroupSpecs;
this.cpuQuotaPeriod.set(managerSpec.getCpuQuotaPeriod());
this.rootGroups.set(managerSpec.getRootGroups());
List<ResourceGroupSelector> selectors = buildSelectors(managerSpec);
if (exactMatchSelectorEnabled) {
ImmutableList.Builder<ResourceGroupSelector> builder = ImmutableList.builder();
builder.add(new DbSourceExactMatchSelector(environment, dao));
builder.addAll(selectors);
this.selectors.set(builder.build());
} else {
this.selectors.set(selectors);
}
configureChangedGroups(changedSpecs);
disableDeletedGroups(deletedSpecs);
if (lastRefresh.get() > 0) {
for (ResourceGroupIdTemplate deleted : deletedSpecs) {
log.info("Resource group spec deleted %s", deleted);
}
for (ResourceGroupIdTemplate changed : changedSpecs) {
log.info("Resource group spec %s changed to %s", changed, resourceGroupSpecs.get(changed));
}
} else {
log.info("Loaded %s selectors and %s resource groups from database", this.selectors.get().size(), this.resourceGroupSpecs.size());
}
lastRefresh.set(System.nanoTime());
} catch (Throwable e) {
if (succinctNanos(System.nanoTime() - lastRefresh.get()).compareTo(maxRefreshInterval) > 0) {
lastRefresh.set(0);
}
refreshFailures.update(1);
log.error(e, "Error loading configuration from db");
}
}
use of io.trino.plugin.resourcegroups.ManagerSpec in project trino by trinodb.
the class DbResourceGroupConfigurationManager method buildSpecsFromDb.
private synchronized Map.Entry<ManagerSpec, Map<ResourceGroupIdTemplate, ResourceGroupSpec>> buildSpecsFromDb() {
// New resource group spec map
Map<ResourceGroupIdTemplate, ResourceGroupSpec> resourceGroupSpecs = new HashMap<>();
// Set of root group db ids
Set<Long> rootGroupIds = new HashSet<>();
// Map of id from db to resource group spec
Map<Long, ResourceGroupSpec> resourceGroupSpecMap = new HashMap<>();
// Map of id from db to resource group template id
Map<Long, ResourceGroupIdTemplate> resourceGroupIdTemplateMap = new HashMap<>();
// Map of id from db to resource group spec builder
Map<Long, ResourceGroupSpecBuilder> recordMap = new HashMap<>();
// Map of subgroup id's not yet built
Map<Long, Set<Long>> subGroupIdsToBuild = new HashMap<>();
populateFromDbHelper(recordMap, rootGroupIds, resourceGroupIdTemplateMap, subGroupIdsToBuild);
// Build up resource group specs from leaf to root
for (LinkedList<Long> queue = new LinkedList<>(rootGroupIds); !queue.isEmpty(); ) {
Long id = queue.pollFirst();
resourceGroupIdTemplateMap.computeIfAbsent(id, k -> {
ResourceGroupSpecBuilder builder = recordMap.get(id);
return ResourceGroupIdTemplate.forSubGroupNamed(resourceGroupIdTemplateMap.get(builder.getParentId().get()), builder.getNameTemplate().toString());
});
Set<Long> childrenToBuild = subGroupIdsToBuild.getOrDefault(id, ImmutableSet.of());
// Add to resource group specs if no more child resource groups are left to build
if (childrenToBuild.isEmpty()) {
ResourceGroupSpecBuilder builder = recordMap.get(id);
ResourceGroupSpec resourceGroupSpec = builder.build();
resourceGroupSpecMap.put(id, resourceGroupSpec);
// Add newly built spec to spec map
resourceGroupSpecs.put(resourceGroupIdTemplateMap.get(id), resourceGroupSpec);
// Add this resource group spec to parent subgroups and remove id from subgroup ids to build
builder.getParentId().ifPresent(parentId -> {
recordMap.get(parentId).addSubGroup(resourceGroupSpec);
subGroupIdsToBuild.get(parentId).remove(id);
});
} else {
// Add this group back to queue since it still has subgroups to build
queue.addFirst(id);
// Add this group's subgroups to the queue so that when this id is dequeued again childrenToBuild will be empty
queue.addAll(0, childrenToBuild);
}
}
// Specs are built from db records, validate and return manager spec
List<ResourceGroupSpec> rootGroups = rootGroupIds.stream().map(resourceGroupSpecMap::get).collect(Collectors.toList());
List<SelectorSpec> selectors = dao.getSelectors(environment).stream().map(selectorRecord -> new SelectorSpec(selectorRecord.getUserRegex(), selectorRecord.getUserGroupRegex(), selectorRecord.getSourceRegex(), selectorRecord.getQueryType(), selectorRecord.getClientTags(), selectorRecord.getSelectorResourceEstimate(), resourceGroupIdTemplateMap.get(selectorRecord.getResourceGroupId()))).collect(Collectors.toList());
ManagerSpec managerSpec = new ManagerSpec(rootGroups, selectors, getCpuQuotaPeriodFromDb());
validateRootGroups(managerSpec);
return new AbstractMap.SimpleImmutableEntry<>(managerSpec, resourceGroupSpecs);
}
Aggregations