protected virtual SecondaryKeyGenDelegate GetForeignKeyGenerator(SecondaryKeyAttribute secondaryKey) { return((pKey, pData) => { var entity = pData.Data.FromBytes(); object foreingKey; if (!entity.TryGet(secondaryKey.Name, out foreingKey)) { throw new InvalidOperationException(); } return new DatabaseEntry(foreingKey.ToBinnary()); }); }
public virtual SecondaryDatabase GetSecondaryDb(Database primaryDb, SecondaryKeyAttribute secondaryKey, Database foreignDb = null) { var dbName = SecondaryKeyDbName(primaryDb, secondaryKey); SecondaryDatabase database; if (_secondaryDbs.TryGetValue(dbName, out database)) { return(database); } database = OpenWritableSecondaryDatabase(primaryDb, secondaryKey, dbName, foreignDb); if (_secondaryDbs.TryAdd(dbName, database)) { return(database); } database.Close(); database = _secondaryDbs[dbName]; return(database); }
public virtual IEnumerable <DatabaseEntry> GetFromSecondaryDb(DatabaseEntry key, string entityName, SecondaryKeyAttribute secondaryKey) { Cursor cursor = null; try { var primaryDb = _schema.GetPrimaryDb(entityName); var secondaryDb = _schema.GetSecondaryDb(primaryDb, secondaryKey); cursor = secondaryDb.Cursor(); if (!cursor.Move(key, exact: true)) { yield break; } if (secondaryKey.DuplicatesPolicy == DuplicatesPolicy.NONE) { yield return(cursor.Current.Value); } else { yield return(cursor.Current.Value); while (cursor.MoveNextDuplicate()) { yield return(cursor.Current.Value); } } } finally { cursor?.Close(); } }
protected virtual string SecondaryKeyDbName(Database primaryDb, SecondaryKeyAttribute secondaryKey) { return($"{primaryDb.DatabaseName}-->{secondaryKey.Name}"); }
protected virtual SecondaryDatabase OpenWritableSecondaryDatabase(Database primaryDb, SecondaryKeyAttribute secondaryForeingKey, string dbName, [CanBeNull] Database foreignDb = null) { var config = new SecondaryBTreeDatabaseConfig(primaryDb, GetForeignKeyGenerator(secondaryForeingKey)) { Env = Environment, Encrypted = IsEncrypted, Duplicates = (BerkeleyDB.DuplicatesPolicy)secondaryForeingKey.DuplicatesPolicy, Creation = CreatePolicy.IF_NEEDED, ReadUncommitted = true, FreeThreaded = IsFreeThreaded, AutoCommit = true, }; if (foreignDb != null) { config.SetForeignKeyConstraint(foreignDb, ForeignKeyDeleteAction.ABORT); } return(SecondaryBTreeDatabase.Open(_dbPath, dbName, config)); }