Beispiel #1
0
 /*
  *  }
  *  catch (Exception ex)
  *  {
  *      throw ex;
  *  }
  *
  * }
  * public static WeightCategories GetRandomisingCategory(Participant newParticipant)
  * {
  *  int returnInt;
  *  if (newParticipant.AdmissionWeight < BlockWeight1)
  *  {
  *      returnInt = 1;
  *  }
  *  else if (newParticipant.AdmissionWeight >= BlockWeight2)
  *  {
  *      returnInt = 5;
  *  }
  *  else
  *  {
  *      returnInt = 3;
  *  }
  *  if (!newParticipant.IsMale)
  *  {
  *      returnInt++;
  *  }
  *  return (WeightCategories)returnInt;
  * }
  */
 public static void RemoveAllocationFromArm(Participant participant, ITrialDataContext context)
 {
     /*
      * RandomisationStrata strata;
      * var blocks = GetDescendingBlocks(participant, context, out strata);
      *
      * //participant is in top block anyway (or no blocks yet existing for strata) - do nothing
      * int topBlockId = blocks.Select(b=>b.Id).FirstOrDefault();
      * if (topBlockId != 0 && participant.AllocationBlockId != topBlockId)
      * {
      *  //participant is not in top block, but another participant is able to replace position in earlier block
      *  Participant movableParticipant = context.Participants.FirstOrDefault(p=>p.AllocationBlockId == topBlockId && p.TrialArm == participant.TrialArm);
      *  if (movableParticipant == null)
      *  {
      *      //no top allocations: merge with next block down
      *      AllocationBlock secondTopBlock = blocks.Skip(1).FirstOrDefault();
      *      if (secondTopBlock == null)
      *      {
      *          //there is nothing we can do
      *          return;
      *      }
      *      AllocationBlock topBlock = blocks.FirstOrDefault();
      *      if (topBlock.Participants == null) {topBlock.Participants = context.Participants.Where(p=>p.AllocationBlockId == topBlockId).ToList();}
      *      if (secondTopBlock.Participants == null) {secondTopBlock.Participants = context.Participants.Where(p=>p.AllocationBlockId == secondTopBlock.Id).ToList();}
      *      secondTopBlock.MergeBlock(topBlock);
      *      context.AllocationBlocks.Remove(topBlock);
      *      movableParticipant = secondTopBlock.Participants.First(p=>p.TrialArm == participant.TrialArm);
      *  }
      *  movableParticipant.AllocationBlockId = participant.AllocationBlockId;
      * }
      */
     participant.AllocationBlockId = 0;
     participant.Block             = null;
 }
Beispiel #2
0
 public static DateTime? MostRecentEntry(ITrialDataContext context)
 {
     return (new DateTime?[]
             {
                 context.Participants.Max(p=>(DateTime?)p.RecordLastModified),
                 context.ScreenedPatients.Max(s=>(DateTime?)s.RecordLastModified),
                 context.Vaccines.Where(v=>v.Id>DataContextInitialiser.MaxReservedVaccineId).Max(v=>(DateTime?)v.RecordLastModified),
                 context.VaccinesAdministered.Max(va=>(DateTime?)va.RecordLastModified),
                 context.ProtocolViolations.Max(pv=>(DateTime?)pv.RecordLastModified),
             }).Max();
 }
