Beispiel #1
0
        private void CustomizePartitionStorageConfiguration(GridViewRow row)
        {
            ServerPartition partition = row.DataItem as ServerPartition;
            Label           lbl       = row.FindControl("PartitionStorageConfigurationLabel") as Label; // The label is added in the template

            if (lbl != null)
            {
                if (partition.HasEnabledDeleteRules)
                {
                    lbl.Text = Resources.SR.PartitionStorageConfiguration_DeleteRuleExists;
                }
                else
                {
                    lbl.Text = partition.ArchiveExists
                            ? Resources.SR.PartitionStorageConfiguration_ArchiveConfiguredNoDeleteRule
                            : Resources.SR.PartitionStorageConfiguration_NoArchiveConfiguredNoDeleteRule;
                }
            }
        }
Beispiel #2
0
        //TODO: Consolidate this and DeleteStudy?
        public void DeleteSeries(Study study, IList <Series> series, string reason)
        {
            // Load the Partition
            var             partitionConfigController = new ServerPartitionConfigController();
            ServerPartition partition = partitionConfigController.GetPartition(study.ServerPartitionKey);

            var seriesUids = new List <string>();

            foreach (Series s in series)
            {
                seriesUids.Add(s.SeriesInstanceUid);
            }

            using (IUpdateContext ctx = PersistentStoreRegistry.GetDefaultStore().OpenUpdateContext(UpdateContextSyncMode.Flush))
            {
                StudyDeleteHelper.DeleteSeries(ctx, partition, study.StudyInstanceUid, seriesUids, reason);
                ctx.Commit();
            }
        }
        protected override void OnPreRender(EventArgs e)
        {
            foreach (GridViewRow row in TheGrid.Rows)
            {
                if (row.RowType == DataControlRowType.DataRow)
                {
                    ServerPartition partition = Partitions[row.RowIndex];

                    if (partition != null)
                    {
                        if (_theController.CanDelete(partition))
                        {
                            row.Attributes.Add("candelete", "true");
                        }
                    }
                }
            }
            base.OnPreRender(e);
        }
Beispiel #4
0
        /// <summary>
        /// Inserts delete request(s) to delete a series in a study.
        /// </summary>
        /// <param name="context">The persistence context used for database connection.</param>
        /// <param name="partition">The <see cref="ServerPartition"/> where the study resides</param>
        /// <param name="studyInstanceUid">The Study Instance Uid of the study</param>
        /// <param name="seriesInstanceUids">The Series Instance Uid of the series to be deleted.</param>
        /// <param name="reason">The reason for deleting the series.</param>
        /// <returns>A list of DeleteSeries <see cref="WorkQueue"/> entries inserted into the system.</returns>
        /// <exception cref="InvalidStudyStateOperationException"></exception>
        public static WorkQueue DeleteSeries(IUpdateContext context, ServerPartition partition, string studyInstanceUid,
                                             List <string> seriesInstanceUids, string reason)
        {
            StudyStorageLocation location = FindStudyStorageLocation(context, partition, studyInstanceUid);

            string failureReason;

            try
            {
                if (LockStudyForDeletion(location.Key, out failureReason))
                {
                    WorkQueue deleteRequest = null;

                    // insert a delete series request
                    foreach (var uid in seriesInstanceUids)
                    {
                        deleteRequest = InsertDeleteSeriesRequest(context, location, uid, reason);
                        if (deleteRequest == null)
                        {
                            throw new ApplicationException(
                                      String.Format("Unable to insert a Delete Series request for series {0} in study {1}",
                                                    uid, location.StudyInstanceUid));
                        }
                    }

                    return(deleteRequest);
                }
            }
            catch (Exception ex)
            {
                Platform.Log(LogLevel.Error, ex, "Errors occurred when trying to insert series delete request");

                if (!ReleaseDeletionLock(location.Key))
                {
                    Platform.Log(LogLevel.Error, "Unable to unlock the study: " + location.StudyInstanceUid);
                }

                throw;
            }

            throw new ApplicationException(
                      String.Format("Unable to lock storage location {0} for deletion : {1}", location.Key, failureReason));
        }
Beispiel #5
0
        public bool MoveStudy(Study study, Device device, IList <Series> seriesList)
        {
            if (seriesList != null)
            {
                using (
                    IUpdateContext context = PersistentStoreRegistry.GetDefaultStore().OpenUpdateContext(UpdateContextSyncMode.Flush))
                {
                    ServerPartition partition = ServerPartition.Load(study.ServerPartitionKey);

                    List <string> seriesUids = new List <string>();
                    foreach (Series series in seriesList)
                    {
                        seriesUids.Add(series.SeriesInstanceUid);
                    }

                    IList <WorkQueue> entries = StudyEditorHelper.MoveSeries(context, partition, study.StudyInstanceUid, device.Key, seriesUids);
                    if (entries != null)
                    {
                        context.Commit();
                    }

                    return(true);
                }
            }
            WorkQueueAdaptor       workqueueAdaptor = new WorkQueueAdaptor();
            DateTime               time             = Platform.Time;
            WorkQueueUpdateColumns columns          = new WorkQueueUpdateColumns
            {
                WorkQueueTypeEnum   = WorkQueueTypeEnum.WebMoveStudy,
                WorkQueueStatusEnum = WorkQueueStatusEnum.Pending,
                ServerPartitionKey  = study.ServerPartitionKey,
                StudyStorageKey     = study.StudyStorageKey,
                FailureCount        = 0,
                DeviceKey           = device.Key,
                ScheduledTime       = time,
                ExpirationTime      = time.AddMinutes(4)
            };

            workqueueAdaptor.Add(columns);

            return(true);
        }
