public UltraLiteCollection(string name, BsonAutoId autoId, LazyLoad <UltraLiteEngine> engine, BsonMapper mapper, Logger log)
        {
            _name   = name ?? mapper.ResolveCollectionName(typeof(T));
            _engine = engine;
            _mapper = mapper;
            _log    = log;

            // if strong typed collection, get _id member mapped (if exists)
            if (typeof(T) == typeof(BsonDocument))
            {
                _entity = null;
                _id     = null;
                _autoId = autoId;
            }
            else
            {
                _entity = mapper.GetEntityMapper(typeof(T));
                _id     = _entity.Id;

                if (_id != null && _id.AutoId)
                {
                    _autoId =
                        _id.DataType == typeof(Int32) || _id.DataType == typeof(Int32?) ? BsonAutoId.Int32 :
                        _id.DataType == typeof(Int64) || _id.DataType == typeof(Int64?) ? BsonAutoId.Int64 :
                        _id.DataType == typeof(Guid) || _id.DataType == typeof(Guid?) ? BsonAutoId.Guid :
                        BsonAutoId.ObjectId;
                }
                else
                {
                    _autoId = BsonAutoId.ObjectId;
                }
            }
        }
        /// <summary>
        /// Starts LiteDB database using a Stream disk
        /// </summary>
        public UltraLiteDatabase(Stream stream, BsonMapper mapper = null, string password = null, bool disposeStream = false)
        {
            if (stream == null)
            {
                throw new ArgumentNullException(nameof(stream));
            }

            _mapper = mapper ?? BsonMapper.Global;
            _log    = new Logger();

            _engine = new LazyLoad <UltraLiteEngine>(() => new UltraLiteEngine(new StreamDiskService(stream, disposeStream), password: password, log: _log));
        }
        /// <summary>
        /// Starts LiteDB database using a custom IDiskService with all parameters available
        /// </summary>
        /// <param name="diskService">Custom implementation of persist data layer</param>
        /// <param name="mapper">Instance of BsonMapper that map poco classes to document</param>
        /// <param name="password">Password to encrypt you datafile</param>
        /// <param name="timeout">Locker timeout for concurrent access</param>
        /// <param name="cacheSize">Max memory pages used before flush data in Journal file (when available)</param>
        /// <param name="log">Custom log implementation</param>
        public UltraLiteDatabase(IDiskService diskService, BsonMapper mapper = null, string password = null, TimeSpan?timeout = null, int cacheSize = 5000, Logger log = null)
        {
            if (diskService == null)
            {
                throw new ArgumentNullException(nameof(diskService));
            }

            _mapper = mapper ?? BsonMapper.Global;
            _log    = log ?? new Logger();

            _engine = new LazyLoad <UltraLiteEngine>(() => new UltraLiteEngine(diskService, password: password, timeout: timeout, cacheSize: cacheSize, log: _log));
        }
        /// <summary>
        /// Starts LiteDB database using a connection string for file system database
        /// </summary>
        public UltraLiteDatabase(ConnectionString connectionString, BsonMapper mapper = null, Logger log = null)
        {
            if (connectionString == null)
            {
                throw new ArgumentNullException(nameof(connectionString));
            }

            _connectionString = connectionString;
            _log       = log ?? new Logger();
            _log.Level = log?.Level ?? _connectionString.Log;

            _mapper = mapper ?? BsonMapper.Global;

            var options = new FileOptions
            {
                Async       = _connectionString.Async,
                Flush       = _connectionString.Flush,
                InitialSize = _connectionString.InitialSize,
                LimitSize   = _connectionString.LimitSize,
                Journal     = _connectionString.Journal,
            };

            _engine = new LazyLoad <UltraLiteEngine>(() => new UltraLiteEngine(new FileDiskService(_connectionString.Filename, options), _connectionString.Password, _connectionString.Timeout, _connectionString.CacheSize, _log, _connectionString.UtcDate));
        }