Beispiel #3
0
        void AddOrUpdateBaks(IEnumerable <string> bakupFilePaths)
        {
            if (_isBackingUp)
            {
                return;
            }
            _isBackingUp = true;
            foreach (var f in bakupFilePaths)
            {
                MigrateIfRequired(f);
            }

#pragma warning disable IDE0067 // Dispose objects before losing scope
            BackgroundWorker worker = new BackgroundWorker()
            {
                WorkerReportsProgress = true
            };
#pragma warning restore IDE0067 // Dispose objects before losing scope
            worker.DoWork += SyncronisationResult.Sync;

            if (UpdateProgress != null)
            {
                worker.ProgressChanged += UpdateProgress;
            }
            bool isForUpdate = ParticipantAdded != null || ParticipantUpdated != null || ScreenedPatientAdded != null;
            if (isForUpdate)
            {
                worker.RunWorkerCompleted += WhenSyncronisationResultsAvailable;
            }
            if (AnyParticipantChange != null)
            {
                worker.RunWorkerCompleted += (o, e) => AnyParticipantChange(this, new LastUpdatedChangedEventAgs(LastCreateModifyParticipant()));
            }
            if (DatabaseUpdating != null)
            {
                DatabaseUpdating(this, new DatabaseUpdatingEventAgs(true));
                worker.RunWorkerCompleted += (o, e) => DatabaseUpdating(this, new DatabaseUpdatingEventAgs(false));
            }
            worker.RunWorkerCompleted += (o, e) => _isBackingUp = false;
            worker.RunWorkerCompleted += (o, e) =>
            {
                string fn = App.DataDirectory + '\\' + _dbContext.DbName + _bakExtension;
                _dbContext.Dispose();
                SyncronisationResult.RepairDb(fn);
                _dbContext = _createContext.Invoke();
                worker.Dispose();
            };
            worker.RunWorkerAsync(new SyncronisationResult.SyncArgs
            {
                DestContext   = _dbContext,
                DbFileNames   = bakupFilePaths.ToList(),
                UpdateResults = isForUpdate
            });
        }
Beispiel #4
0
 public static DateTime? MostRecentEntry(ITrialDataContext context, IEnumerable<IntegerRange> idRanges)
 {
     if (idRanges.Any())
     {
         return (idRanges.Select(rng=>new DateTime?[]
             {
                 context.Participants.Where(p=>p.CentreId == rng.Min).Max(p=>(DateTime?)p.RecordLastModified),
                 context.ScreenedPatients.Where(p=>p.CentreId == rng.Min).Max(s=>(DateTime?)s.RecordLastModified),
                 context.Vaccines.Where(p=> p.Id > DataContextInitialiser.MaxReservedVaccineId && p.Id >= rng.Min && p.Id<= rng.Max).Max(v=>(DateTime?)v.RecordLastModified),
                 context.VaccinesAdministered.Where(p=>p.Id >= rng.Min && p.Id<= rng.Max).Max(va=>(DateTime?)va.RecordLastModified),
                 context.ProtocolViolations.Where(p=>p.Id >= rng.Min && p.Id<= rng.Max).Max(pv=>(DateTime?)pv.RecordLastModified),
             }).Max()).Max();
     }
     return null;
 }
Beispiel #5
0
        public void Restore()
        {
            //DateTime RecordLastModified = _dbContext.DbLastModifiedUtc(); //note this is all assuming user on backup end has no ability to modify data
            IEnumerable <MatchedFilePair> filePairs = GetMatchedCloudAndExtractedFiles()
                                                      .Where(fp => fp.ExtractedBak == null || fp.ExtractedBak.CreationTimeUtc < fp.Zip.LastWriteTimeUtc)
                                                      .ToList();

            if (!filePairs.Any())
            {
                return;
            }
            List <BakFileDetails> bakDetails = new List <BakFileDetails>();

            _dbContext.Dispose();

            foreach (var fp in filePairs)
            {
                using (ZipFile readFile = ZipFile.Read(fp.Zip.FullName))
                {
                    try
                    {
                        readFile[0].Extract(App.DataDirectory, ExtractExistingFileAction.OverwriteSilently);
                    }
                    catch (Exception e)
                    {
                        FailedDbRestore?.Invoke(this, new FailedRestoreEvent(fp.Zip.FullName, e));
                    }
                }
                BakFileDetails newBak = new BakFileDetails();
                bakDetails.Add(newBak);
                if (fp.ExtractedBak == null)
                {
                    fp.ExtractedBak = new FileInfo(Path.Combine(App.DataDirectory, Path.GetFileNameWithoutExtension(fp.Zip.Name) + BakExtension));
                }
                else
                {
                    newBak.LastBackupUtc = fp.ExtractedBak.CreationTimeUtc;
                }
                newBak.FullFilename             = fp.ExtractedBak.FullName;
                fp.ExtractedBak.CreationTimeUtc = fp.Zip.LastWriteTimeUtc;
            }

            _dbContext = _createContext.Invoke();
            AddOrUpdateBaks(bakDetails.Select(b => b.FullFilename));
        }