Beispiel #6
0
        /// <summary>
        /// Load <see cref="Device"/> information for a Move destination.
        /// </summary>
        /// <param name="read"></param>
        /// <param name="partition"></param>
        /// <param name="remoteAe"></param>
        /// <returns></returns>
        private static Device LoadRemoteHost(IPersistenceContext read, ServerPartition partition, string remoteAe)
        {
            var select = read.GetBroker <IDeviceEntityBroker>();

            // Setup the select parameters.
            var selectParms = new DeviceSelectCriteria();

            selectParms.AeTitle.EqualTo(remoteAe);
            selectParms.ServerPartitionKey.EqualTo(partition.GetKey());
            var devices = select.Find(selectParms);

            foreach (var d in devices)
            {
                if (string.Compare(d.AeTitle, remoteAe, false, CultureInfo.InvariantCulture) == 0)
                {
                    return(d);
                }
            }
            return(null);
        }
Beispiel #7
0
 public UpdateStudyCommand(ServerPartition partition,
                           StudyStorageLocation studyLocation,
                           IList <BaseImageLevelUpdateCommand> imageLevelCommands,
                           ServerRuleApplyTimeEnum applyTime,
                           WorkQueue workQueue)
     : base("Update existing study")
 {
     _partition        = partition;
     _oldStudyLocation = studyLocation;
     _commands         = imageLevelCommands;
     _workQueue        = workQueue;
     _statistics       = new UpdateStudyStatistics(_oldStudyLocation.StudyInstanceUid);
     // Load the engine for editing rules.
     _rulesEngine = new ServerRulesEngine(applyTime, _partition.Key);
     if (applyTime.Equals(ServerRuleApplyTimeEnum.SopProcessed))
     {
         _rulesEngine.AddIncludeType(ServerRuleTypeEnum.AutoRoute);
     }
     _rulesEngine.Load();
 }
Beispiel #8
0
        /// <summary>
        /// Checks if the specified user is allowed to access this partition.
        /// </summary>
        /// <returns></returns>
        public static bool IsUserAccessAllowed(this ServerPartition partition, CustomPrincipal user)
        {
            Platform.CheckForNullReference(user, "user cannot be null");

            if (partition.ServerPartitionTypeEnum.Equals(ServerPartitionTypeEnum.VFS))
            {
                return(user.IsInRole(AuthorityTokens.Vfs.ViewPartitions));
            }

            // If user has the "access all" token, return true
            if (user.IsInRole(MatrixPACS.Enterprise.Common.AuthorityTokens.DataAccess.AllPartitions))
            {
                return(true);
            }

            // If user belongs to any data access authority group which can access the partition, return true
            var isAllowed = user.Credentials.DataAccessAuthorityGroups != null &&
                            user.Credentials.DataAccessAuthorityGroups.Any(g => partition.IsAuthorityGroupAllowed(g.ToString()));

            return(isAllowed);
        }
        protected void Page_Load(object sender, EventArgs e)
        {
            if (Page.IsPostBack)
            {
                if (ViewState["_Mode"] != null)
                {
                    _mode = (AddEditDataRuleDialogMode)ViewState["_Mode"];
                }

                if (ViewState["_ServerPartition"] != null)
                {
                    _partition = (ServerPartition)ViewState["_ServerPartition"];
                }

                if (ViewState["_EdittedRule"] != null)
                {
                    var ruleKey = ViewState["_EdittedRule"] as ServerEntityKey;
                    _rule = ServerRule.Load(ruleKey);
                }
            }
        }
