Search in sources :

Example 11 with RequestContext

use of org.hypertrace.core.grpcutils.context.RequestContext 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);
        }
    }
}
Also used : ByIdRequest(org.hypertrace.entity.data.service.v1.ByIdRequest) ServiceException(com.google.protobuf.ServiceException) LoggerFactory(org.slf4j.LoggerFactory) Channel(io.grpc.Channel) EntityTypeClient(org.hypertrace.entity.type.service.rxclient.EntityTypeClient) StreamObserver(io.grpc.stub.StreamObserver) Map(java.util.Map) Objects.isNull(java.util.Objects.isNull) ENRICHED_ENTITIES_COLLECTION(org.hypertrace.entity.service.constants.EntityCollectionConstants.ENRICHED_ENTITIES_COLLECTION) DocStoreConverter(org.hypertrace.entity.service.util.DocStoreConverter) InvalidRequestException(org.hypertrace.entity.service.exception.InvalidRequestException) StringUtils(org.hypertrace.entity.service.util.StringUtils) Streams(com.google.common.collect.Streams) Empty(org.hypertrace.entity.data.service.v1.Empty) Collectors(java.util.stream.Collectors) List(java.util.List) Stream(java.util.stream.Stream) EntityRelationship(org.hypertrace.entity.data.service.v1.EntityRelationship) EntityRelationships(org.hypertrace.entity.data.service.v1.EntityRelationships) MergeAndUpsertEntityRequest(org.hypertrace.entity.data.service.v1.MergeAndUpsertEntityRequest) Optional(java.util.Optional) EntityChangeEventGenerator(org.hypertrace.entity.service.change.event.api.EntityChangeEventGenerator) EnrichedEntity(org.hypertrace.entity.data.service.v1.EnrichedEntity) Builder(org.hypertrace.entity.data.service.v1.Entity.Builder) Document(org.hypertrace.core.documentstore.Document) RequestContext(org.hypertrace.core.grpcutils.context.RequestContext) ByTypeAndIdentifyingAttributes(org.hypertrace.entity.data.service.v1.ByTypeAndIdentifyingAttributes) DocStoreJsonFormat(org.hypertrace.entity.service.util.DocStoreJsonFormat) Descriptors(com.google.protobuf.Descriptors) Filter(org.hypertrace.core.documentstore.Filter) HashMap(java.util.HashMap) Function(java.util.function.Function) Collection(org.hypertrace.core.documentstore.Collection) Entities(org.hypertrace.entity.data.service.v1.Entities) ArrayList(java.util.ArrayList) Datastore(org.hypertrace.core.documentstore.Datastore) Key(org.hypertrace.core.documentstore.Key) EntityServiceConstants(org.hypertrace.entity.service.constants.EntityServiceConstants) Entity(org.hypertrace.entity.data.service.v1.Entity) EntityDataServiceImplBase(org.hypertrace.entity.data.service.v1.EntityDataServiceGrpc.EntityDataServiceImplBase) Logger(org.slf4j.Logger) Iterator(java.util.Iterator) JSONDocument(org.hypertrace.core.documentstore.JSONDocument) IOException(java.io.IOException) ENTITY_RELATIONSHIPS_COLLECTION(org.hypertrace.entity.service.constants.EntityCollectionConstants.ENTITY_RELATIONSHIPS_COLLECTION) EnrichedEntities(org.hypertrace.entity.data.service.v1.EnrichedEntities) Query(org.hypertrace.entity.data.service.v1.Query) RAW_ENTITIES_COLLECTION(org.hypertrace.entity.service.constants.EntityCollectionConstants.RAW_ENTITIES_COLLECTION) Message(com.google.protobuf.Message) GeneratedMessageV3(com.google.protobuf.GeneratedMessageV3) MergeAndUpsertEntityResponse(org.hypertrace.entity.data.service.v1.MergeAndUpsertEntityResponse) Collections(java.util.Collections) RelationshipsQuery(org.hypertrace.entity.data.service.v1.RelationshipsQuery) EnrichedEntity(org.hypertrace.entity.data.service.v1.EnrichedEntity) Entity(org.hypertrace.entity.data.service.v1.Entity) ServiceException(com.google.protobuf.ServiceException) List(java.util.List) ArrayList(java.util.ArrayList) RequestContext(org.hypertrace.core.grpcutils.context.RequestContext) IOException(java.io.IOException)

