コード例 #1
0
        private HashSet <OldToNewIdMapping> RestoreData(Database restoreTo, ILogger logger)
        {
            HashSet <OldToNewIdMapping> result = new HashSet <OldToNewIdMapping>();

            DatabaseToRestoreTo = restoreTo;
            DatabaseToRestoreTo.TryEnsureSchema(DaoTypes.First(), logger);

            Dictionary <string, Dao> tempForeignKeyTargets = InsertTempForeignKeyTargets();

            // for all the poco types load them all from the repo
            foreach (Type pocoType in BackupRepository.StorableTypes)
            {
                // copy the poco as a dao and save it into the restoreTo
                IEnumerable <object> all = BackupRepository.RetrieveAll(pocoType);
                Type daoType             = DaoTypes.FirstOrDefault(t => t.Name.Equals(pocoType.Name));
                Args.ThrowIf <InvalidOperationException>(daoType == null, "The Dto of type {0} didn't have a corresponding Dao type", pocoType.Name);

                foreach (object poco in all)
                {
                    string uuid = Meta.GetUuid(poco, true);
                    Dao    dao  = (Dao)poco.CopyAs(daoType);
                    dao.IdValue              = null;
                    dao.DataRow              = null;
                    dao.ForceInsert          = true;
                    dao.UniqueFilterProvider = () =>
                    {
                        return(Query.Where("Uuid") == uuid);
                    };
                    ForceUpdateIfExistsInTarget(uuid, dao);
                    SetTemporaryForeignKeys(dao, tempForeignKeyTargets);

                    dao.Save(DatabaseToRestoreTo);
                    OldToNewIdMapping idMapping = new OldToNewIdMapping
                    {
                        PocoType = pocoType,
                        DaoType  = daoType,
                        OldId    = (long)poco.Property("Id"),
                        NewId    = (long)dao.IdValue,
                        Uuid     = uuid
                    };

                    result.Add(idMapping);
                }
            }
            return(result);
        }
コード例 #2
0
        protected internal void CorrectForeignKeys(HashSet <OldToNewIdMapping> oldToNewIdMappings, Database source, Database destination)
        {
            Dictionary <string, OldToNewIdMapping> byUuid = oldToNewIdMappings.ToDictionary(otn => otn.Uuid);

            IParameterBuilder   oldParameterBuilder  = source.GetService <IParameterBuilder>();
            SqlStringBuilder    committer            = destination.GetService <SqlStringBuilder>();
            List <Type>         tableTypes           = DaoAssembly.GetTypes().Where(type => type.HasCustomAttributeOfType <TableAttribute>()).ToList();
            List <PropertyInfo> foreignKeyProperties = new List <PropertyInfo>();

            foreach (Type type in tableTypes)
            {
                foreignKeyProperties.AddRange(type.GetProperties().Where(prop => prop.HasCustomAttributeOfType <ForeignKeyAttribute>()).ToList());
            }

            // for every foreign key
            foreach (PropertyInfo prop in foreignKeyProperties)
            {
                ForeignKeyAttribute fk = prop.GetCustomAttributeOfType <ForeignKeyAttribute>();
                // get the old Dao instances that represents the referenced table
                Type referencedDaoType = DaoTypes.First(t =>
                {
                    TableAttribute table;
                    t.HasCustomAttributeOfType <TableAttribute>(out table);
                    return(table.TableName.Equals(fk.ReferencedTable));
                });

                SqlStringBuilder oldSelector = source.GetService <SqlStringBuilder>();
                oldSelector.Select(fk.ReferencedTable);
                List <object> oldReferencedDaos = source.GetDataTable(oldSelector, CommandType.Text, oldParameterBuilder.GetParameters(oldSelector)).ToListOf(referencedDaoType);

                foreach (object oldReferenced in oldReferencedDaos)
                {
                    Dao oldReferencedDao = (Dao)oldReferenced;

                    // get the old Dao instances that represent the referencing table where the referencing column value = the old table id
                    Type referencingDaoType = DaoTypes.First(t =>
                    {
                        TableAttribute table;
                        t.HasCustomAttributeOfType <TableAttribute>(out table);
                        return(table.TableName.Equals(fk.Table));
                    });
                    SqlStringBuilder oldReferencerSelector = source.GetService <SqlStringBuilder>();
                    oldReferencerSelector.Select(fk.Table).Where(new AssignValue(fk.Name, oldReferencedDao.IdValue));
                    List <object> oldReferencingDaoInstances = source.GetDataTable(oldReferencerSelector, CommandType.Text, oldParameterBuilder.GetParameters(oldReferencerSelector)).ToListOf(referencingDaoType);

                    if (oldReferencingDaoInstances.Count > 0)
                    {
                        List <string> oldReferencingDaoInstanceUuids = oldReferencingDaoInstances.Select(o => o.Property <string>("Uuid")).ToList();

                        long oldReferencedId = oldReferencedDao.IdValue.Value;
                        // get the new referenced id
                        long whatItShouldBeNow = byUuid[oldReferencedDao.Property <string>("Uuid")].NewId;

                        // update the new referencing column to match the newId in the destination where the uuids in oldDaoInstances
                        committer.Update(fk.Table, new AssignValue(fk.Name, whatItShouldBeNow)).Where(Query.Where("Uuid").In(oldReferencingDaoInstanceUuids.ToArray()));
                        committer.Go();
                    }
                }
            }

            destination.ExecuteSql(committer, oldParameterBuilder);
        }