Beispiel #10
0
        /// <summary>
        /// Inserts delete request(s) to delete a series in a study.
        /// </summary>
        /// <param name="context">The persistence context used for database connection.</param>
        /// <param name="partition">The <see cref="ServerPartition"/> where the study resides</param>
        /// <param name="studyInstanceUid">The Study Instance Uid of the study</param>
        /// <param name="reason">The reason for deleting the series.</param>
        /// <returns>A list of DeleteSeries <see cref="WorkQueue"/> entries inserted into the system.</returns>
        /// <exception cref="InvalidStudyStateOperationException"></exception>
        public static WorkQueue DeleteStudy(IUpdateContext context, ServerPartition partition, string studyInstanceUid,
                                            string reason)
        {
            StudyStorageLocation location;

            FilesystemMonitor.Instance.GetWritableStudyStorageLocation(partition.Key, studyInstanceUid,
                                                                       StudyRestore.False, StudyCache.True, out location);
            string failureReason;

            try
            {
                if (LockStudyForDeletion(location.Key, out failureReason))
                {
                    WorkQueue deleteRequest = InsertDeleteStudyRequest(context, location, reason);
                    if (deleteRequest == null)
                    {
                        throw new ApplicationException(
                                  String.Format("Unable to insert a Delete Study request for study {0}",
                                                location.StudyInstanceUid));
                    }


                    return(deleteRequest);
                }
            }
            catch (Exception ex)
            {
                Platform.Log(LogLevel.Error, ex, "Errors occurred when trying to insert study delete request");

                if (!ReleaseDeletionLock(location.Key))
                {
                    Platform.Log(LogLevel.Error, "Unable to unlock the study: " + location.StudyInstanceUid);
                }

                throw;
            }

            throw new ApplicationException(
                      String.Format("Unable to lock storage location {0} for deletion : {1}", location.Key, failureReason));
        }
        protected override int OnStart(StudyLoaderArgs studyLoaderArgs)
        {
            var ae = studyLoaderArgs.Server as IDicomServiceNode;

            _ae = ae;

            EventResult      result          = EventResult.Success;
            AuditedInstances loadedInstances = new AuditedInstances();

            try
            {
                ServerPartition partition = ServerPartitionMonitor.Instance.GetPartition(_ae.AETitle);
                if (!partition.Enabled)
                {
                    throw new OfflineLoadStudyException(studyLoaderArgs.StudyInstanceUid);
                }

                FilesystemMonitor.Instance.GetReadableStudyStorageLocation(partition.Key,
                                                                           studyLoaderArgs.StudyInstanceUid,
                                                                           StudyRestore.False,
                                                                           StudyCache.True,
                                                                           out _location);

                StudyXml studyXml = _location.LoadStudyXml();

                _instances = GetInstances(studyXml).GetEnumerator();

                loadedInstances.AddInstance(studyXml.PatientId, studyXml.PatientsName, studyXml.StudyInstanceUid);

                return(studyXml.NumberOfStudyRelatedInstances);
            }
            catch (StudyIsNearlineException e)
            {
                throw new NearlineLoadStudyException(studyLoaderArgs.StudyInstanceUid, e);
            }
            finally
            {
                AuditHelper.LogOpenStudies(new[] { ae.AETitle }, loadedInstances, EventSource.CurrentUser, result);
            }
        }
        private void SaveData()
        {
            if (Partition == null)
            {
                Partition = new ServerPartition {
                    ServerPartitionTypeEnum = ServerPartitionTypeEnum.Standard
                };
            }


            Partition.Enabled         = EnabledCheckBox.Checked;
            Partition.AeTitle         = AETitleTextBox.Text;
            Partition.Description     = DescriptionTextBox.Text;
            Partition.PartitionFolder = PartitionFolderTextBox.Text;

            int port;

            if (Int32.TryParse(PortTextBox.Text, out port))
            {
                Partition.Port = port;
            }

            Partition.AcceptAnyDevice  = AcceptAnyDeviceCheckBox.Checked;
            Partition.AutoInsertDevice = AutoInsertDeviceCheckBox.Checked;
            if (Int32.TryParse(DefaultRemotePortTextBox.Text, out port))
            {
                Partition.DefaultRemotePort = port;
            }

            Partition.DuplicateSopPolicyEnum = DuplicateSopPolicyEnum.GetAll()[DuplicateSopDropDownList.SelectedIndex];
            Partition.AcceptLatestReport     = AcceptLatestReportCheckBox.Checked;
            Partition.MatchPatientsName      = MatchPatientName.Checked;
            Partition.MatchPatientId         = MatchPatientID.Checked;
            Partition.MatchPatientsBirthDate = MatchPatientBirthDate.Checked;
            Partition.MatchPatientsSex       = MatchPatientSex.Checked;
            Partition.MatchAccessionNumber   = MatchAccessionNumber.Checked;
            Partition.MatchIssuerOfPatientId = MatchIssuer.Checked;
            Partition.AuditDeleteStudy       = AuditDeleteStudyCheckBox.Checked;
        }
Beispiel #13
0
        private bool UpdateNameBasedOnTheStudy(DicomFile file)
        {
            bool   updated = false;
            string orginalPatientsNameInFile = file.DataSet[DicomTags.PatientsName].ToString();

            if (_theStudy == null)
            {
                return(false);
            }

            StudyComparer        comparer  = new StudyComparer();
            ServerPartition      partition = ServerPartitionMonitor.Instance.FindPartition(_theStudy.ServerPartitionKey);
            DifferenceCollection list      = comparer.Compare(file, _theStudy, partition.GetComparisonOptions());

            if (list.Count == 1)
            {
                ComparisionDifference different = list[0];
                if (different.DicomTag.TagValue == DicomTags.PatientsName)
                {
                    if (DicomNameUtils.LookLikeSameNames(orginalPatientsNameInFile, _theStudy.PatientsName))
                    {
                        using (ServerCommandProcessor processor = new ServerCommandProcessor("Update Patient's Name"))
                        {
                            SetTagCommand command = new SetTagCommand(file, DicomTags.PatientsName, orginalPatientsNameInFile, _theStudy.PatientsName);
                            processor.AddCommand(command);

                            if (!processor.Execute())
                            {
                                throw new ApplicationException(String.Format("AUTO-CORRECTION Failed: Unable to correct the patient's name in the image. Reason: {0}",
                                                                             processor.FailureReason), processor.FailureException);
                            }

                            updated = true;
                        }
                    }
                }
            }
            return(updated);
        }
