diff --git a/framework/src/Volo.Abp.MongoDB/Volo/Abp/MongoDB/AbpMongoDbOptions.cs b/framework/src/Volo.Abp.MongoDB/Volo/Abp/MongoDB/AbpMongoDbOptions.cs new file mode 100644 index 0000000000..21502e0cf8 --- /dev/null +++ b/framework/src/Volo.Abp.MongoDB/Volo/Abp/MongoDB/AbpMongoDbOptions.cs @@ -0,0 +1,18 @@ +using Volo.Abp.Timing; + +namespace Volo.Abp.MongoDB +{ + public class AbpMongoDbOptions + { + /// + /// Serializer the datetime based on in MongoDb. + /// Default: true. + /// + public bool UseAbpClockHandleDateTime { get; set; } + + public AbpMongoDbOptions() + { + UseAbpClockHandleDateTime = true; + } + } +} diff --git a/framework/src/Volo.Abp.MongoDB/Volo/Abp/MongoDB/MongoModelBuilder.cs b/framework/src/Volo.Abp.MongoDB/Volo/Abp/MongoDB/MongoModelBuilder.cs index 1f155fc21d..03f3b52572 100644 --- a/framework/src/Volo.Abp.MongoDB/Volo/Abp/MongoDB/MongoModelBuilder.cs +++ b/framework/src/Volo.Abp.MongoDB/Volo/Abp/MongoDB/MongoModelBuilder.cs @@ -28,7 +28,7 @@ namespace Volo.Abp.MongoDB { lock (SyncObj) { - var clockOptions = dbContext.LazyServiceProvider?.LazyGetService>(); + var useAbpClockHandleDateTime = dbContext.LazyServiceProvider.LazyGetRequiredService>().Value.UseAbpClockHandleDateTime; var entityModels = _entityModelBuilders .Select(x => x.Value) @@ -41,7 +41,7 @@ namespace Volo.Abp.MongoDB { var map = entityModel.As().GetMap(); - if (clockOptions != null) + if (useAbpClockHandleDateTime) { var dateTimePropertyInfos = entityModel.EntityType.GetProperties(BindingFlags.DeclaredOnly | BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public) .Where(property => @@ -58,11 +58,11 @@ namespace Volo.Abp.MongoDB if (property.PropertyType == typeof(DateTime?)) { - map.MapProperty(property.Name).SetSerializer(new NullableSerializer().WithSerializer(new AbpMongoDbDateTimeSerializer(clockOptions.Value.Kind, disableDateTimeNormalization))); + map.MapProperty(property.Name).SetSerializer(new NullableSerializer().WithSerializer(new AbpMongoDbDateTimeSerializer(GetDateTimeKind(dbContext), disableDateTimeNormalization))); } else { - map.MapProperty(property.Name).SetSerializer(new AbpMongoDbDateTimeSerializer(clockOptions.Value.Kind, disableDateTimeNormalization)); + map.MapProperty(property.Name).SetSerializer(new AbpMongoDbDateTimeSerializer(GetDateTimeKind(dbContext), disableDateTimeNormalization)); } }); } @@ -86,7 +86,7 @@ namespace Volo.Abp.MongoDB var map = new BsonClassMap(baseClass); map.ConfigureAbpConventions(); - if (clockOptions != null) + if (useAbpClockHandleDateTime) { var dateTimePropertyInfos = baseClass.GetProperties(BindingFlags.DeclaredOnly | BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public) .Where(property => @@ -99,11 +99,11 @@ namespace Volo.Abp.MongoDB { if (property.PropertyType == typeof(DateTime?)) { - map.MapProperty(property.Name).SetSerializer(new NullableSerializer().WithSerializer(new AbpMongoDbDateTimeSerializer(clockOptions.Value.Kind, false))); + map.MapProperty(property.Name).SetSerializer(new NullableSerializer().WithSerializer(new AbpMongoDbDateTimeSerializer(GetDateTimeKind(dbContext), false))); } else { - map.MapProperty(property.Name).SetSerializer(new AbpMongoDbDateTimeSerializer(clockOptions.Value.Kind, false)); + map.MapProperty(property.Name).SetSerializer(new AbpMongoDbDateTimeSerializer(GetDateTimeKind(dbContext), false)); } }); } @@ -116,6 +116,11 @@ namespace Volo.Abp.MongoDB } } + private DateTimeKind GetDateTimeKind(AbpMongoDbContext dbContext) + { + return dbContext.LazyServiceProvider.LazyGetRequiredService>().Value.Kind; + } + public virtual void Entity(Action> buildAction = null) { var model = (IMongoEntityModelBuilder)_entityModelBuilders.GetOrAdd( diff --git a/framework/test/Volo.Abp.MongoDB.Tests/Volo/Abp/MongoDB/Serializer/MongoDB_DateTimeKind_Tests.cs b/framework/test/Volo.Abp.MongoDB.Tests/Volo/Abp/MongoDB/Serializer/MongoDB_DateTimeKind_Tests.cs index f691145d60..39a685380b 100644 --- a/framework/test/Volo.Abp.MongoDB.Tests/Volo/Abp/MongoDB/Serializer/MongoDB_DateTimeKind_Tests.cs +++ b/framework/test/Volo.Abp.MongoDB.Tests/Volo/Abp/MongoDB/Serializer/MongoDB_DateTimeKind_Tests.cs @@ -1,8 +1,11 @@ using System; using System.Reflection; +using System.Threading.Tasks; using Microsoft.Extensions.DependencyInjection; using MongoDB.Bson.Serialization; using MongoDB.Bson.Serialization.Serializers; +using Shouldly; +using Volo.Abp.TestApp.Domain; using Volo.Abp.TestApp.Testing; using Volo.Abp.Timing; using Xunit; @@ -10,7 +13,7 @@ using Xunit; namespace Volo.Abp.MongoDB.Serializer { [Collection(MongoTestCollection.Name)] - public abstract class MongoDB_DateTimeKind_Tests : DateTimeKind_Tests, IDisposable + public abstract class MongoDB_DateTimeKind_Tests : DateTimeKind_Tests { protected override void AfterAddApplication(IServiceCollection services) { @@ -78,4 +81,40 @@ namespace Volo.Abp.MongoDB.Serializer base.AfterAddApplication(services); } } + + [Collection(MongoTestCollection.Name)] + public class DisableDateTimeKindTests : TestAppTestBase + { + protected IPersonRepository PersonRepository { get; } + + public DisableDateTimeKindTests() + { + PersonRepository = GetRequiredService(); + } + + protected override void AfterAddApplication(IServiceCollection services) + { + services.Configure(x => x.UseAbpClockHandleDateTime = false); + base.AfterAddApplication(services); + } + + [Fact] + public async Task DateTime_Kind_Should_Be_Normalized_By_MongoDb_Test() + { + var personId = Guid.NewGuid(); + await PersonRepository.InsertAsync(new Person(personId, "bob lee", 18) + { + Birthday = DateTime.Parse("2020-01-01 00:00:00"), + LastActive = DateTime.Parse("2020-01-01 00:00:00"), + }, true); + + var person = await PersonRepository.GetAsync(personId); + + person.ShouldNotBeNull(); + person.CreationTime.Kind.ShouldBe(DateTimeKind.Utc); + + person.Birthday.ShouldNotBeNull(); + person.Birthday.Value.Kind.ShouldBe(DateTimeKind.Utc); + } + } }