public void SendStudy(IDicomServiceNode remoteAEInfo, IStudyRootData study, WorkItemPriorityEnum priority) { EventResult result = EventResult.Success; try { var request = new DicomSendStudyRequest { DestinationServerName = remoteAEInfo.Name, Priority = priority, Study = new WorkItemStudy(study), Patient = new WorkItemPatient(study) }; InsertRequest(request, new DicomSendProgress()); } catch (Exception ex) { result = EventResult.MajorFailure; Exception = ex; Platform.Log(LogLevel.Error, ex, Common.SR.MessageFailedToSendStudy); throw; } finally { var instances = new AuditedInstances(); instances.AddInstance(study.PatientId, study.PatientsName, study.StudyInstanceUid); AuditHelper.LogBeginSendInstances(remoteAEInfo.AETitle, remoteAEInfo.ScpParameters.HostName, instances, string.IsNullOrEmpty(Request.UserName) ? EventSource.CurrentProcess : EventSource.CurrentUser, result); } }
public void RetrieveSeries(IDicomServiceNode remoteAEInfo, IStudyRootData study, string[] seriesInstanceUids) { EventResult result = EventResult.Success; try { var request = new DicomRetrieveSeriesRequest { ServerName = remoteAEInfo.Name, SeriesInstanceUids = new List <string>(), Study = new WorkItemStudy(study), Patient = new WorkItemPatient(study) }; request.SeriesInstanceUids.AddRange(seriesInstanceUids); InsertRequest(request, new DicomRetrieveProgress()); } catch (Exception ex) { result = EventResult.MajorFailure; Exception = ex; throw; } finally { var instances = new AuditedInstances(); instances.AddInstance(study.PatientId, study.PatientsName, study.StudyInstanceUid); AuditHelper.LogBeginReceiveInstances(remoteAEInfo.AETitle, remoteAEInfo.ScpParameters.HostName, instances, string.IsNullOrEmpty(Request.UserName) ? EventSource.CurrentProcess : EventSource.CurrentUser, result); } }
private static AuditedInstances GetInstancesForAudit(IEnumerable <IClipboardItem> itemsToExport, string exportFilePath) { AuditedInstances exportedInstances = new AuditedInstances(); foreach (ClipboardItem clipboardItem in itemsToExport) { if (clipboardItem.Item is IPresentationImage && clipboardItem.Item is IImageSopProvider) { IImageSopProvider sopProv = (IImageSopProvider)clipboardItem.Item; exportedInstances.AddInstance(sopProv.ImageSop.PatientId, sopProv.ImageSop.PatientsName, sopProv.ImageSop.StudyInstanceUid, exportFilePath); } else if (clipboardItem.Item is IDisplaySet) { foreach (IPresentationImage image in ((IDisplaySet)clipboardItem.Item).PresentationImages) { IImageSopProvider sopProv = image as IImageSopProvider; if (sopProv != null) { exportedInstances.AddInstance(sopProv.ImageSop.PatientId, sopProv.ImageSop.PatientsName, sopProv.ImageSop.StudyInstanceUid, exportFilePath); } } } } return(exportedInstances); }
protected override int OnStart(StudyLoaderArgs studyLoaderArgs) { _sops = null; EventResult result = EventResult.Success; var loadedInstances = new AuditedInstances(); try { using (var context = new DataAccessContext()) { IStudy study = context.GetStudyBroker().GetStudy(studyLoaderArgs.StudyInstanceUid); if (study == null) { result = EventResult.MajorFailure; loadedInstances.AddInstance(studyLoaderArgs.StudyInstanceUid); throw new NotFoundLoadStudyException(studyLoaderArgs.StudyInstanceUid); } loadedInstances.AddInstance(study.PatientId, study.PatientsName, study.StudyInstanceUid); _sops = study.GetSopInstances().GetEnumerator(); return(study.NumberOfStudyRelatedInstances); } } finally { AuditHelper.LogOpenStudies(new[] { AuditHelper.LocalAETitle }, loadedInstances, EventSource.CurrentUser, result); } }
protected void LoadImportContext(ServerAssociationParameters association) { _importContext = new DicomReceiveImportContext(association.CallingAE, GetRemoteHostName(association), StudyStore.GetConfiguration(), EventSource.CurrentProcess); // Publish new WorkItems as they're added to the context lock (_importContext.StudyWorkItemsSyncLock) { _importContext.StudyWorkItems.ItemAdded += (sender, args) => { _importContext.PublishWorkItemActivity(WorkItemDataHelper.FromWorkItem(args.Item)); var auditedInstances = new AuditedInstances(); var request = args.Item.Request as DicomReceiveRequest; if (request != null) { auditedInstances.AddInstance(request.Patient.PatientId, request.Patient.PatientsName, request.Study.StudyInstanceUid); } AuditHelper.LogReceivedInstances( association.CallingAE, GetRemoteHostName(association), auditedInstances, EventSource.CurrentProcess, EventResult.Success, EventReceiptAction.ActionUnknown); }; _importContext.StudyWorkItems.ItemChanged += (sender, args) => _importContext.PublishWorkItemActivity(WorkItemDataHelper.FromWorkItem(args.Item)); } }
public void DeleteStudy(IStudyRootData study) { EventResult result = EventResult.Success; try { var request = new DeleteStudyRequest { Study = new WorkItemStudy(study), Patient = new WorkItemPatient(study) }; InsertRequest(request, new DeleteProgress()); } catch (Exception ex) { result = EventResult.MajorFailure; Exception = ex; throw; } finally { var instances = new AuditedInstances(); instances.AddInstance(study.PatientId, study.PatientsName, study.StudyInstanceUid); AuditHelper.LogDeleteStudies(AuditHelper.LocalAETitle, instances, EventSource.CurrentUser, result); } }
private void AuditSendOperation(bool noExceptions) { if (noExceptions) { var sentInstances = new AuditedInstances(); var failedInstances = new AuditedInstances(); foreach (StorageInstance instance in StorageInstanceList) { if (instance.SendStatus.Status == DicomState.Success) { sentInstances.AddInstance(instance.PatientId, instance.PatientsName, instance.StudyInstanceUid); } else { failedInstances.AddInstance(instance.PatientId, instance.PatientsName, instance.StudyInstanceUid); } } AuditHelper.LogSentInstances(RemoteAE, RemoteHost, sentInstances, EventSource.CurrentProcess, EventResult.Success); AuditHelper.LogSentInstances(RemoteAE, RemoteHost, failedInstances, EventSource.CurrentProcess, EventResult.MinorFailure); } else { var sentInstances = new AuditedInstances(); foreach (StorageInstance instance in StorageInstanceList) { sentInstances.AddInstance(instance.PatientId, instance.PatientsName, instance.StudyInstanceUid); } AuditHelper.LogSentInstances(RemoteAE, RemoteHost, sentInstances, EventSource.CurrentProcess, EventResult.MajorFailure); } }
protected override int OnStart(StudyLoaderArgs studyLoaderArgs) { var serverAe = studyLoaderArgs.Server; Platform.CheckForNullReference(serverAe, "Server"); Platform.CheckMemberIsSet(serverAe.StreamingParameters, "StreamingParameters"); _serverAe = serverAe; EventResult result = EventResult.Success; AuditedInstances loadedInstances = new AuditedInstances(); try { StudyXml studyXml = RetrieveStudyXml(studyLoaderArgs); _instances = GetInstances(studyXml).GetEnumerator(); loadedInstances.AddInstance(studyXml.PatientId, studyXml.PatientsName, studyXml.StudyInstanceUid); return(studyXml.NumberOfStudyRelatedInstances); } finally { AuditHelper.LogOpenStudies(new string[] { _serverAe.AETitle }, loadedInstances, EventSource.CurrentUser, result); } }
protected override void ProcessItem(Study study) { var result = EventResult.Success; try { WorkItem item; using (var context = new DataAccessContext(DataAccessContext.WorkItemMutex)) { item = ProcessStudy(study.Oid, context); context.Commit(); } if (item != null) { WorkItemPublishSubscribeHelper.PublishWorkItemChanged(WorkItemsChangedEventType.Update, WorkItemDataHelper.FromWorkItem(item)); } } catch (Exception) { result = EventResult.MajorFailure; throw; } finally { var instances = new AuditedInstances(); instances.AddInstance(study.PatientId, study.PatientsName, study.StudyInstanceUid); AuditHelper.LogDeleteStudies(AuditHelper.LocalAETitle, instances, EventSource.CurrentUser, result); } }
protected override int OnStart(StudyLoaderArgs studyLoaderArgs) { _sops = null; EventResult result = EventResult.Success; var loadedInstances = new AuditedInstances(); try { using (var context = new DataAccessContext()) { if (!studyLoaderArgs.Options.IgnoreInUse) { var workItemStatusFilter = WorkItemStatusFilter.StatusIn( WorkItemStatusEnum.Pending, WorkItemStatusEnum.InProgress, WorkItemStatusEnum.Idle, WorkItemStatusEnum.Failed); var updateItems = context.GetWorkItemBroker().GetWorkItems( WorkItemConcurrency.StudyUpdate, workItemStatusFilter, studyLoaderArgs.StudyInstanceUid); var deleteItems = context.GetWorkItemBroker().GetWorkItems( WorkItemConcurrency.StudyDelete, workItemStatusFilter, studyLoaderArgs.StudyInstanceUid); var updateTriggerItems = context.GetWorkItemBroker().GetWorkItems( WorkItemConcurrency.StudyUpdateTrigger, workItemStatusFilter, studyLoaderArgs.StudyInstanceUid); if (updateItems.Any() || deleteItems.Any() || updateTriggerItems.Any()) { var message = string.Format("There are work items actively modifying the study with UID '{0}'.", studyLoaderArgs.StudyInstanceUid); throw new InUseLoadStudyException(studyLoaderArgs.StudyInstanceUid, message); } } IStudy study = context.GetStudyBroker().GetStudy(studyLoaderArgs.StudyInstanceUid); if (study == null) { result = EventResult.MajorFailure; loadedInstances.AddInstance(studyLoaderArgs.StudyInstanceUid); throw new NotFoundLoadStudyException(studyLoaderArgs.StudyInstanceUid); } loadedInstances.AddInstance(study.PatientId, study.PatientsName, study.StudyInstanceUid); _sops = study.GetSopInstances().GetEnumerator(); return(study.NumberOfStudyRelatedInstances); } } finally { AuditHelper.LogOpenStudies(new[] { AuditHelper.LocalAETitle }, loadedInstances, EventSource.CurrentUser, result); } }
private bool Initialize() { _synchronizationContext = SynchronizationContext.Current; _exportedInstances = new AuditedInstances(); _canceled = false; _overwrite = false; if (Anonymize) { ExportComponent component = new ExportComponent(); component.OutputPath = OutputPath; if (DialogBoxAction.Ok != DesktopWindow.ShowDialogBox(component, SR.Export)) { return(false); } OutputPath = component.OutputPath; StudyData studyData = new StudyData { PatientId = component.PatientId, PatientsNameRaw = component.PatientsName, PatientsBirthDate = component.PatientsDateOfBirth, StudyId = component.StudyId, StudyDescription = component.StudyDescription, AccessionNumber = component.AccessionNumber, StudyDate = component.StudyDate }; _anonymizer = new DicomAnonymizer(); _anonymizer.KeepPrivateTags = component.KeepPrivateTags; _anonymizer.ValidationOptions = ValidationOptions.RelaxAllChecks; _anonymizer.StudyDataPrototype = studyData; } else { SelectFolderDialogCreationArgs args = new SelectFolderDialogCreationArgs(); args.Prompt = SR.MessageSelectOutputLocation; args.Path = OutputPath; FileDialogResult result = DesktopWindow.ShowSelectFolderDialogBox(args); if (result.Action != DialogBoxAction.Ok) { return(false); } OutputPath = result.FileName; } return(true); }
public void RetrieveStudy(IDicomServiceNode remoteAEInfo, IStudyRootData study) { EventResult result = EventResult.Success; try { var request = new DicomRetrieveStudyRequest { ServerName = remoteAEInfo.Name, ServerAETitle = remoteAEInfo.AETitle, ServerHostname = remoteAEInfo.ScpParameters != null ? remoteAEInfo.ScpParameters.HostName : null, ServerPort = remoteAEInfo.ScpParameters != null ? remoteAEInfo.ScpParameters.Port : 0, Study = new WorkItemStudy(study), Patient = new WorkItemPatient(study) }; // TODO (CR Jul 2012): The service itself has logic like this already, so this should probably be there, too. // Then, we could also get rid of this GetMatching... method. var data = GetMatchingActiveWorkItem(request); if (data != null) { var existingRequest = data.Request as DicomRetrieveStudyRequest; if (existingRequest != null && remoteAEInfo.Name == existingRequest.ServerName) { Request = data.Request; return; } } InsertRequest(request, new DicomRetrieveProgress()); } catch (Exception ex) { result = EventResult.MajorFailure; Exception = ex; Platform.Log(LogLevel.Error, ex, Common.SR.MessageFailedToSendStudy); throw; } finally { var instances = new AuditedInstances(); instances.AddInstance(study.PatientId, study.PatientsName, study.StudyInstanceUid); AuditHelper.LogBeginReceiveInstances(remoteAEInfo.AETitle, remoteAEInfo.ScpParameters.HostName, instances, string.IsNullOrEmpty(Request.UserName) ? EventSource.CurrentProcess : EventSource.CurrentUser, result); } }
private void ExportImages(IBackgroundTaskContext context) { List <IPresentationImage> imagesToDispose = new List <IPresentationImage>(); EventResult result = EventResult.Success; AuditedInstances exportedInstances = new AuditedInstances(); foreach (IPresentationImage image in this.DisplaySet.PresentationImages) { IImageSopProvider sopProv = image as IImageSopProvider; if (sopProv != null) { exportedInstances.AddInstance(sopProv.ImageSop.PatientId, sopProv.ImageSop.PatientsName, sopProv.ImageSop.StudyInstanceUid, this.FilePath); } } try { ReportProgress(context, SR.MessageCreatingVideo, 0); ExportImages(context, ref imagesToDispose); if (context != null) { if (context.CancelRequested) { ReportProgress(context, SR.MessageCancelled, NumberOfImages); context.Cancel(); } else { ReportProgress(context, SR.MessageExportComplete, NumberOfImages); context.Complete(); } } } catch (Exception e) { _error = e; result = EventResult.SeriousFailure; Platform.Log(LogLevel.Error, e); } finally { AuditHelper.LogExportStudies(exportedInstances, EventSource.CurrentUser, result); imagesToDispose.ForEach(delegate(IPresentationImage image) { image.Dispose(); }); } }
public void SaveAll() { if (!WarnSaveEditedReportsOrAttachments()) { return; } var modifiedInstances = new AuditedInstances(); var failureCount = 0; for (int i = 0; i < _loadedFiles.Count; i++) { var file = _loadedFiles[i]; try { var studyInstanceUid = file.DataSet[DicomTags.StudyInstanceUid].ToString(); var patientId = file.DataSet[DicomTags.PatientId].ToString(); var patientsName = file.DataSet[DicomTags.PatientsName].ToString(); file.Save(DicomWriteOptions.Default); _dirtyFlags[i] = false; modifiedInstances.AddInstance(patientId, patientsName, studyInstanceUid); } catch (Exception ex) { ++failureCount; if (file != null && !string.IsNullOrEmpty(file.Filename)) { Platform.Log(LogLevel.Warn, ex, "An exception was encountered while trying to update the file \'{0}\'.", file.Filename); } else { Platform.Log(LogLevel.Warn, ex, "An unexpected error was encountered while trying to update a file."); } } } if (failureCount > 0) { Host.DesktopWindow.ShowMessageBox(SR.MessageErrorUpdatingSomeFiles, MessageBoxActions.Ok); } AuditHelper.LogUpdateInstances(new string[0], modifiedInstances, EventSource.CurrentUser, EventResult.Success); }
private void Export() { if (SelectedImageExporter == null) { throw new InvalidOperationException("No exporter was chosen; unable to export any images."); } if (NumberOfImagesToExport == 1) { EventResult result = EventResult.Success; AuditedInstances exportedInstances = GetInstancesForAudit(ItemsToExport, this.ExportFilePath); try { if (!Directory.Exists(Path.GetDirectoryName(ExportFilePath ?? ""))) { throw new FileNotFoundException("The specified export file path does not exist: " + ExportFilePath ?? ""); } ClipboardItem clipboardItem = (ClipboardItem)_itemsToExport[0]; ExportImageParams exportParams = GetExportParams(clipboardItem); SelectedImageExporter.Export((IPresentationImage)clipboardItem.Item, ExportFilePath, exportParams); } catch (Exception ex) { result = EventResult.SeriousFailure; Platform.Log(LogLevel.Error, ex); } finally { AuditHelper.LogExportStudies(exportedInstances, EventSource.CurrentUser, result); } } else { if (!Directory.Exists(ExportFilePath ?? "")) { throw new FileNotFoundException("The specified export directory does not exist." + ExportFilePath ?? ""); } _multipleImageExporter = new MultipleImageExporter(this); _multipleImageExporter.Run(); } }
protected override int OnStart(StudyLoaderArgs studyLoaderArgs) { _studyKey = studyLoaderArgs.Server as MINTApi.StudyKey; EventResult result = EventResult.Success; AuditedInstances loadedInstances = new AuditedInstances(); try { XmlDocument doc = RetrieveHeaderXml(); StudyMINTXml studyXml = new StudyMINTXml(studyLoaderArgs); studyXml.SetMemento(_studyKey.MetadataUri, doc); var allInstances = studyXml.AllInstances; _instances = allInstances.GetEnumerator(); var patientId = studyXml[DicomTags.PatientId].GetString(0, ""); var patientsName = studyXml[DicomTags.PatientsName].GetString(0, ""); var studyInstanceUid = studyXml[DicomTags.StudyInstanceUid].GetString(0, ""); loadedInstances.AddInstance(patientId, patientsName, studyInstanceUid); UseBulkLoading = false; if (UseBulkLoading) { binaryStream = new MINTBinaryStream(); binaryStream.SetBaseURI(_studyKey.MetadataUri); binaryStream.RetrievePixelData(); } return(allInstances.Count); } catch (Exception e) { Console.WriteLine("EXCEPTION: " + e.Message); result = EventResult.MajorFailure; throw; } finally { AuditHelper.LogOpenStudies(new string[] { this.Name }, loadedInstances, EventSource.CurrentUser, result); } }
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 Export(IBackgroundTaskContext context) { EventResult result = EventResult.Success; AuditedInstances exportedInstances = GetInstancesForAudit(ItemsToExport, this._exportComponent.ExportFilePath); try { _taskContext = context; Export(); } catch (Exception e) { _error = e; result = EventResult.SeriousFailure; Platform.Log(LogLevel.Error, e); } finally { AuditHelper.LogExportStudies(exportedInstances, EventSource.CurrentUser, result); _imagesToDispose.ForEach(delegate(IPresentationImage image) { image.Dispose(); }); } }
public void PublishFiles(IDicomServiceNode remoteAEInfo, IStudyRootData study, DeletionBehaviour behaviour, List <string> files) { EventResult result = EventResult.Success; try { var request = new PublishFilesRequest { DestinationServerName = remoteAEInfo.Name, DestinationServerAETitle = remoteAEInfo.AETitle, DestinationServerHostname = remoteAEInfo.ScpParameters != null ? remoteAEInfo.ScpParameters.HostName : null, DestinationServerPort = remoteAEInfo.ScpParameters != null ? remoteAEInfo.ScpParameters.Port : 0, Priority = WorkItemPriorityEnum.High, DeletionBehaviour = behaviour, Study = new WorkItemStudy(study), Patient = new WorkItemPatient(study), FilePaths = files }; InsertRequest(request, new DicomSendProgress()); } catch (Exception ex) { result = EventResult.MajorFailure; Exception = ex; Platform.Log(LogLevel.Error, ex, Common.SR.MessageFailedToSendSops); throw; } finally { var instances = new AuditedInstances(); instances.AddInstance(study.PatientId, study.PatientsName, study.StudyInstanceUid); AuditHelper.LogBeginSendInstances(remoteAEInfo.AETitle, remoteAEInfo.ScpParameters.HostName, instances, string.IsNullOrEmpty(Request.UserName) ? EventSource.CurrentProcess : EventSource.CurrentUser, result); } }
public bool SaveAll(bool promptForLocation) { // warn if there appear to be any reports or attachments in the files being edited if (!WarnSaveEditedReportsOrAttachments()) { return(false); } // prompt for destination if requested or any files are from local data store var filenameMap = (Dictionary <string, string>)null; if ((promptForLocation || AnyFilesFromLocalStore()) && !PromptSaveDestination(out filenameMap)) { return(false); } // if destination was not prompted, warn user that files will be overwritten if (filenameMap == null && !WarnOverwriteFiles()) { return(false); } var modifiedInstances = new AuditedInstances(); var failureCount = 0; for (int i = 0; i < _loadedFiles.Count; i++) { var file = _loadedFiles[i]; try { var studyInstanceUid = file.DataSet[DicomTags.StudyInstanceUid].ToString(); var patientId = file.DataSet[DicomTags.PatientId].ToString(); var patientsName = file.DataSet[DicomTags.PatientsName].ToString(); var filename = filenameMap != null ? filenameMap[file.Filename] : file.Filename; file.Save(filename, DicomWriteOptions.Default); _dirtyFlags[i] = false; modifiedInstances.AddInstance(patientId, patientsName, studyInstanceUid); } catch (Exception ex) { ++failureCount; if (file != null && !string.IsNullOrEmpty(file.Filename)) { Platform.Log(LogLevel.Warn, ex, "An exception was encountered while trying to update the file \'{0}\'.", file.Filename); } else { Platform.Log(LogLevel.Warn, ex, "An unexpected error was encountered while trying to update a file."); } } } if (failureCount > 0) { Host.DesktopWindow.ShowMessageBox(SR.MessageErrorUpdatingSomeFiles, MessageBoxActions.Ok); } AuditHelper.LogUpdateInstances(new string[0], modifiedInstances, EventSource.CurrentUser, EventResult.Success); return(true); }
private void Anonymize(IBackgroundTaskContext context) { //TODO (Marmot) This probably should be its own WorkItem type and have it done in the background there. var study = (StudyTableItem)context.UserState; var anonymizedInstances = new AuditedInstances(); try { context.ReportProgress(new BackgroundTaskProgress(0, SR.MessageAnonymizingStudy)); var loader = study.Server.GetService <IStudyLoader>(); int numberOfSops = loader.Start(new StudyLoaderArgs(study.StudyInstanceUid, null)); if (numberOfSops <= 0) { return; } var anonymizer = new DicomAnonymizer { StudyDataPrototype = _component.AnonymizedData }; if (_component.PreserveSeriesData) { //The default anonymizer removes the series data, so we just clone the original. anonymizer.AnonymizeSeriesDataDelegate = original => original.Clone(); } // Setup the ImportFilesUtility to perform the import var configuration = DicomServer.GetConfiguration(); // setup auditing information var result = EventResult.Success; string patientsSex = null; for (int i = 0; i < numberOfSops; ++i) { using (var sop = loader.LoadNextSop()) { if (sop != null && (_component.KeepReportsAndAttachments || !IsReportOrAttachmentSopClass(sop.SopClassUid))) { //preserve the patient sex. if (patientsSex == null) { anonymizer.StudyDataPrototype.PatientsSex = patientsSex = sop.PatientsSex ?? ""; } var localSopDataSource = sop.DataSource as ILocalSopDataSource; if (localSopDataSource != null) { string filename = string.Format("{0}.dcm", i); DicomFile file = (localSopDataSource).File; // make sure we anonymize a new instance, not the same instance that the Sop cache holds!! file = new DicomFile(filename, file.MetaInfo.Copy(), file.DataSet.Copy()); anonymizer.Anonymize(file); // TODO (CR Jun 2012): Importing each file separately? Platform.GetService((IPublishFiles w) => w.PublishLocal(new List <DicomFile> { file })); string studyInstanceUid = file.DataSet[DicomTags.StudyInstanceUid].ToString(); string patientId = file.DataSet[DicomTags.PatientId].ToString(); string patientsName = file.DataSet[DicomTags.PatientsName].ToString(); anonymizedInstances.AddInstance(patientId, patientsName, studyInstanceUid); var progressPercent = (int)Math.Floor((i + 1) / (float)numberOfSops * 100); var progressMessage = String.Format(SR.MessageAnonymizingStudy, file.MediaStorageSopInstanceUid); context.ReportProgress(new BackgroundTaskProgress(progressPercent, progressMessage)); } } } } AuditHelper.LogCreateInstances(new[] { configuration.AETitle }, anonymizedInstances, EventSource.CurrentUser, result); context.Complete(); } catch (Exception e) { AuditHelper.LogCreateInstances(new[] { string.Empty }, anonymizedInstances, EventSource.CurrentUser, EventResult.MajorFailure); context.Error(e); } }
/// <summary> /// Generates a "Dicom Instances Accessed" update event in the audit log (with ActionCode of Delete), according to DICOM Supplement 95. /// </summary> /// <remarks> /// This method automatically separates different patients into separately logged events, as required by DICOM. /// /// We chose to impleemnt the DicomInstancesAccessed audit log, as opposed to the DicomStudyDeleted audit message because the whole /// study isn't being deleted, just a series. /// </remarks> /// <param name="aeTitles">The application entities from which the instances were accessed.</param> /// <param name="instances">The studies that the series belong that are being deleted.</param> /// <param name="eventSource">The source user or application entity which invoked the operation.</param> /// <param name="eventResult">The result of the operation.</param> public static void LogDeleteSeries(IEnumerable<string> aeTitles, AuditedInstances instances, EventSource eventSource, EventResult eventResult) { AuditLogHelper.LogDeleteSeries(aeTitles, instances, eventSource, eventResult); }
/// <summary> /// Main Processing routine. /// </summary> public override void Process() { bool stillProcessing = ProcessUidList(); if (CancelPending) { Proxy.Cancel(); return; } if (StopPending) { Proxy.Idle(); return; } if (!stillProcessing) { bool failed = false; bool complete = true; bool filesMissing = false; foreach (WorkItemUid sop in WorkQueueUidList) { if (sop.Failed) { //If any items failed simply because the file doesn't exist, then fail outright. if (!File.Exists(GetFilePath(sop))) { filesMissing = true; } failed = true; break; } if (!sop.Complete) { complete = false; break; } } DateTime now = Platform.Time; if (failed) { var failureType = filesMissing ? WorkItemFailureType.Fatal : WorkItemFailureType.NonFatal; Proxy.Fail(failureType); if (Proxy.Item.Status == WorkItemStatusEnum.Failed) { var auditedInstances = new AuditedInstances(); auditedInstances.AddInstance(Request.Patient.PatientId, Request.Patient.PatientsName, Request.Study.StudyInstanceUid); AuditHelper.LogImportStudies(auditedInstances, string.IsNullOrEmpty(Request.UserName) ? EventSource.CurrentProcess : EventSource.GetUserEventSource(Request.UserName), EventResult.MajorFailure); } } else if (!complete) { Proxy.Idle(); } else if (now > Proxy.Item.ExpirationTime) { if (Study == null) { Study = LoadRelatedStudy(); } var ruleOptions = new RulesEngineOptions { ApplyDeleteActions = true, ApplyRouteActions = true }; RulesEngine.Create().ApplyStudyRules(Study.ToStoreEntry(), ruleOptions); Proxy.Complete(); var auditedInstances = new AuditedInstances(); auditedInstances.AddInstance(Request.Patient.PatientId, Request.Patient.PatientsName, Request.Study.StudyInstanceUid); AuditHelper.LogImportStudies(auditedInstances, string.IsNullOrEmpty(Request.UserName) ? EventSource.CurrentProcess : EventSource.GetUserEventSource(Request.UserName), EventResult.Success); } else { Proxy.Idle(); } } else { Proxy.Idle(); } }
/// <summary> /// Generates a "Dicom Study Deleted" event in the audit log, according to DICOM Supplement 95. /// </summary> /// <remarks> /// This method automatically separates different patients into separately logged events, as required by DICOM. /// </remarks> /// <param name="aeTitle">The application entity from which the instances were deleted.</param> /// <param name="instances">The studies that were deleted.</param> /// <param name="eventSource">The source user or application entity which invoked the operation.</param> /// <param name="eventResult">The result of the operation.</param> public static void LogDeleteStudies(string aeTitle, AuditedInstances instances, EventSource eventSource, EventResult eventResult) { AuditLogHelper.LogDeleteStudies(aeTitle, instances, eventSource, eventResult); }
/// <summary> /// Generates a "Data Export" event in the audit log, according to DICOM Supplement 95. /// </summary> /// <remarks> /// One audit event is generated for each file system volume to which data is exported. /// If the audited instances are not on a file system, a single event is generated with an empty media identifier. /// </remarks> /// <param name="instances">The files that were exported.</param> /// <param name="eventSource">The source user or application entity which invoked the operation.</param> /// <param name="eventResult">The result of the operation.</param> public static void LogExportStudies(AuditedInstances instances, EventSource eventSource, EventResult eventResult) { AuditLogHelper.LogExportStudies(instances, eventSource, EventSource.GetCurrentDicomAE(), eventResult); }
/// <summary> /// Generates a "DICOM Instances Transferred" received event in the audit log, according to DICOM Supplement 95. /// </summary> /// <remarks> /// This method automatically separates different patients into separately logged events, as required by DICOM. /// </remarks> /// <param name="remoteAETitle">The application entity from which the transfer was completed.</param> /// <param name="remoteHostName">The hostname of the application entity from which the transfer was completed.</param> /// <param name="instances">The studies that were transferred.</param> /// <param name="eventSource">The source user or application entity which invoked the operation.</param> /// <param name="eventResult">The result of the operation.</param> /// <param name="action">The action taken on the studies that were transferred.</param> public static void LogReceivedInstances(string remoteAETitle, string remoteHostName, AuditedInstances instances, EventSource eventSource, EventResult eventResult, EventReceiptAction action) { AuditLogHelper.LogReceivedInstances(LocalAETitle, remoteAETitle, remoteHostName, instances, eventSource, eventResult, action); }
/// <summary> /// Generates a "Begin Transferring DICOM Instances" receive event in the audit log, according to DICOM Supplement 95. /// </summary> /// <remarks> /// This method automatically separates different patients into separately logged events, as required by DICOM. /// </remarks> /// <param name="remoteAETitle">The application entity from which the transfer was started.</param> /// <param name="remoteHostName">The hostname of the application entity from which the transfer was started.</param> /// <param name="instances">The studies that were requested for transfer.</param> /// <param name="eventSource">The source user or application entity which invoked the operation.</param> /// <param name="eventResult">The result of the operation.</param> public static void LogBeginReceiveInstances(string remoteAETitle, string remoteHostName, AuditedInstances instances, EventSource eventSource, EventResult eventResult) { AuditLogHelper.LogBeginReceiveInstances(LocalAETitle, remoteAETitle, remoteHostName, instances, eventSource, eventResult); }
public override bool OnReceiveRequest(ClearCanvas.Dicom.Network.DicomServer server, ServerAssociationParameters association, byte presentationID, DicomMessage message) { string studyInstanceUid; string seriesInstanceUid; DicomUid sopInstanceUid; bool ok = message.DataSet[DicomTags.SopInstanceUid].TryGetUid(0, out sopInstanceUid); if (ok) { ok = message.DataSet[DicomTags.SeriesInstanceUid].TryGetString(0, out seriesInstanceUid); } if (ok) { ok = message.DataSet[DicomTags.StudyInstanceUid].TryGetString(0, out studyInstanceUid); } if (!ok) { Platform.Log(LogLevel.Error, "Unable to retrieve UIDs from request message, sending failure status."); server.SendCStoreResponse(presentationID, message.MessageId, sopInstanceUid.UID, DicomStatuses.ProcessingFailure); return(true); } if (_importContext == null) { _importContext = new DicomReceiveImportContext(association.CallingAE, GetRemoteHostName(association), StudyStore.GetConfiguration(), EventSource.CurrentProcess); // Publish new WorkItems as they're added to the context lock (_importContext.StudyWorkItemsSyncLock) { _importContext.StudyWorkItems.ItemAdded += delegate(object sender, DictionaryEventArgs <string, WorkItem> args) { Platform.GetService( (IWorkItemActivityMonitorService service) => service.Publish(new WorkItemPublishRequest { Item = WorkItemDataHelper .FromWorkItem( args.Item) })); var auditedInstances = new AuditedInstances(); var request = args.Item.Request as DicomReceiveRequest; if (request != null) { auditedInstances.AddInstance(request.Patient.PatientId, request.Patient.PatientsName, request.Study.StudyInstanceUid); } AuditHelper.LogReceivedInstances( association.CallingAE, GetRemoteHostName(association), auditedInstances, EventSource.CurrentProcess, EventResult.Success, EventReceiptAction.ActionUnknown); } ; _importContext.StudyWorkItems.ItemChanged += (sender, args) => Platform.GetService( (IWorkItemActivityMonitorService service) => service.Publish(new WorkItemPublishRequest { Item = WorkItemDataHelper.FromWorkItem(args.Item) })); } } var importer = new ImportFilesUtility(_importContext); var result = importer.Import(message, BadFileBehaviourEnum.Ignore, FileImportBehaviourEnum.Save); if (result.Successful) { if (!String.IsNullOrEmpty(result.AccessionNumber)) { Platform.Log(LogLevel.Info, "Received SOP Instance {0} from {1} to {2} (A#:{3} StudyUid:{4})", result.SopInstanceUid, association.CallingAE, association.CalledAE, result.AccessionNumber, result.StudyInstanceUid); } else { Platform.Log(LogLevel.Info, "Received SOP Instance {0} from {1} to {2} (StudyUid:{3})", result.SopInstanceUid, association.CallingAE, association.CalledAE, result.StudyInstanceUid); } server.SendCStoreResponse(presentationID, message.MessageId, message.AffectedSopInstanceUid, result.DicomStatus); } else { if (result.DicomStatus == DicomStatuses.ProcessingFailure) { Platform.Log(LogLevel.Error, "Failure importing sop: {0}", result.ErrorMessage); } //OnReceiveError(message, result.ErrorMessage, association.CallingAE); server.SendCStoreResponse(presentationID, message.MessageId, message.AffectedSopInstanceUid, result.DicomStatus, result.ErrorMessage); } return(true); }