Beispiel #14
0
        /// <summary>
        /// Constructor.
        /// </summary>
        /// <param name="thePartition"></param>
        /// <param name="location"></param>
        /// <param name="thePatient"></param>
        /// <param name="theStudy"></param>
        public StudyEditor(ServerPartition thePartition, StudyStorageLocation location, Patient thePatient, Study theStudy)
        {
            FailureReason = string.Empty;
            Platform.CheckForNullReference(thePartition, "thePartition");
            Platform.CheckForNullReference(location, "location");
            Platform.CheckForNullReference(thePatient, "thePatient");
            Platform.CheckForNullReference(theStudy, "theStudy");

            ServerPartition = thePartition;
            StorageLocation = location;

            Patient = thePatient;
            Study   = theStudy;

            // Scrub for invalid characters that may cause a failure when the Xml is generated for the history
            Patient.PatientId    = XmlUtils.XmlCharacterScrub(Patient.PatientId);
            Patient.PatientsName = XmlUtils.XmlCharacterScrub(Patient.PatientsName);

            Study.StudyDescription        = XmlUtils.XmlCharacterScrub(Study.StudyDescription);
            Study.ReferringPhysiciansName = XmlUtils.XmlCharacterScrub(Study.ReferringPhysiciansName);
            Study.PatientId    = XmlUtils.XmlCharacterScrub(Study.PatientId);
            Study.PatientsName = XmlUtils.XmlCharacterScrub(Study.PatientsName);
        }
Beispiel #15
0
        public HeaderLoader(HeaderStreamingContext context)
        {
            _studyInstanceUid = context.Parameters.StudyInstanceUID;
            _partitionAE      = context.Parameters.ServerAETitle;
            _statistics.FindStudyFolder.Start();
            string sessionId = context.CallerAE;

            ServerPartition partition = ServerPartitionMonitor.Instance.GetPartition(_partitionAE);

            StudyStorageLoader storageLoader = new StudyStorageLoader(sessionId);

            storageLoader.CacheEnabled       = ImageStreamingServerSettings.Default.EnableCache;
            storageLoader.CacheRetentionTime = ImageStreamingServerSettings.Default.CacheRetentionWindow;
            StudyLocation = storageLoader.Find(_studyInstanceUid, partition);

            if (StudyLocation != null && StudyLocation.QueueStudyStateEnum != QueueStudyStateEnum.Idle)
            {
                Platform.Log(LogLevel.Warn, "Accessing to study {0} while its current state is {1}",
                             StudyLocation.StudyInstanceUid, StudyLocation.QueueStudyStateEnum);
            }

            _statistics.FindStudyFolder.End();
        }
        /// <summary>
        /// Return the absolute path to the currently active Incoming folder for this partition
        /// or null if there's no incoming folder (eg, Import Service is not running)
        /// </summary>
        /// <returns></returns>
        public static string GetIncomingFolder(this ServerPartition partition)
        {
            var importServices = ServiceLock.FindServicesOfType(ServiceLockTypeEnum.ImportFiles);

            if (importServices == null || importServices.Count == 0)
            {
                return(null);
            }

            var activeService = importServices.SingleOrDefault(s => s.Enabled);

            if (activeService == null)
            {
                return(null);
            }

            var filesystem = FilesystemMonitor.Instance.GetFilesystemInfo(activeService.FilesystemKey);

            // Note: Import Service doesn't care if the filesystem is disabled or readonly so we don't need to care either
            var incomingPath = Path.Combine(filesystem.Filesystem.FilesystemPath, String.Format("{0}_{1}", partition.PartitionFolder, FilesystemMonitor.ImportDirectorySuffix));

            return(incomingPath);
        }
Beispiel #17
0
        protected override void ProcessFile(Model.WorkQueueUid queueUid, DicomFile file, ClearCanvas.Dicom.Utilities.Xml.StudyXml stream, bool compare)
        {
            Platform.CheckFalse(compare, "compare");

            SopInstanceProcessor processor = new SopInstanceProcessor(Context);

            FileInfo fileInfo = new FileInfo(file.Filename);
            long     fileSize = fileInfo.Length;

            processor.InstanceStats.FileSize = (ulong)fileSize;
            string sopInstanceUid = file.DataSet[DicomTags.SopInstanceUid].GetString(0, "File:" + fileInfo.Name);

            processor.InstanceStats.Description = sopInstanceUid;

            if (Study != null)
            {
                StudyComparer        comparer = new StudyComparer();
                DifferenceCollection list     = comparer.Compare(file, Study, ServerPartition.GetComparisonOptions());
                if (list != null && list.Count > 0)
                {
                    Platform.Log(LogLevel.Warn, "Dicom file contains information inconsistent with the study in the system");
                }
            }

            string groupID = ServerHelper.GetUidGroup(file, StorageLocation.ServerPartition, WorkQueueItem.InsertTime);

            processor.ProcessFile(groupID, file, stream, false, false, null, null);

            Statistics.StudyInstanceUid = StorageLocation.StudyInstanceUid;
            if (String.IsNullOrEmpty(processor.Modality) == false)
            {
                Statistics.Modality = processor.Modality;
            }

            // Update the statistics
            Statistics.NumInstances++;
        }
Beispiel #18
0
        private static void Validate(HttpListenerContext context)
        {
            string serverAE = UriHelper.GetServerAE(context);

            if (String.IsNullOrEmpty(serverAE))
            {
                throw new HttpException((int)HttpStatusCode.BadRequest,
                                        String.Format("Partition AE Title is required after {0}", ImageStreamingServerSettings.Default.Path));
            }

            ServerPartition partition = ServerPartitionMonitor.Instance.GetPartition(serverAE);

            if (partition == null)
            {
                throw new HttpException((int)HttpStatusCode.BadRequest, String.Format("Partition AE {0} is invalid", serverAE));
            }

            string requestType = context.Request.QueryString["requestType"] ?? "";

            if (String.IsNullOrEmpty(requestType))
            {
                throw new WADOException(HttpStatusCode.BadRequest, "RequestType parameter is missing");
            }
        }
