use of com.b2international.snowowl.core.ServiceProvider in project snow-owl by b2ihealthcare.
the class DefaultResourceURIPathResolver method resolveWithVersion.
@Override
public PathWithVersion resolveWithVersion(ServiceProvider context, ResourceURI uriToResolve, Resource resource) {
if (resource instanceof TerminologyResource) {
TerminologyResource terminologyResource = (TerminologyResource) resource;
if (uriToResolve.isHead()) {
// use code system working branch directly when HEAD is specified
final String workingBranchPath = terminologyResource.getBranchPath() + uriToResolve.getTimestampPart();
return new PathWithVersion(workingBranchPath);
}
// prevent running version search if path does not look like a versionId (single path segment)
final String relativeBranchPath = terminologyResource.getRelativeBranchPath(uriToResolve.getPath());
if (uriToResolve.getPath().contains(Branch.SEPARATOR)) {
final String absoluteBranchPath = relativeBranchPath + uriToResolve.getTimestampPart();
return new PathWithVersion(absoluteBranchPath);
}
VersionSearchRequestBuilder versionSearch = ResourceRequests.prepareSearchVersion().one().filterByResource(terminologyResource.getResourceURI());
if (uriToResolve.isLatest()) {
// fetch the latest resource version if LATEST is specified in the URI
versionSearch.sortBy(SearchResourceRequest.Sort.fieldDesc(VersionDocument.Fields.EFFECTIVE_TIME));
} else {
// try to fetch the path as exact version if not the special LATEST is specified in the URI
versionSearch.filterByVersionId(uriToResolve.getPath());
}
// determine the final branch path, if based on the version search we find a version, then use that, otherwise use the defined path as relative branch of the code system working branch
Versions versions = versionSearch.buildAsync().getRequest().execute(context);
return versions.first().map(v -> {
final String versionBranchPath = v.getBranchPath() + uriToResolve.getTimestampPart();
final ResourceURI versionResourceURI = v.getVersionResourceURI().withTimestampPart(uriToResolve.getTimestampPart());
return new PathWithVersion(versionBranchPath, versionResourceURI);
}).orElseGet(() -> {
if (uriToResolve.isLatest() || !allowBranches) {
throw new BadRequestException("No Resource version is present in '%s'. Explicit '%s' can be used to retrieve the latest work in progress version of the Resource.", terminologyResource.getId(), terminologyResource.getId());
}
return new PathWithVersion(relativeBranchPath);
});
}
return new PathWithVersion("");
}
use of com.b2international.snowowl.core.ServiceProvider in project snow-owl by b2ihealthcare.
the class FhirValidateCodeRequest method doExecute.
@Override
public ValidateCodeResult doExecute(ServiceProvider context, CodeSystem codeSystem) {
Set<Coding> codings = collectCodingsToValidate(request);
Map<String, Coding> codingsById = codings.stream().collect(Collectors.toMap(Coding::getCodeValue, c -> c));
// extract locales from the request
Map<String, Concept> conceptsById = CodeSystemRequests.prepareSearchConcepts().setLimit(codingsById.keySet().size()).filterByCodeSystemUri(codeSystem.getResourceURI()).filterByIds(codingsById.keySet()).setLocales(extractLocales(request.getDisplayLanguage())).buildAsync().execute(context).stream().collect(Collectors.toMap(Concept::getId, c -> c));
// check if both Maps have the same keys and report if not
Set<String> missingConceptIds = Sets.difference(codingsById.keySet(), conceptsById.keySet());
if (!missingConceptIds.isEmpty()) {
return ValidateCodeResult.builder().result(false).message(String.format("Could not find code%s '%s'.", missingConceptIds.size() == 1 ? "" : "s", ImmutableSortedSet.copyOf(missingConceptIds))).build();
}
// XXX it would be great to have support for multiple messages/validation results in a single request
for (String id : codingsById.keySet()) {
// check display if provided
Coding providedCoding = codingsById.get(id);
if (providedCoding.getDisplay() != null) {
Concept concept = conceptsById.get(id);
if (!providedCoding.getDisplay().equals(concept.getTerm())) {
return ValidateCodeResult.builder().result(false).display(concept.getTerm()).message(String.format("Incorrect display '%s' for code '%s'.", providedCoding.getDisplay(), providedCoding.getCodeValue())).build();
}
}
}
return ValidateCodeResult.builder().result(true).build();
}
use of com.b2international.snowowl.core.ServiceProvider in project snow-owl by b2ihealthcare.
the class ApiRequestHandler method handle.
@Override
public final void handle(IMessage message) {
try {
final Request<ServiceProvider, ?> req = message.body(Request.class, classLoader);
final ResponseHeaders responseHeaders = new ResponseHeaders();
final ServiceProvider executionContext = context.inject().bind(RequestHeaders.class, new RequestHeaders(message.headers())).bind(ResponseHeaders.class, responseHeaders).build();
// monitor each request execution
final Object body = new MonitoredRequest<>(// authorize each request execution
new AuthorizedRequest<>(// rate limit all requests
new RateLimitingRequest<>(// actual request
req))).execute(executionContext);
if (body == null) {
LoggerFactory.getLogger(ApiRequestHandler.class).error("No response was returned from request: " + req.getClass());
}
message.reply(body, responseHeaders.headers());
} catch (WrappedException e) {
message.fail(e.getCause());
} catch (ApiException e) {
message.fail(e);
} catch (Throwable e) {
LoggerFactory.getLogger(ApiRequestHandler.class).error("Unexpected error when executing request:", e);
message.fail(e);
}
}
use of com.b2international.snowowl.core.ServiceProvider in project snow-owl by b2ihealthcare.
the class BaseResourceSearchRequest method addSecurityFilter.
/**
* Configures security filters to allow access to certain resources only. This method is no-op if the given {@link ServiceProvider context}'s {@link User} is an administrator or has read access to everything.
*
* @param context - the context where user information will be extracted
* @param queryBuilder - the query builder to append the clauses to
*/
protected final void addSecurityFilter(ServiceProvider context, ExpressionBuilder queryBuilder) {
final User user = context.service(User.class);
if (user.isAdministrator() || user.hasPermission(Permission.requireAll(Permission.OPERATION_BROWSE, Permission.ALL))) {
return;
}
// extract read permissions
final List<Permission> readPermissions = user.getPermissions().stream().filter(p -> Permission.ALL.equals(p.getOperation()) || Permission.OPERATION_BROWSE.equals(p.getOperation())).collect(Collectors.toList());
final Set<String> exactResourceIds = readPermissions.stream().flatMap(p -> p.getResources().stream()).filter(resource -> !resource.endsWith("*")).collect(Collectors.toSet());
final Set<String> resourceIdPrefixes = readPermissions.stream().flatMap(p -> p.getResources().stream()).filter(resource -> resource.endsWith("*")).map(resource -> resource.substring(0, resource.length() - 1)).collect(Collectors.toSet());
if (!exactResourceIds.isEmpty() || !resourceIdPrefixes.isEmpty()) {
context.log().info("Restricting user '{}' to resources exact: '{}', prefix: '{}'.", user.getUsername(), ImmutableSortedSet.copyOf(exactResourceIds), ImmutableSortedSet.copyOf(resourceIdPrefixes));
ExpressionBuilder bool = Expressions.builder();
// the permissions give access to either
if (!exactResourceIds.isEmpty()) {
// explicit IDs
bool.should(ResourceDocument.Expressions.ids(exactResourceIds));
// or the permitted resources are bundles which give access to all resources within it (recursively)
bool.should(ResourceDocument.Expressions.bundleIds(exactResourceIds));
bool.should(ResourceDocument.Expressions.bundleAncestorIds(exactResourceIds));
}
if (!resourceIdPrefixes.isEmpty()) {
// partial IDs, prefixes
bool.should(ResourceDocument.Expressions.idPrefixes(resourceIdPrefixes));
// or the permitted resources are bundle ID prefixes which give access to all resources within it (recursively)
bool.should(ResourceDocument.Expressions.bundleIdPrefixes(resourceIdPrefixes));
bool.should(ResourceDocument.Expressions.bundleAncestorIdPrefixes(resourceIdPrefixes));
}
queryBuilder.filter(bool.build());
} else {
throw new NoResultException();
}
}
use of com.b2international.snowowl.core.ServiceProvider in project snow-owl by b2ihealthcare.
the class ValueSetMemberSearchRequest method doExecute.
@Override
protected ValueSetMembers doExecute(ServiceProvider context) throws IOException {
final int limit = limit();
Options options = Options.builder().putAll(options()).put(MemberSearchRequestEvaluator.OptionKey.AFTER, searchAfter()).put(MemberSearchRequestEvaluator.OptionKey.LIMIT, limit).put(MemberSearchRequestEvaluator.OptionKey.LOCALES, locales()).put(SearchResourceRequest.OptionKey.SORT_BY, sortBy()).build();
// extract all ValueSetMemberSearchRequestEvaluator from all connected toolings and determine which ones can handle this request
List<ValueSetMembers> evaluatedMembers = context.service(RepositoryManager.class).repositories().stream().flatMap(repository -> {
ValueSetMemberSearchRequestEvaluator evaluator = repository.service(ValueSetMemberSearchRequestEvaluator.class);
Set<ResourceURI> targets = evaluator.evaluateSearchTargetResources(context, options);
return targets.stream().map(uri -> {
return evaluator.evaluate(uri, context, options);
});
}).collect(Collectors.toList());
// calculate grand total
int total = 0;
for (ValueSetMembers evaluatedMember : evaluatedMembers) {
total += evaluatedMember.getTotal();
}
return new ValueSetMembers(// TODO add manual sorting here if multiple resources have been fetched
evaluatedMembers.stream().flatMap(ValueSetMembers::stream).limit(limit).collect(Collectors.toList()), null, /* not supported across resources, TODO support it when a single ValueSet is being fetched */
limit, total);
}
Aggregations