Beispiel #6
0
        public void Backup()
        {
            string   bakFileName = _dbContext.BackupDb();
            FileInfo bakFile     = new FileInfo(bakFileName);

            if (!bakFile.Exists)
            {
                return;
            }
#if DEBUG
            if (!(CloudDirectories.Count() == 1))
            {
                throw new InvalidOperationException("Backup called without cloud directories set to a single directory");
            }
#endif
            string uniqueFileNameSuffix = '_' + LocalStudyCentres.First().DuplicateIdCheck.ToString("N");
            string cloudDir             = CloudDirectories.First();
            string cloudZipName         = cloudDir + '\\' + Path.GetFileNameWithoutExtension(bakFileName) + uniqueFileNameSuffix + ".zip";

            var cloudFile = new FileInfo(cloudZipName);

            if (cloudFile.Exists)
            {
                DateTime?mostRecentEntry = SyncronisationResult.MostRecentEntry(_dbContext);
                if (mostRecentEntry == null || cloudFile.LastWriteTimeUtc >= mostRecentEntry)
                {
                    return;
                }
            }
            _dbContext.Dispose(); // only necessary for ce
            SyncronisationResult.RepairDb(bakFileName);
            int    dotPos         = bakFileName.LastIndexOf('.');
            string copiedFileName = bakFileName.Insert(dotPos, uniqueFileNameSuffix);
            File.Copy(bakFileName, copiedFileName, true);

            void work()
            {
                BackupHelper.ZipVerifyAndPutInCloudDir(copiedFileName, cloudDir);
            }

            new Thread(work).Start();
            _dbContext = _createContext.Invoke();
        }
        public static void CreateAllocation(Participant participant, ITrialDataContext context)
        {
            //try
            //{
            if (participant.TrialArm != RandomisationArm.NotSet)
            {
                throw new InvalidOperationException("participant.TrialArm must have a value of NotSet - use forceallocation if the allocation is pre-set");
            }
            var            currentBlock = Get1stUnfilledBlock(participant, out RandomisationStrata strata, context);
            BlockComponent component    = currentBlock?.GetComponents();

            if (currentBlock == null || context.Participants.Count(p => p.AllocationBlockId == currentBlock.Id) == component.TotalBlockSize())
            {
                currentBlock = CreateNewAllocationBlock(participant, strata, out component, context);
            }
            participant.AllocationBlockId = currentBlock.Id;
            participant.Block             = currentBlock;
            participant.TrialArm          = BlockRandomisation.NextAllocation(from p in context.Participants
                                                                              where p.AllocationBlockId == currentBlock.Id
                                                                              select p.TrialArm, component);
        }
        public static void ForceAllocationToArm(Participant participant, ITrialDataContext context)
        {
            if (participant.TrialArm == RandomisationArm.NotSet)
            {
                throw new InvalidOperationException("participant.TrialArm must be set before calling this method");
            }
            var currentBlock = Get1stBlockWithSpaceForSpecificAllocation(participant, out RandomisationStrata strata, context);

            if (currentBlock == null)
            {
                currentBlock = GetDescendingBlocks(participant.Centre ?? (participant.Centre = context.StudyCentres.Find(participant.CentreId)), strata, context).FirstOrDefault();
                if (currentBlock == null)
                {
                    currentBlock = CreateNewAllocationBlock(participant, strata, out _, context);
                }
                else
                {
                    currentBlock.GroupRepeats++;
                }
            }
            participant.AllocationBlockId = currentBlock.Id;
            participant.Block             = currentBlock;
        }
        static AllocationBlock CreateNewAllocationBlock(Participant participant, RandomisationStrata strata, out BlockComponent component, ITrialDataContext context)
        {
            var block = GetNextAllocationGroup(participant, strata, context);

            component = ArmData.GetRatio(block);
            if (participant.Centre == null)
            {
                participant.Centre = context.StudyCentres.Find(participant.CentreId);
            }
            var returnVar = new AllocationBlock
            {
                Id = context.AllocationBlocks.GetNextId(participant.CentreId, participant.Centre.MaxIdForSite),
                AllocationGroup       = block,
                GroupRepeats          = component.Repeats,
                RandomisationCategory = strata
            };

            context.AllocationBlocks.Add(returnVar);

            return(returnVar);
        }