Beispiel #19
0
        protected void Page_Load(object sender, EventArgs e)
        {
            IList <ArchiveQueueStatusEnum> statusItems = ArchiveQueueStatusEnum.GetAll();

            int prevSelectedIndex = StatusFilter.SelectedIndex;

            StatusFilter.Items.Clear();
            StatusFilter.Items.Add(new ListItem(SR.All, "All"));
            foreach (ArchiveQueueStatusEnum s in statusItems)
            {
                StatusFilter.Items.Add(new ListItem(ServerEnumDescription.GetLocalizedDescription(s), s.Lookup));
            }
            StatusFilter.SelectedIndex = prevSelectedIndex;

            DeleteItemButton.Roles       = AuthorityTokens.ArchiveQueue.Delete;
            ViewStudyDetailsButton.Roles = AuthorityTokens.Study.View;

            if (!IsPostBack && !Page.IsAsync)
            {
                string patientID    = Server.UrlDecode(Request["PatientID"]);
                string patientName  = Server.UrlDecode(Request["PatientName"]);
                string partitionKey = Server.UrlDecode(Request["PartitionKey"]);

                if (patientID != null && patientName != null && partitionKey != null)
                {
                    var controller = new ServerPartitionConfigController();
                    ServerPartition = controller.GetPartition(new ServerEntityKey("ServerPartition", partitionKey));

                    PatientId.Text   = patientID;
                    PatientName.Text = patientName;

                    ArchiveQueueItemList.SetDataSource();
                    ArchiveQueueItemList.Refresh();
                }
            }
        }
        protected void Page_Load(object sender, EventArgs e)
        {
            _studyInstanceUid = Request.QueryString[ImageServerConstants.QueryStrings.StudyInstanceUID];
            _serverae         = Request.QueryString[ImageServerConstants.QueryStrings.ServerAE];

            if (!String.IsNullOrEmpty(_studyInstanceUid) && !String.IsNullOrEmpty(_serverae))
            {
                ServerPartitionDataAdapter    adaptor  = new ServerPartitionDataAdapter();
                ServerPartitionSelectCriteria criteria = new ServerPartitionSelectCriteria();
                criteria.AeTitle.EqualTo(_serverae);
                IList <ServerPartition> partitions = adaptor.Get(criteria);
                if (partitions != null && partitions.Count > 0)
                {
                    if (partitions.Count == 1)
                    {
                        Partition = partitions[0];

                        //TODO: Do something if parition is inactive. Perhapse show an alert on the screen?

                        LoadStudy();
                    }
                    else
                    {
                        Response.Write(String.Format(ErrorMessages.MultiplePartitionsExistWithAETitle, _serverae));
                    }
                }
            }

            //Hide the UserPanel information
            IMasterProperties master = Master as IMasterProperties;

            if (master != null)
            {
                master.DisplayUserInformationPanel = false;
            }
        }
Beispiel #21
0
        /// <summary>
        /// Get an Online and Writeable <see cref="ServiceLock"/> related incoming directory.
        /// </summary>
        /// <param name="partition">The ServerPartion</param>
        /// <param name="folder">The absolute path of the output folder</param>
        /// <returns>true on a found writeable path, false on failure or no writeable path</returns>
        public bool GetWriteableIncomingFolder(ServerPartition partition, out string folder)
        {
            using (ServerExecutionContext context = new ServerExecutionContext())
            {
                IServiceLockEntityBroker  broker   = context.ReadContext.GetBroker <IServiceLockEntityBroker>();
                ServiceLockSelectCriteria criteria = new ServiceLockSelectCriteria();
                criteria.ServiceLockTypeEnum.EqualTo(ServiceLockTypeEnum.ImportFiles);

                IList <ServiceLock> rows = broker.Find(criteria);
                foreach (ServiceLock serviceLock in rows)
                {
                    if (!serviceLock.Enabled)
                    {
                        continue;
                    }

                    string reason;
                    if (!CheckFilesystemOnline(serviceLock.FilesystemKey, out reason))
                    {
                        continue;
                    }

                    if (!CheckFilesystemWriteable(serviceLock.FilesystemKey, out reason))
                    {
                        continue;
                    }

                    String incomingFolder = String.Format("{0}_{1}", partition.PartitionFolder, ImportDirectorySuffix);
                    folder = serviceLock.Filesystem.GetAbsolutePath(incomingFolder);
                    return(true);
                }

                folder = string.Empty;
                return(false);
            }
        }
