protected override async Task <IReadOnlyCollection <TReadModel> > Process(EntityIdentifiersQuery <string, TReadModel> request, CancellationToken cancellationToken) { if (request is null) { throw new System.ArgumentNullException(nameof(request)); } var keys = new HashSet <string>(); foreach (var requestId in request.Ids) { if (CosmosKey.TryDecode(requestId, out var id, out PartitionKey partitionKey)) { keys.Add(id); } } var query = await Repository .GetQueryableAsync() .ConfigureAwait(false); var results = await query .Where(p => keys.Contains(p.Id)) .ToListAsync(cancellationToken) .ConfigureAwait(false); return(Mapper.Map <IList <TEntity>, IReadOnlyCollection <TReadModel> >(results)); }
public void TryDecodeTests(string cosmosKey, bool expectedResult, string expectedId, PartitionKey expectedPartitionKey) { var result = CosmosKey.TryDecode(cosmosKey, out var id, out var partitionKey); result.Should().Be(expectedResult); id.Should().Be(expectedId); partitionKey.Should().Be(expectedPartitionKey); }
protected override async Task <TReadModel> Process(EntityUpsertCommand <string, TUpdateModel, TReadModel> request, CancellationToken cancellationToken) { if (request is null) { throw new ArgumentNullException(nameof(request)); } if (!CosmosKey.TryDecode(request.Id, out var id, out var partitionKey)) { throw new InvalidOperationException("Invalid Cosmos Key format"); } var entity = await Repository .FindAsync(id, partitionKey, cancellationToken) .ConfigureAwait(false); // create entity if not found if (entity == null) { entity = new TEntity { Id = id }; // apply create metadata if (entity is ITrackCreated createdModel) { createdModel.Created = request.Activated; createdModel.CreatedBy = request.ActivatedBy; } } // copy updates from model to entity Mapper.Map(request.Model, entity); // apply update metadata if (entity is ITrackUpdated updateEntity) { updateEntity.Updated = request.Activated; updateEntity.UpdatedBy = request.ActivatedBy; } // save updates var savedEntity = await Repository .UpdateAsync(entity, cancellationToken) .ConfigureAwait(false); // return read model var model = Mapper.Map <TReadModel>(savedEntity); return(model); }
protected override async Task <TReadModel> Process(EntityDeleteCommand <string, TReadModel> request, CancellationToken cancellationToken) { if (request is null) { throw new ArgumentNullException(nameof(request)); } if (!CosmosKey.TryDecode(request.Id, out var id, out var partitionKey)) { throw new InvalidOperationException("Invalid Cosmos Key format"); } var entity = await Repository .FindAsync(id, partitionKey, cancellationToken) .ConfigureAwait(false); if (entity == null) { return(default !);
public async Task Upsert() { var cosmosKey = CosmosKey.Encode(ObjectId.GenerateNewId().ToString(), Constants.TenantConstants.Test.Id); var mediator = ServiceProvider.GetService <IMediator>(); mediator.Should().NotBeNull(); var mapper = ServiceProvider.GetService <IMapper>(); mapper.Should().NotBeNull(); // Update Entity var updateModel = Generator.Default.Single <TaskUpdateModel>(); updateModel.Title = "Upsert Test"; updateModel.Description = "Insert " + DateTime.Now.Ticks; updateModel.StatusId = StatusConstants.NotStarted.Id; updateModel.TenantId = TenantConstants.Test.Id; var upsertCommandNew = new EntityUpsertCommand <string, TaskUpdateModel, TaskReadModel>(MockPrincipal.Default, cosmosKey, updateModel); var upsertResultNew = await mediator.Send(upsertCommandNew).ConfigureAwait(false); upsertResultNew.Should().NotBeNull(); // Get Entity by Key var identifierQuery = new EntityIdentifierQuery <string, TaskReadModel>(MockPrincipal.Default, cosmosKey); var identifierResult = await mediator.Send(identifierQuery).ConfigureAwait(false); identifierResult.Should().NotBeNull(); identifierResult.Title.Should().Be(updateModel.Title); // update model updateModel.Description = "Update " + DateTime.Now.Ticks; // Upsert again, should be update var upsertCommandUpdate = new EntityUpsertCommand <string, TaskUpdateModel, TaskReadModel>(MockPrincipal.Default, cosmosKey, updateModel); var upsertResultUpdate = await mediator.Send(upsertCommandUpdate).ConfigureAwait(false); upsertResultUpdate.Should().NotBeNull(); upsertResultUpdate.Description.Should().NotBe(upsertResultNew.Description); }
protected override async Task <TReadModel> Process(EntityIdentifierQuery <string, TReadModel> request, CancellationToken cancellationToken) { if (request is null) { throw new ArgumentNullException(nameof(request)); } if (!CosmosKey.TryDecode(request.Id, out var id, out var partitionKey)) { throw new InvalidOperationException("Invalid Cosmos Key format"); } var entity = await Repository .FindAsync(id, partitionKey, cancellationToken) .ConfigureAwait(false); // convert deleted entity to read model var model = Mapper.Map <TReadModel>(entity); return(model); }
public async Task Upsert() { var id = ObjectId.GenerateNewId().ToString(); var key = CosmosKey.Encode(id, id); var mediator = ServiceProvider.GetService <IMediator>(); mediator.Should().NotBeNull(); var mapper = ServiceProvider.GetService <IMapper>(); mapper.Should().NotBeNull(); // Update Entity var updateModel = Generator.Default.Single <AuditUpdateModel>(); updateModel.Username = "******"; updateModel.Content = "Insert " + DateTime.Now.Ticks; var upsertCommandNew = new EntityUpsertCommand <string, AuditUpdateModel, AuditReadModel>(MockPrincipal.Default, key, updateModel); var upsertResultNew = await mediator.Send(upsertCommandNew).ConfigureAwait(false); upsertResultNew.Should().NotBeNull(); // Get Entity by Key var identifierQuery = new EntityIdentifierQuery <string, AuditReadModel>(MockPrincipal.Default, key); var identifierResult = await mediator.Send(identifierQuery).ConfigureAwait(false); identifierResult.Should().NotBeNull(); identifierResult.Username.Should().Be(updateModel.Username); // update model updateModel.Content = "Update " + DateTime.Now.Ticks; // Upsert again, should be update var upsertCommandUpdate = new EntityUpsertCommand <string, AuditUpdateModel, AuditReadModel>(MockPrincipal.Default, key, updateModel); var upsertResultUpdate = await mediator.Send(upsertCommandUpdate).ConfigureAwait(false); upsertResultUpdate.Should().NotBeNull(); upsertResultUpdate.Content.Should().NotBe(upsertResultNew.Content); }
public async Task FullTest() { var mediator = ServiceProvider.GetService <IMediator>(); mediator.Should().NotBeNull(); var mapper = ServiceProvider.GetService <IMapper>(); mapper.Should().NotBeNull(); // Create Entity var createModel = Generator.Default.Single <AuditCreateModel>(); createModel.Username = "******"; createModel.Content = "Test " + DateTime.Now.Ticks; var createCommand = new EntityCreateCommand <AuditCreateModel, AuditReadModel>(MockPrincipal.Default, createModel); var createResult = await mediator.Send(createCommand).ConfigureAwait(false); createResult.Should().NotBeNull(); // Get Entity by Key var key = CosmosKey.Encode(createResult.Id, createResult.Id); var identifierQuery = new EntityIdentifierQuery <string, AuditReadModel>(MockPrincipal.Default, key); var identifierResult = await mediator.Send(identifierQuery).ConfigureAwait(false); identifierResult.Should().NotBeNull(); identifierResult.Username.Should().Be(createModel.Username); // Query Entity var entityQuery = new EntityQuery { Sort = new List <EntitySort> { new EntitySort { Name = "Updated", Direction = "Descending" } }, Filter = new EntityFilter { Name = "Username", Value = "TEST" } }; var listQuery = new EntityPagedQuery <AuditReadModel>(MockPrincipal.Default, entityQuery); var listResult = await mediator.Send(listQuery).ConfigureAwait(false); listResult.Should().NotBeNull(); // Patch Entity var patchModel = new JsonPatchDocument <Audit>(); patchModel.Operations.Add(new Operation <Audit> { op = "replace", path = "/Content", value = "Patch Update" }); var patchCommand = new EntityPatchCommand <string, AuditReadModel>(MockPrincipal.Default, key, patchModel); var patchResult = await mediator.Send(patchCommand).ConfigureAwait(false); patchResult.Should().NotBeNull(); patchResult.Content.Should().Be("Patch Update"); // Update Entity var updateModel = mapper.Map <AuditUpdateModel>(patchResult); updateModel.Content = "Update Command"; var updateCommand = new EntityUpdateCommand <string, AuditUpdateModel, AuditReadModel>(MockPrincipal.Default, key, updateModel); var updateResult = await mediator.Send(updateCommand).ConfigureAwait(false); updateResult.Should().NotBeNull(); updateResult.Content.Should().Be("Update Command"); // Delete Entity var deleteCommand = new EntityDeleteCommand <string, AuditReadModel>(MockPrincipal.Default, key); var deleteResult = await mediator.Send(deleteCommand).ConfigureAwait(false); deleteResult.Should().NotBeNull(); deleteResult.Id.Should().Be(createResult.Id); }
public void EncodeTests(string id, string partitionKey, string cosmosKey) { var result = CosmosKey.Encode(id, partitionKey); result.Should().Be(cosmosKey); }
public async Task FullTest() { var mediator = ServiceProvider.GetService <IMediator>(); mediator.Should().NotBeNull(); var mapper = ServiceProvider.GetService <IMapper>(); mapper.Should().NotBeNull(); // Create Entity var createModel = Generator.Default.Single <TaskCreateModel>(); createModel.Title = "Testing"; createModel.Description = "Test " + DateTime.Now.Ticks; createModel.StatusId = StatusConstants.NotStarted.Id; createModel.TenantId = TenantConstants.Test.Id; var createCommand = new EntityCreateCommand <TaskCreateModel, TaskReadModel>(MockPrincipal.Default, createModel); var createResult = await mediator.Send(createCommand).ConfigureAwait(false); createResult.Should().NotBeNull(); // Get Entity by Key var cosmosKey = CosmosKey.Encode(createResult.Id, createResult.TenantId); var identifierQuery = new EntityIdentifierQuery <string, TaskReadModel>(MockPrincipal.Default, cosmosKey); var identifierResult = await mediator.Send(identifierQuery).ConfigureAwait(false); identifierResult.Should().NotBeNull(); identifierResult.Title.Should().Be(createModel.Title); // Query Entity var entityQuery = new EntityQuery { Sort = new List <EntitySort> { new EntitySort { Name = "Updated", Direction = "Descending" } }, Filter = new EntityFilter { Name = "StatusId", Value = StatusConstants.NotStarted.Id } }; var listQuery = new EntityPagedQuery <TaskReadModel>(MockPrincipal.Default, entityQuery); var listResult = await mediator.Send(listQuery).ConfigureAwait(false); listResult.Should().NotBeNull(); // Patch Entity var patchModel = new JsonPatchDocument <Task>(); patchModel.Operations.Add(new Operation <Task> { op = "replace", path = "/Title", value = "Patch Update" }); var patchCommand = new EntityPatchCommand <string, TaskReadModel>(MockPrincipal.Default, cosmosKey, patchModel); var patchResult = await mediator.Send(patchCommand).ConfigureAwait(false); patchResult.Should().NotBeNull(); patchResult.Title.Should().Be("Patch Update"); // Update Entity var updateModel = mapper.Map <TaskUpdateModel>(patchResult); updateModel.Title = "Update Command"; var updateCommand = new EntityUpdateCommand <string, TaskUpdateModel, TaskReadModel>(MockPrincipal.Default, cosmosKey, updateModel); var updateResult = await mediator.Send(updateCommand).ConfigureAwait(false); updateResult.Should().NotBeNull(); updateResult.Title.Should().Be("Update Command"); // Delete Entity var deleteCommand = new EntityDeleteCommand <string, TaskReadModel>(MockPrincipal.Default, cosmosKey); var deleteResult = await mediator.Send(deleteCommand).ConfigureAwait(false); deleteResult.Should().NotBeNull(); deleteResult.Id.Should().Be(createResult.Id); }