Beispiel #10
0
 static IOrderedQueryable <AllocationBlock> GetDescendingBlocks(StudyCentre centre, RandomisationStrata strata, ITrialDataContext context)
 {
     return(from b in context.AllocationBlocks
            where b.RandomisationCategory == strata && b.Id >= centre.Id && b.Id <= centre.MaxIdForSite
            orderby b.Id descending
            select b);
 }
Beispiel #11
0
        static AllocationGroups GetNextAllocationGroup(Participant participant, RandomisationStrata strata, ITrialDataContext context)
        {
            AllocationGroups returnVar = (participant.Centre ?? (participant.Centre = context.StudyCentres.Find(participant.CentreId))).DefaultAllocation;

            if (returnVar == AllocationGroups.India3ArmUnbalanced)
            {
                var alloc = context.BalancedAllocations.First(a => a.RandomisationCategory == strata && a.StudyCentreId == participant.CentreId);
                if (!alloc.IsEqualised)
                {
                    var catQuery = from p in context.Participants
                                   where p.CentreId == participant.CentreId && p.Block.RandomisationCategory == strata
                                   select p;
                    if ((double)catQuery.Count() / catQuery.Count(p => p.TrialArm == RandomisationArm.DanishBcg) <= 3)
                    {
                        alloc.IsEqualised = true;
                        context.SaveChanges(true);
                        if (context.BalancedAllocations.All(a => a.IsEqualised && a.StudyCentreId == participant.CentreId))
                        {
                            participant.Centre.DefaultAllocation = AllocationGroups.India3ArmBalanced;
                        }
                    }
                }
                if (alloc.IsEqualised)
                {
                    return(AllocationGroups.India3ArmBalanced);
                }
            }
            return(returnVar);
        }
Beispiel #12
0
        public static AllocationBlock Get1stUnfilledBlock(Participant participant, out RandomisationStrata strata, ITrialDataContext context)
        {
            const string queryTemplate =
                "SELECT [Id]"
                + ",[GroupRepeats]"
                + ",[AllocationGroup]"
                + ",[RandomisationCategory]"
                + ",[RecordLastModified]"
                + " FROM [AllocationBlocks] a"
                + " JOIN"
                + " (SELECT AllocationBlockId, COUNT(Id) partCount"
                + " FROM Participants"
                + " WHERE Participants.CentreId={0}"
                + " GROUP BY Participants.AllocationBlockId) s"
                + " ON s.AllocationBlockId = a.id"
                + " WHERE a.RandomisationCategory={1} and s.partCount < GroupRepeats *(case a.AllocationGroup {2} end);";
            string casestring = string.Join(" ", GetBaseCounts()
                                            .Select(kv => string.Format(" when {0} then {1}", (int)kv.Key, kv.Value)));

            strata = RandomisingExtensions.RandomisationCategory(participant);
            string query = string.Format(queryTemplate,
                                         participant.CentreId,
                                         (int)strata,
                                         casestring);

            return(context.AllocationBlocks.SqlQuery(query).FirstOrDefault());
        }