Beispiel #22
0
        private static IList <StudySummary> LoadStudies(WebViewerInitParams initParams)
        {
            ValidateParameters(initParams);

            var controller       = new StudyController();
            var partitionAdapter = new ServerPartitionDataAdapter();
            StudySelectCriteria studyCriteria;
            var                 partitionCriteria = new ServerPartitionSelectCriteria();
            ServerPartition     partition         = null;
            IList <Study>       studies;
            List <StudySummary> totalStudies = new List <StudySummary>();

            if (!string.IsNullOrEmpty(initParams.AeTitle))
            {
                partitionCriteria.AeTitle.EqualTo(initParams.AeTitle);
                IList <ServerPartition> partitions = partitionAdapter.GetServerPartitions(partitionCriteria);
                if (partitions.Count == 1)
                {
                    partition = partitions[0];
                }
            }

            foreach (string patientId in initParams.PatientIds)
            {
                studyCriteria = new StudySelectCriteria();
                if (partition != null)
                {
                    studyCriteria.ServerPartitionKey.EqualTo(partition.Key);
                }
                SetStringCondition(studyCriteria.PatientId, patientId);
                studyCriteria.StudyDate.SortDesc(0);
                studies = controller.GetStudies(studyCriteria);

                foreach (Study study in studies)
                {
                    totalStudies.Add(StudySummaryAssembler.CreateStudySummary(HttpContextData.Current.ReadContext, study));
                }
            }

            foreach (string accession in initParams.AccessionNumbers)
            {
                studyCriteria = new StudySelectCriteria();
                if (partition != null)
                {
                    studyCriteria.ServerPartitionKey.EqualTo(partition.Key);
                }
                SetStringCondition(studyCriteria.AccessionNumber, accession);
                studyCriteria.StudyDate.SortDesc(0);
                studies = controller.GetStudies(studyCriteria);

                foreach (Study study in studies)
                {
                    totalStudies.Add(StudySummaryAssembler.CreateStudySummary(HttpContextData.Current.ReadContext, study));
                }
            }

            if (initParams.StudyInstanceUids.Count > 0)
            {
                studyCriteria = new StudySelectCriteria();
                if (partition != null)
                {
                    studyCriteria.ServerPartitionKey.EqualTo(partition.Key);
                }
                studyCriteria.StudyInstanceUid.In(initParams.StudyInstanceUids);
                studyCriteria.StudyDate.SortDesc(0);
                studies = controller.GetStudies(studyCriteria);

                foreach (Study study in studies)
                {
                    totalStudies.Add(StudySummaryAssembler.CreateStudySummary(HttpContextData.Current.ReadContext, study));
                }
            }

            totalStudies.Sort((a, b) => a.StudyDate.CompareTo(b.StudyDate) * -1);

            return(totalStudies);
        }
Beispiel #23
0
        private void DoStudyLevelValidation(StudyStorageLocation storageLocation, StudyXml studyXml, Study study, ServerPartition partition)
        {
            int xmlNumInstances = studyXml.NumberOfStudyRelatedInstances;
            int xmlNumSeries    = studyXml.NumberOfStudyRelatedSeries;

            if (study.NumberOfStudyRelatedInstances != xmlNumInstances)
            {
                throw new StudyIntegrityValidationFailure(
                          ValidationErrors.InconsistentObjectCount,
                          new ValidationStudyInfo(study, partition),
                          String.Format("Number of study related instances in the database ({0}) does not match number of images in the filesystem ({1})",
                                        study.NumberOfStudyRelatedInstances, xmlNumInstances));
            }

            if (study.NumberOfStudyRelatedSeries != xmlNumSeries)
            {
                throw new StudyIntegrityValidationFailure(ValidationErrors.InconsistentObjectCount,
                                                          new ValidationStudyInfo(study, partition),
                                                          String.Format("Number of study related series in the database ({0}) does not match number of series in the xml ({1})",
                                                                        study.NumberOfStudyRelatedSeries, xmlNumSeries));
            }


            long dirFileCount = DirectoryUtility.Count(storageLocation.GetStudyPath(),
                                                       "*" + ServerPlatform.DicomFileExtension, true, null);

            if (xmlNumInstances != dirFileCount)
            {
                throw new StudyIntegrityValidationFailure(ValidationErrors.InconsistentObjectCount,
                                                          new ValidationStudyInfo(study, partition),
                                                          String.Format("Number of instance in xml ({0}) does not match number of images in the filesystem ({1})",
                                                                        xmlNumInstances, dirFileCount));
            }
        }
        public ServerEntityKey GetCurrentPartitionKey()
        {
            ServerPartition partition = GetCurrentPartition();

            return(partition != null ? partition.Key : null);
        }
Beispiel #25
0
 public StudyRulesEngine(StudyStorageLocation location, ServerPartition partition)
 {
     _location  = location;
     _partition = partition ?? ServerPartition.Load(_location.ServerPartitionKey);
 }
