using System; using System.Linq.Expressions; using System.Threading; using AutoFixture; using CoreUnitTests.Infrastructure; using CoreUnitTests.Infrastructure.Model; using FluentAssertions; using MongoDB.Bson; using MongoDB.Driver; using MongoDbGenericRepository; using MongoDbGenericRepository.DataAccess.Update; using Moq; using Xunit; namespace CoreUnitTests.DataAccessTests.MongoDbUpdaterTests; public class UpdateOneTests : GenericTestContext { [Fact] public void WithDocument_ReplacesOne() { // Arrange var document = Fixture.Create(); var collection = SetupCollection(); // Act var result = Sut.UpdateOne(document); // Assert result.Should().BeTrue(); var expectedFilter = Builders.Filter.Eq("Id", document.Id); ReplaceOptions expectedOptions = null; collection .Verify( x => x.ReplaceOne( It.Is>(f => f.EquivalentTo(expectedFilter)), document, expectedOptions, CancellationToken.None), Times.Once()); } [Fact] public void WithDocumentAndCancellationToken_ReplacesOne() { // Arrange var document = Fixture.Create(); var token = new CancellationToken(true); var collection = SetupCollection(); // Act var result = Sut.UpdateOne(document, token); // Assert result.Should().BeTrue(); var expectedFilter = Builders.Filter.Eq("Id", document.Id); ReplaceOptions expectedOptions = null; collection .Verify( x => x.ReplaceOne( It.Is>(f => f.EquivalentTo(expectedFilter)), document, expectedOptions, token), Times.Once()); } [Fact] public void WithDocumentAndUpdateDefinition_ReplacesOne() { // Arrange var document = Fixture.Create(); var collection = SetupCollection(); var updateDefinition = Builders.Update.Set(x => x.Id, document.Id); // Act var result = Sut.UpdateOne(document, updateDefinition); // Assert result.Should().BeTrue(); var expectedFilter = Builders.Filter.Eq("Id", document.Id); collection .Verify( x => x.UpdateOne( It.Is>(f => f.EquivalentTo(expectedFilter)), updateDefinition, null, CancellationToken.None), Times.Once()); } [Fact] public void WithDocumentAndUpdateDefinitionAndCancellationToken_ReplacesOne() { // Arrange var document = Fixture.Create(); var collection = SetupCollection(); var updateDefinition = Builders.Update.Set(x => x.Id, document.Id); var token = new CancellationToken(true); // Act var result = Sut.UpdateOne(document, updateDefinition, token); // Assert result.Should().BeTrue(); var expectedFilter = Builders.Filter.Eq("Id", document.Id); collection .Verify( x => x.UpdateOne( It.Is>(f => f.EquivalentTo(expectedFilter)), updateDefinition, null, token), Times.Once()); } [Fact] public void WithDocumentAndFieldExpressionAndValue_ReplacesOne() { // Arrange var document = Fixture.Create(); var value = Fixture.Create(); var collection = SetupCollection(); Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne(document, fieldExpression, value); // Assert result.Should().BeTrue(); var expectedFilter = Builders.Filter.Eq("Id", document.Id); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); collection .Verify( x => x.UpdateOne( It.Is>(f => f.EquivalentTo(expectedFilter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, CancellationToken.None), Times.Once()); } [Fact] public void WithDocumentAndFieldExpressionAndValueAndCancellationToken_ReplacesOne() { // Arrange var document = Fixture.Create(); var value = Fixture.Create(); var collection = SetupCollection(); var token = new CancellationToken(true); Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne(document, fieldExpression, value, token); // Assert result.Should().BeTrue(); var expectedFilter = Builders.Filter.Eq("Id", document.Id); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); collection .Verify( x => x.UpdateOne( It.Is>(f => f.EquivalentTo(expectedFilter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, token), Times.Once()); } [Fact] public void WithFilterAndFieldExpressionAndValueAndPartitionKey_ReplacesOne() { // Arrange var value = Fixture.Create(); var partitionKey = Fixture.Create(); var collection = SetupCollection(partitionKey); var filter = Builders.Filter.Eq(x => x.SomeContent, "SomeContent"); Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne( filter, fieldExpression, value, partitionKey); // Assert result.Should().BeTrue(); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); collection .Verify( x => x.UpdateOne( It.Is>(f => f.EquivalentTo(filter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, CancellationToken.None), Times.Once()); } [Fact] public void WithFilterAndFieldExpressionAndValueAndCancellationToken_ReplacesOne() { // Arrange var value = Fixture.Create(); var collection = SetupCollection(); var token = new CancellationToken(true); var filter = Builders.Filter.Eq(x => x.SomeContent, "SomeContent"); Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne( filter, fieldExpression, value, cancellationToken: token); // Assert result.Should().BeTrue(); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); collection .Verify( x => x.UpdateOne( It.Is>(f => f.EquivalentTo(filter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, token), Times.Once()); } [Fact] public void WithFilterAndFieldExpressionAndValueAndPartitionKeyAndCancellationToken_ReplacesOne() { // Arrange var value = Fixture.Create(); var partitionKey = Fixture.Create(); var collection = SetupCollection(partitionKey); var token = new CancellationToken(true); var filter = Builders.Filter.Eq(x => x.SomeContent, "SomeContent"); Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne( filter, fieldExpression, value, partitionKey, token); // Assert result.Should().BeTrue(); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); collection .Verify( x => x.UpdateOne( It.Is>(f => f.EquivalentTo(filter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, token), Times.Once()); } [Fact] public void WithFilterExpressionAndFieldExpressionAndValueAndCancellationToken_ReplacesOne() { // Arrange var value = Fixture.Create(); var collection = SetupCollection(); var token = new CancellationToken(true); Expression> filterExpression = testDocument => testDocument.SomeContent == "SomeContent"; Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne( filterExpression, fieldExpression, value, cancellationToken: token); // Assert result.Should().BeTrue(); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); var expectedFilter = Builders.Filter.Where(filterExpression); collection .Verify( x => x.UpdateOne( It.Is>(f => f.EquivalentTo(expectedFilter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, token), Times.Once()); } [Fact] public void WithFilterExpressionAndFieldExpressionAndValueAndPartitionKey_ReplacesOne() { // Arrange var value = Fixture.Create(); var partitionKey = Fixture.Create(); var collection = SetupCollection(partitionKey); Expression> filterExpression = testDocument => testDocument.SomeContent == "SomeContent"; Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne( filterExpression, fieldExpression, value, partitionKey); // Assert result.Should().BeTrue(); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); var expectedFilter = Builders.Filter.Where(filterExpression); collection .Verify( x => x.UpdateOne( It.Is>(f => f.EquivalentTo(expectedFilter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, CancellationToken.None), Times.Once()); } [Fact] public void WithFilterExpressionAndFieldExpressionAndValueAndPartitionKeyAndCancellationToken_ReplacesOne() { // Arrange var value = Fixture.Create(); var partitionKey = Fixture.Create(); var collection = SetupCollection(partitionKey); var token = new CancellationToken(true); Expression> filterExpression = testDocument => testDocument.SomeContent == "SomeContent"; Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne( filterExpression, fieldExpression, value, partitionKey, token); // Assert result.Should().BeTrue(); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); var expectedFilter = Builders.Filter.Where(filterExpression); collection .Verify( x => x.UpdateOne( It.Is>(f => f.EquivalentTo(expectedFilter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, token), Times.Once()); } [Fact] public void WithClientSessionAndDocument_ReplacesOne() { // Arrange var session = MockOf(); var document = Fixture.Create(); var collection = SetupCollection(); // Act var result = Sut.UpdateOne(session.Object, document); // Assert result.Should().BeTrue(); var expectedFilter = Builders.Filter.Eq("Id", document.Id); ReplaceOptions expectedOptions = null; collection .Verify( x => x.ReplaceOne( session.Object, It.Is>(f => f.EquivalentTo(expectedFilter)), document, expectedOptions, CancellationToken.None), Times.Once()); } [Fact] public void WithClientSessionAndDocumentAndCancellationToken_ReplacesOne() { // Arrange var session = MockOf(); var document = Fixture.Create(); var token = new CancellationToken(true); var collection = SetupCollection(); // Act var result = Sut.UpdateOne(session.Object, document, token); // Assert result.Should().BeTrue(); var expectedFilter = Builders.Filter.Eq("Id", document.Id); ReplaceOptions expectedOptions = null; collection .Verify( x => x.ReplaceOne( session.Object, It.Is>(f => f.EquivalentTo(expectedFilter)), document, expectedOptions, token), Times.Once()); } [Fact] public void WithClientSessionAndDocumentAndUpdateDefinition_ReplacesOne() { // Arrange var session = MockOf(); var document = Fixture.Create(); var collection = SetupCollection(); var updateDefinition = Builders.Update.Set(x => x.Id, document.Id); // Act var result = Sut.UpdateOne(session.Object, document, updateDefinition); // Assert result.Should().BeTrue(); var expectedFilter = Builders.Filter.Eq("Id", document.Id); collection .Verify( x => x.UpdateOne( session.Object, It.Is>(f => f.EquivalentTo(expectedFilter)), updateDefinition, null, CancellationToken.None), Times.Once()); } [Fact] public void WithClientSessionAndDocumentAndUpdateDefinitionAndCancellationToken_ReplacesOne() { // Arrange var session = MockOf(); var document = Fixture.Create(); var collection = SetupCollection(); var updateDefinition = Builders.Update.Set(x => x.Id, document.Id); var token = new CancellationToken(true); // Act var result = Sut.UpdateOne(session.Object, document, updateDefinition, token); // Assert result.Should().BeTrue(); var expectedFilter = Builders.Filter.Eq("Id", document.Id); collection .Verify( x => x.UpdateOne( session.Object, It.Is>(f => f.EquivalentTo(expectedFilter)), updateDefinition, null, token), Times.Once()); } [Fact] public void WithClientSessionAndDocumentAndFieldExpressionAndValue_ReplacesOne() { // Arrange var session = MockOf(); var document = Fixture.Create(); var value = Fixture.Create(); var collection = SetupCollection(); Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne(session.Object, document, fieldExpression, value); // Assert result.Should().BeTrue(); var expectedFilter = Builders.Filter.Eq("Id", document.Id); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); collection .Verify( x => x.UpdateOne( session.Object, It.Is>(f => f.EquivalentTo(expectedFilter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, CancellationToken.None), Times.Once()); } [Fact] public void WithClientSessionAndDocumentAndFieldExpressionAndValueAndCancellationToken_ReplacesOne() { // Arrange var session = MockOf(); var document = Fixture.Create(); var value = Fixture.Create(); var collection = SetupCollection(); var token = new CancellationToken(true); Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne(session.Object, document, fieldExpression, value, token); // Assert result.Should().BeTrue(); var expectedFilter = Builders.Filter.Eq("Id", document.Id); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); collection .Verify( x => x.UpdateOne( session.Object, It.Is>(f => f.EquivalentTo(expectedFilter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, token), Times.Once()); } [Fact] public void WithClientSessionAndFilterAndFieldExpressionAndValueAndPartitionKey_ReplacesOne() { // Arrange var session = MockOf(); var value = Fixture.Create(); var partitionKey = Fixture.Create(); var collection = SetupCollection(partitionKey); var filter = Builders.Filter.Eq(x => x.SomeContent, "SomeContent"); Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne( session.Object, filter, fieldExpression, value, partitionKey); // Assert result.Should().BeTrue(); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); collection .Verify( x => x.UpdateOne( session.Object, It.Is>(f => f.EquivalentTo(filter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, CancellationToken.None), Times.Once()); } [Fact] public void WithClientSessionAndFilterAndFieldExpressionAndValueAndCancellationToken_ReplacesOne() { // Arrange var session = MockOf(); var value = Fixture.Create(); var collection = SetupCollection(); var token = new CancellationToken(true); var filter = Builders.Filter.Eq(x => x.SomeContent, "SomeContent"); Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne( session.Object, filter, fieldExpression, value, cancellationToken: token); // Assert result.Should().BeTrue(); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); collection .Verify( x => x.UpdateOne( session.Object, It.Is>(f => f.EquivalentTo(filter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, token), Times.Once()); } [Fact] public void WithClientSessionAndFilterAndFieldExpressionAndValueAndPartitionKeyAndCancellationToken_ReplacesOne() { // Arrange var session = MockOf(); var value = Fixture.Create(); var partitionKey = Fixture.Create(); var collection = SetupCollection(partitionKey); var token = new CancellationToken(true); var filter = Builders.Filter.Eq(x => x.SomeContent, "SomeContent"); Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne( session.Object, filter, fieldExpression, value, partitionKey, token); // Assert result.Should().BeTrue(); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); collection .Verify( x => x.UpdateOne( session.Object, It.Is>(f => f.EquivalentTo(filter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, token), Times.Once()); } [Fact] public void WithClientSessionAndFilterExpressionAndFieldExpressionAndValueAndCancellationToken_ReplacesOne() { // Arrange var session = MockOf(); var value = Fixture.Create(); var collection = SetupCollection(); var token = new CancellationToken(true); Expression> filterExpression = testDocument => testDocument.SomeContent == "SomeContent"; Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne( session.Object, filterExpression, fieldExpression, value, cancellationToken: token); // Assert result.Should().BeTrue(); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); var expectedFilter = Builders.Filter.Where(filterExpression); collection .Verify( x => x.UpdateOne( session.Object, It.Is>(f => f.EquivalentTo(expectedFilter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, token), Times.Once()); } [Fact] public void WithClientSessionAndFilterExpressionAndFieldExpressionAndValueAndPartitionKey_ReplacesOne() { // Arrange var session = MockOf(); var value = Fixture.Create(); var partitionKey = Fixture.Create(); var collection = SetupCollection(partitionKey); Expression> filterExpression = testDocument => testDocument.SomeContent == "SomeContent"; Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne( session.Object, filterExpression, fieldExpression, value, partitionKey); // Assert result.Should().BeTrue(); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); var expectedFilter = Builders.Filter.Where(filterExpression); collection .Verify( x => x.UpdateOne( session.Object, It.Is>(f => f.EquivalentTo(expectedFilter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, CancellationToken.None), Times.Once()); } [Fact] public void WithClientSessionAndFilterExpressionAndFieldExpressionAndValueAndPartitionKeyAndCancellationToken_ReplacesOne() { // Arrange var session = MockOf(); var value = Fixture.Create(); var partitionKey = Fixture.Create(); var collection = SetupCollection(partitionKey); var token = new CancellationToken(true); Expression> filterExpression = testDocument => testDocument.SomeContent == "SomeContent"; Expression> fieldExpression = testDocument => testDocument.SomeContent; // Act var result = Sut.UpdateOne( session.Object, filterExpression, fieldExpression, value, partitionKey, token); // Assert result.Should().BeTrue(); var expectedUpdateDefinition = Builders.Update.Set(x => x.SomeContent, value); var expectedFilter = Builders.Filter.Where(filterExpression); collection .Verify( x => x.UpdateOne( session.Object, It.Is>(f => f.EquivalentTo(expectedFilter)), It.Is>(u => u.EquivalentTo(expectedUpdateDefinition)), null, token), Times.Once()); } private Mock> SetupCollection(string partitionKey = null) { var replacedId = Fixture.Create(); var count = Fixture.Create(); var replaceResult = new ReplaceOneResult.Acknowledged(count, 1, new BsonBinaryData(replacedId, GuidRepresentation.Standard)); var updateResult = new UpdateResult.Acknowledged(count, 1, new BsonBinaryData(replacedId, GuidRepresentation.Standard)); var collection = MockOf>(); collection .Setup( x => x.ReplaceOne( It.IsAny>(), It.IsAny(), It.IsAny(), It.IsAny())) .Returns(replaceResult); collection .Setup( x => x.UpdateOne( It.IsAny>(), It.IsAny>(), It.IsAny(), It.IsAny())) .Returns(updateResult); collection .Setup( x => x.ReplaceOne( It.IsAny(), It.IsAny>(), It.IsAny(), It.IsAny(), It.IsAny())) .Returns(replaceResult); collection .Setup( x => x.UpdateOne( It.IsAny(), It.IsAny>(), It.IsAny>(), It.IsAny(), It.IsAny())) .Returns(updateResult); var dbContext = MockOf(); dbContext .Setup(x => x.GetCollection(partitionKey)) .Returns(collection.Object); return collection; } }