Example 12 with RequestContext

use of org.hypertrace.core.grpcutils.context.RequestContext in project entity-service by hypertrace.

the class EntityDataCachingClient method createOrUpdateEntityEventually.

@Override
public void createOrUpdateEntityEventually(RequestContext requestContext, Entity entity, UpsertCondition condition, Duration maximumUpsertDelay) {
    EntityKey entityKey = new EntityKey(requestContext, entity);
    // Don't allow other update processing until finished
    Lock lock = this.pendingUpdateStripedLock.get(entityKey);
    try {
        lock.lock();
        this.pendingEntityUpdates.computeIfAbsent(entityKey, unused -> new PendingEntityUpdate()).addNewUpdate(entityKey, condition, maximumUpsertDelay);
    } finally {
        lock.unlock();
    }
}
Also used : CallCredentials(io.grpc.CallCredentials) RequestContext(org.hypertrace.core.grpcutils.context.RequestContext) Single(io.reactivex.rxjava3.core.Single) LoadingCache(com.google.common.cache.LoadingCache) Channel(io.grpc.Channel) ConcurrentMap(java.util.concurrent.ConcurrentMap) Functions(io.reactivex.rxjava3.internal.functions.Functions) Duration(java.time.Duration) Entity(org.hypertrace.entity.data.service.v1.Entity) Objects.isNull(java.util.Objects.isNull) Nonnull(javax.annotation.Nonnull) Striped(com.google.common.util.concurrent.Striped) ConcurrentHashMap(java.util.concurrent.ConcurrentHashMap) Completable(io.reactivex.rxjava3.core.Completable) UpsertCondition(org.hypertrace.entity.data.service.v1.MergeAndUpsertEntityRequest.UpsertCondition) Instant(java.time.Instant) CacheLoader(com.google.common.cache.CacheLoader) TimeUnit(java.util.concurrent.TimeUnit) EntityDataServiceStub(org.hypertrace.entity.data.service.v1.EntityDataServiceGrpc.EntityDataServiceStub) Lock(java.util.concurrent.locks.Lock) Slf4j(lombok.extern.slf4j.Slf4j) EntityDataServiceGrpc(org.hypertrace.entity.data.service.v1.EntityDataServiceGrpc) Disposable(io.reactivex.rxjava3.disposables.Disposable) MergeAndUpsertEntityRequest(org.hypertrace.entity.data.service.v1.MergeAndUpsertEntityRequest) Clock(java.time.Clock) Optional(java.util.Optional) MergeAndUpsertEntityResponse(org.hypertrace.entity.data.service.v1.MergeAndUpsertEntityResponse) CacheBuilder(com.google.common.cache.CacheBuilder) Objects.nonNull(java.util.Objects.nonNull) Lock(java.util.concurrent.locks.Lock)

Example 13 with RequestContext

use of org.hypertrace.core.grpcutils.context.RequestContext in project entity-service by hypertrace.

the class EntityKeyTest method matchesSameIdentifyingAttributesSameRequestContext.

@Test
void matchesSameIdentifyingAttributesSameRequestContext() {
    RequestContext matchingContext = RequestContext.forTenantId(TENANT_ID_1);
    // Change some attributes to make sure it's not a deep compare
    Entity matchingEntity = this.entityV1.toBuilder().clearAttributes().build();
    assertEquals(new EntityKey(REQUEST_CONTEXT_1, this.entityV1), new EntityKey(matchingContext, matchingEntity));
}
Also used : Entity(org.hypertrace.entity.data.service.v1.Entity) RequestContext(org.hypertrace.core.grpcutils.context.RequestContext) Test(org.junit.jupiter.api.Test)

Example 14 with RequestContext

use of org.hypertrace.core.grpcutils.context.RequestContext in project entity-service by hypertrace.

the class FromClauseConverterTest method testConvert1.