Beispiel #26
0
        /// <summary>
        /// Checks for a storage location for the study in the database, and creates a new location
        /// in the database if it doesn't exist.
        /// </summary>
        /// <param name="partition">The partition where the study is being sent to</param>
        /// <param name="created"></param>
        /// <param name="studyDate"></param>
        /// <param name="studyInstanceUid"></param>
        /// <param name="syntax"></param>
        /// <param name="updateContext">The update context to create the study on</param>
        /// <returns>A <see cref="StudyStorageLocation"/> instance.</returns>
        public StudyStorageLocation GetOrCreateWritableStudyStorageLocation(string studyInstanceUid, string studyDate, TransferSyntax syntax, IUpdateContext updateContext, ServerPartition partition, out bool created)
        {
            created = false;

            StudyStorageLocation location;

            try
            {
                GetWritableStudyStorageLocation(partition.Key, studyInstanceUid, StudyRestore.True,
                                                StudyCache.True, out location);
                return(location);
            }
            catch (StudyNotFoundException)
            {
            }

            FilesystemSelector   selector   = new FilesystemSelector(Instance);
            ServerFilesystemInfo filesystem = selector.SelectFilesystem();

            if (filesystem == null)
            {
                throw new NoWritableFilesystemException();
            }

            IInsertStudyStorage          locInsert   = updateContext.GetBroker <IInsertStudyStorage>();
            InsertStudyStorageParameters insertParms = new InsertStudyStorageParameters
            {
                ServerPartitionKey = partition.GetKey(),
                StudyInstanceUid   = studyInstanceUid,
                Folder             =
                    ResolveStorageFolder(partition.Key, studyInstanceUid, studyDate,
                                         updateContext, false
                                         /* set to false for optimization because we are sure it's not in the system */),
                FilesystemKey       = filesystem.Filesystem.GetKey(),
                QueueStudyStateEnum = QueueStudyStateEnum.Idle
            };

            if (syntax.LosslessCompressed)
            {
                insertParms.TransferSyntaxUid = syntax.UidString;
                insertParms.StudyStatusEnum   = StudyStatusEnum.OnlineLossless;
            }
            else if (syntax.LossyCompressed)
            {
                insertParms.TransferSyntaxUid = syntax.UidString;
                insertParms.StudyStatusEnum   = StudyStatusEnum.OnlineLossy;
            }
            else
            {
                insertParms.TransferSyntaxUid = syntax.UidString;
                insertParms.StudyStatusEnum   = StudyStatusEnum.Online;
            }

            location = locInsert.FindOne(insertParms);
            created  = true;

            return(location);
        }
Beispiel #27
0
        private void _buttonGenerate_Click(object sender, EventArgs e)
        {
            int totalStudies;
            int studiesPerDay;

            if (!int.TryParse(_textBoxTotalStudies.Text, out totalStudies))
            {
                totalStudies = 50000;
            }
            if (!int.TryParse(_textBoxStudiesPerDay.Text, out studiesPerDay))
            {
                studiesPerDay = 1800;
            }

            if (_checkBoxImageServerDatabase.Checked)
            {
                if (_comboBoxServerPartition.SelectedItem == null)
                {
                    return;
                }

                ServerPartition selectedPartition = _comboBoxServerPartition.SelectedItem as ServerPartition;
                if (selectedPartition == null)
                {
                    return;
                }

                _generator = new ImageServerDbGenerator(selectedPartition, _dateTimePickerStart.Value, totalStudies,
                                                        studiesPerDay,
                                                        (int)_numericUpDownPercentWeekend.Value);
            }
            else
            {
                _generator = new ImageServerDbGenerator(_textBoxRemoteAETitle.Text, _textBoxHost.Text,
                                                        int.Parse(_textBoxPort.Text), _dateTimePickerStart.Value,
                                                        totalStudies,
                                                        studiesPerDay,
                                                        (int)_numericUpDownPercentWeekend.Value);
            }
            _progressBar.Maximum = 0;
            _progressBar.Maximum = 100;
            _generator.RegisterProgressUpated(ProgressUpdated);

            if (_checkBoxMR.Checked)
            {
                _generator.AddSopGenerator(new MrSopGenerator(_hospital1));
                _generator.AddSopGenerator(new MrSopGenerator(_hospital2));
                _generator.AddSopGenerator(new MrSopGenerator(_hospital3));
            }
            if (_checkBoxCT.Checked)
            {
                _generator.AddSopGenerator(new CtSopGenerator(_hospital1));
                _generator.AddSopGenerator(new CtSopGenerator(_hospital4));
                _generator.AddSopGenerator(new CtSopGenerator(_hospital3));
            }
            if (_checkBoxCR.Checked)
            {
                _generator.AddSopGenerator(new CrSopGenerator(_hospital1));
                _generator.AddSopGenerator(new CrSopGenerator(_hospital3));
            }
            if (_checkBoxDX.Checked)
            {
                _generator.AddSopGenerator(new DxSopGenerator(_hospital1));
                _generator.AddSopGenerator(new DxSopGenerator(_hospital4));
            }
            if (_checkBoxRF.Checked)
            {
                _generator.AddSopGenerator(new RfSopGenerator(_hospital2));
            }
            if (_checkBoxXA.Checked)
            {
                _generator.AddSopGenerator(new XaSopGenerator(_hospital1));
            }
            if (_checkBoxMG.Checked)
            {
                _generator.AddSopGenerator(new MgSopGenerator(_hospital1));
                _generator.AddSopGenerator(new MgSopGenerator(_hospital2));
            }
            if (_checkBoxUS.Checked)
            {
                _generator.AddSopGenerator(new UsSopGenerator(_hospital1));
                _generator.AddSopGenerator(new UsSopGenerator(_hospital4));
                _generator.AddSopGenerator(new UsSopGenerator(_hospital3));
            }



            _buttonCancel.Enabled   = true;
            _buttonGenerate.Enabled = false;

            _generator.Start();
        }
Beispiel #28
0
 public DicomScpContext(ServerPartition partition)
 {
     Partition = partition;
 }
Beispiel #29
0
 public StudyRulesEngine(ServerRulesEngine studyRulesEngine, StudyStorageLocation location, ServerPartition partition, StudyXml studyXml)
 {
     _studyRulesEngine = studyRulesEngine;
     _studyXml         = studyXml;
     _location         = location;
     _partition        = partition ?? ServerPartition.Load(_location.ServerPartitionKey);
 }
