public static IEntityDefinition RegisterType(Type entityType)
        {
            if (!IsValidTypeToMap(entityType))
            {
                throw new ArgumentException("Type is not a valid type to map", nameof(entityType));
            }

            MappingLock.EnterUpgradeableReadLock();
            try
            {
                if (EntityDefinitions.ContainsKey(entityType))
                {
                    throw new ArgumentException("Type is already registered", nameof(entityType));
                }

                if (BsonClassMap.IsClassMapRegistered(entityType))
                {
                    throw new ArgumentException($"Type is already registered as a {nameof(BsonClassMap)}");
                }

                MappingLock.EnterWriteLock();
                try
                {
                    //Now we have the write lock, do one super last minute check
                    if (EntityDefinitions.TryGetValue(entityType, out var definition))
                    {
                        //We will treat success of this check as if we have registered it just now
                        return(definition);
                    }

                    var classMap = new BsonClassMap(entityType);
                    definition = new EntityDefinition
                    {
                        EntityType = entityType
                    };

                    EntityDefinitions.TryAdd(entityType, definition);
                    BsonClassMap.RegisterClassMap(classMap);

                    foreach (var processor in MappingProcessors)
                    {
                        processor.ApplyMapping(definition, classMap);
                    }

                    return(definition);
                }
                finally
                {
                    MappingLock.ExitWriteLock();
                }
            }
            finally
            {
                MappingLock.ExitUpgradeableReadLock();
            }
        }
        public static bool TryRegisterType(Type entityType, out IEntityDefinition definition)
        {
            if (!IsValidTypeToMap(entityType))
            {
                definition = null;
                return(false);
            }

            MappingLock.EnterUpgradeableReadLock();
            try
            {
                if (EntityDefinitions.ContainsKey(entityType) || BsonClassMap.IsClassMapRegistered(entityType))
                {
                    definition = null;
                    return(false);
                }

                MappingLock.EnterWriteLock();
                try
                {
                    //Now we have the write lock, do one super last minute check
                    if (EntityDefinitions.TryGetValue(entityType, out definition))
                    {
                        //We will treat success of this check as if we have registered it just now
                        return(true);
                    }

                    var classMap = new BsonClassMap(entityType);
                    definition = new EntityDefinition
                    {
                        EntityType = entityType
                    };

                    EntityDefinitions.TryAdd(entityType, definition);
                    BsonClassMap.RegisterClassMap(classMap);

                    foreach (var processor in MappingProcessors)
                    {
                        processor.ApplyMapping(definition, classMap);
                    }

                    return(true);
                }
                finally
                {
                    MappingLock.ExitWriteLock();
                }
            }
            finally
            {
                MappingLock.ExitUpgradeableReadLock();
            }
        }
        public static IEntityDefinition GetOrCreateDefinition(Type entityType)
        {
            MappingLock.EnterUpgradeableReadLock();
            try
            {
                if (EntityDefinitions.TryGetValue(entityType, out var definition))
                {
                    return(definition);
                }

                return(RegisterType(entityType));
            }
            finally
            {
                MappingLock.ExitUpgradeableReadLock();
            }
        }