use of org.hypertrace.entity.data.service.v1.MergeAndUpsertEntityRequest in project entity-service by hypertrace.
the class EntityDataServiceImpl method mergeAndUpsertEntity.
@Override
public void mergeAndUpsertEntity(MergeAndUpsertEntityRequest request, StreamObserver<MergeAndUpsertEntityResponse> responseObserver) {
RequestContext requestContext = RequestContext.CURRENT.get();
String tenantId = requestContext.getTenantId().orElse(null);
if (tenantId == null) {
responseObserver.onError(new ServiceException("Tenant id is missing in the request."));
return;
}
Entity receivedEntity = this.entityNormalizer.normalize(tenantId, request.getEntity());
Optional<Entity> existingEntity = getExistingEntity(tenantId, receivedEntity.getEntityType(), receivedEntity.getEntityId());
boolean rejectUpsertForConditionMismatch = existingEntity.map(entity -> !this.upsertConditionMatcher.matches(entity, request.getUpsertCondition())).orElse(false);
if (rejectUpsertForConditionMismatch) {
// There's an existing entity and the update doesn't meet the condition, return existing
responseObserver.onNext(MergeAndUpsertEntityResponse.newBuilder().setEntity(existingEntity.get()).build());
responseObserver.onCompleted();
} else {
// There's either a new entity or a valid update to upsert
Entity entityToUpsert = existingEntity.map(Entity::toBuilder).map(Entity.Builder::clearCreatedTime).map(builder -> builder.mergeFrom(receivedEntity)).map(Builder::build).orElse(receivedEntity);
try {
Entity upsertedEntity = this.upsertEntity(tenantId, entityToUpsert);
responseObserver.onNext(MergeAndUpsertEntityResponse.newBuilder().setEntity(upsertedEntity).build());
responseObserver.onCompleted();
entityChangeEventGenerator.sendChangeNotification(requestContext, existingEntity.map(List::of).orElse(Collections.emptyList()), List.of(upsertedEntity));
} catch (IOException e) {
responseObserver.onError(e);
}
}
}
Aggregations