@Test
void testConvert1() throws Exception {
    final ColumnIdentifier col1 = ColumnIdentifier.newBuilder().setColumnName("col1").build();
    final ColumnIdentifier col2 = ColumnIdentifier.newBuilder().setColumnName("col2").build();
    final List<Expression> expressions = List.of(Expression.newBuilder().setColumnIdentifier(col1).build(), Expression.newBuilder().setColumnIdentifier(col2).build());
    final RequestContext requestContext = new RequestContext();
    when(mockEntityAttributeMapping.isMultiValued(eq(requestContext), eq("col1"))).thenReturn(false);
    when(mockEntityAttributeMapping.isMultiValued(eq(requestContext), eq("col2"))).thenReturn(true);
    when(mockIdentifierExpressionConverter.convert(col2, requestContext)).thenReturn(IdentifierExpression.of("name"));
    final List<FromTypeExpression> expected = List.of(UnnestExpression.of(IdentifierExpression.of("name"), false));
    final List<FromTypeExpression> actual = fromClauseConverter.convert(expressions, requestContext);
    assertEquals(expected, actual);
}
Also used : FromTypeExpression(org.hypertrace.core.documentstore.expression.type.FromTypeExpression) IdentifierExpression(org.hypertrace.core.documentstore.expression.impl.IdentifierExpression) FromTypeExpression(org.hypertrace.core.documentstore.expression.type.FromTypeExpression) UnnestExpression(org.hypertrace.core.documentstore.expression.impl.UnnestExpression) Expression(org.hypertrace.entity.query.service.v1.Expression) ColumnIdentifier(org.hypertrace.entity.query.service.v1.ColumnIdentifier) RequestContext(org.hypertrace.core.grpcutils.context.RequestContext) Test(org.junit.jupiter.api.Test)

Example 15 with RequestContext

use of org.hypertrace.core.grpcutils.context.RequestContext in project entity-service by hypertrace.

the class FromClauseConverterTest method testConvert1_ConverterThrowsConversionException.

@Test
void testConvert1_ConverterThrowsConversionException() {
    final ColumnIdentifier col1 = ColumnIdentifier.newBuilder().setColumnName("col1").build();
    final ColumnIdentifier col2 = ColumnIdentifier.newBuilder().setColumnName("col2").build();
    final List<Expression> expressions = List.of(Expression.newBuilder().setColumnIdentifier(col1).build(), Expression.newBuilder().setFunction(Function.newBuilder().addArguments(Expression.newBuilder().setColumnIdentifier(col2))).build());
    final RequestContext requestContext = new RequestContext();
    assertThrows(ConversionException.class, () -> fromClauseConverter.convert(expressions, requestContext));
}
Also used : IdentifierExpression(org.hypertrace.core.documentstore.expression.impl.IdentifierExpression) FromTypeExpression(org.hypertrace.core.documentstore.expression.type.FromTypeExpression) UnnestExpression(org.hypertrace.core.documentstore.expression.impl.UnnestExpression) Expression(org.hypertrace.entity.query.service.v1.Expression) ColumnIdentifier(org.hypertrace.entity.query.service.v1.ColumnIdentifier) RequestContext(org.hypertrace.core.grpcutils.context.RequestContext) Test(org.junit.jupiter.api.Test)

Aggregations

RequestContext (org.hypertrace.core.grpcutils.context.RequestContext)17 Test (org.junit.jupiter.api.Test)9 Entity (org.hypertrace.entity.data.service.v1.Entity)8 ServiceException (com.google.protobuf.ServiceException)6 Document (org.hypertrace.core.documentstore.Document)5 JSONDocument (org.hypertrace.core.documentstore.JSONDocument)5 Optional (java.util.Optional)4 Query (org.hypertrace.entity.data.service.v1.Query)4 ConversionException (org.hypertrace.entity.query.service.converter.ConversionException)4 ColumnIdentifier (org.hypertrace.entity.query.service.v1.ColumnIdentifier)4 EntityQueryRequest (org.hypertrace.entity.query.service.v1.EntityQueryRequest)4 StreamObserver (io.grpc.stub.StreamObserver)3 List (java.util.List)3 Map (java.util.Map)3 Objects.isNull (java.util.Objects.isNull)3 Collectors (java.util.stream.Collectors)3 Collection (org.hypertrace.core.documentstore.Collection)3 IdentifierExpression (org.hypertrace.core.documentstore.expression.impl.IdentifierExpression)3 EntityUpdateInfo (org.hypertrace.entity.query.service.v1.BulkEntityUpdateRequest.EntityUpdateInfo)3 Expression (org.hypertrace.entity.query.service.v1.Expression)3