Beispiel #30
0
        /// <summary>
        /// Returns an instance of <see cref="StudySummary"/> based on a <see cref="Study"/> object.
        /// </summary>
        /// <param name="study"></param>
        /// <param name="read"></param>
        /// <returns></returns>
        /// <remark>
        ///
        /// </remark>
        static public StudySummary CreateStudySummary(IPersistenceContext read, Study study)
        {
            if (study == null)
            {
                return(null);
            }

            var studySummary = new StudySummary();
            var controller   = new StudyController();

            studySummary.TheStudy = study;

            studySummary.Key             = study.GetKey();
            studySummary.AccessionNumber = study.AccessionNumber;
            studySummary.NumberOfStudyRelatedInstances = study.NumberOfStudyRelatedInstances;
            studySummary.NumberOfStudyRelatedSeries    = study.NumberOfStudyRelatedSeries;
            studySummary.PatientId               = study.PatientId;
            studySummary.PatientsName            = study.PatientsName;
            studySummary.StudyDate               = study.StudyDate;
            studySummary.StudyInstanceUid        = study.StudyInstanceUid;
            studySummary.StudyDescription        = study.StudyDescription;
            studySummary.ModalitiesInStudy       = controller.GetModalitiesInStudy(read, study);
            studySummary.ReferringPhysiciansName = study.ReferringPhysiciansName;
            studySummary.ResponsibleOrganization = study.ResponsibleOrganization;
            studySummary.ResponsiblePerson       = study.ResponsiblePerson;
            studySummary.StudyTime               = study.StudyTime;
            studySummary.StudyId  = study.StudyId;
            studySummary.HasOrder = study.OrderKey != null;

            if (study.OrderKey != null)
            {
                var order = Order.Load(study.OrderKey);
                studySummary.OrderRequiresQC = order.QCExpected;
                studySummary.StudyIsQCed     = (study.QCStatusEnum != null && study.QCStatusEnum != QCStatusEnum.NA);
            }



            studySummary.ThePartition = ServerPartitionMonitor.Instance.FindPartition(study.ServerPartitionKey) ??
                                        ServerPartition.Load(read, study.ServerPartitionKey);

            studySummary.ReferringPhysiciansName = study.ReferringPhysiciansName;
            studySummary.TheStudyStorage         = StudyStorage.Load(read, study.StudyStorageKey);
            studySummary.StudyStatusEnum         = studySummary.TheStudyStorage.StudyStatusEnum;
            studySummary.QueueStudyStateEnum     = studySummary.TheStudyStorage.QueueStudyStateEnum;

            studySummary.TheArchiveLocation = controller.GetFirstArchiveStudyStorage(read, studySummary.TheStudyStorage.Key);

            studySummary.IsArchiving = controller.GetArchiveQueueCount(study) > 0;

            studySummary.IsProcessing = studySummary.TheStudyStorage.WriteLock;

            // the study is considered "locked" if it's being processed or some action which requires the lock has been scheduled
            // No additional action should be allowed on the study until everything is completed.
            studySummary.IsLocked = studySummary.IsProcessing ||
                                    (studySummary.TheStudyStorage.QueueStudyStateEnum != QueueStudyStateEnum.Idle);

            if (controller.GetStudyIntegrityQueueCount(studySummary.TheStudyStorage.Key) > 0)
            {
                studySummary.IsReconcileRequired = true;
            }

            studySummary.HasPendingExternalEdit = controller.GetCountPendingExternalEditWorkQueueItems(study) > 0;
            if (studySummary.HasPendingExternalEdit)
            {
                studySummary.HasPendingWorkQueueItems = true;
            }
            else
            {
                studySummary.HasPendingWorkQueueItems = controller.GetCountPendingWorkQueueItems(study) > 0;
            }

            var ep = new StudySummaryAssemblerExtensionPoint();

            foreach (IStudySummaryAssembler assemblerPlugin in ep.CreateExtensions())
            {
                assemblerPlugin.PopulateStudy(studySummary, study);
            }

            return(studySummary);
        }
        public void Insert(Guid Guid, bool Enabled, string Description, string AeTitle, int Port, string PartitionFolder,
                           bool AcceptAnyDevice, bool AuditDeleteStudy, bool AutoInsertDevice, int DefaultRemotePort,
                           int StudyCount, short DuplicateSopPolicyEnum, bool MatchAccessionNumber,
                           bool MatchIssuerOfPatientId, bool MatchPatientId, bool MatchPatientsBirthDate,
                           bool MatchPatientsName, bool MatchPatientsSex)
        {
            var item = new ServerPartition();

            item.Guid = Guid;

            item.Enabled = Enabled;

            item.Description = Description;

            item.AeTitle = AeTitle;

            item.Port = Port;

            item.PartitionFolder = PartitionFolder;

            item.AcceptAnyDevice = AcceptAnyDevice;

            item.AuditDeleteStudy = AuditDeleteStudy;

            item.AutoInsertDevice = AutoInsertDevice;

            item.DefaultRemotePort = DefaultRemotePort;

            item.StudyCount = StudyCount;

            item.DuplicateSopPolicyEnum = DuplicateSopPolicyEnum;

            item.MatchAccessionNumber = MatchAccessionNumber;

            item.MatchIssuerOfPatientId = MatchIssuerOfPatientId;

            item.MatchPatientId = MatchPatientId;

            item.MatchPatientsBirthDate = MatchPatientsBirthDate;

            item.MatchPatientsName = MatchPatientsName;

            item.MatchPatientsSex = MatchPatientsSex;


            item.Save(UserName);
        }