private static ApplicationEntity createAE(
      String aet,
      String description,
      Connection dicom,
      Connection dicomTLS,
      QueryRetrieveView qrView,
      boolean storeSCP,
      boolean storeSCU) {
    ApplicationEntity ae = new ApplicationEntity(aet);
    ae.setDescription(description);
    ae.addConnection(dicom);
    if (dicomTLS != null) ae.addConnection(dicomTLS);

    ArchiveAEExtension aeExt = new ArchiveAEExtension();
    ae.addAEExtension(aeExt);
    ae.setAssociationAcceptor(true);
    ae.setAssociationInitiator(true);
    addTC(ae, null, SCP, UID.VerificationSOPClass, UID.ImplicitVRLittleEndian);
    addTC(ae, null, SCU, UID.VerificationSOPClass, UID.ImplicitVRLittleEndian);
    addTCs(ae, EnumSet.allOf(QueryOption.class), SCP, QUERY_CUIDS, UID.ImplicitVRLittleEndian);
    if (storeSCU) {
      addTCs(
          ae, EnumSet.of(QueryOption.RELATIONAL), SCP, RETRIEVE_CUIDS, UID.ImplicitVRLittleEndian);
      for (int i = 0; i < CUIDS_TSUIDS.length; i++, i++)
        addTCs(ae, null, SCU, CUIDS_TSUIDS[i], CUIDS_TSUIDS[i + 1]);
    }
    if (storeSCP) {
      for (int i = 0; i < CUIDS_TSUIDS.length; i++, i++)
        addTCs(ae, null, SCP, CUIDS_TSUIDS[i], CUIDS_TSUIDS[i + 1]);
      addTC(ae, null, SCP, UID.StorageCommitmentPushModelSOPClass, UID.ImplicitVRLittleEndian);
      addTC(ae, null, SCP, UID.ModalityPerformedProcedureStepSOPClass, UID.ImplicitVRLittleEndian);
      addTC(ae, null, SCU, UID.ModalityPerformedProcedureStepSOPClass, UID.ImplicitVRLittleEndian);
    }
    aeExt.setQueryRetrieveViewID(qrView.getViewID());
    return ae;
  }
 public void addQueryRetrieveView(QueryRetrieveView view) {
   queryRetrieveViewMap.put(view.getViewID(), view);
 }
  private static void addArchiveDeviceExtension(Device device, boolean sampleConfig) {
    ArchiveDeviceExtension ext = new ArchiveDeviceExtension();
    device.addDeviceExtension(ext);
    ext.setFuzzyAlgorithmClass("org.dcm4che3.soundex.ESoundex");
    ext.setStorageID(STORAGE_ID);
    ext.setOverwritePolicy(OverwritePolicy.SAME_SOURCE);
    ext.setQueryRetrieveViewID(HIDE_REJECTED_VIEW.getViewID());
    ext.setBulkDataSpoolDirectory(BULK_DATA_SPOOL_DIR);
    ext.setQueryRetrieveViews(QUERY_RETRIEVE_VIEWS);
    ext.setSendPendingCGet(SEND_PENDING_C_GET);
    ext.setSendPendingCMoveInterval(SEND_PENDING_C_MOVE_INTERVAL);
    ext.setWadoSupportedSRClasses(SR_CUIDS);
    ext.setWadoSR2HtmlTemplateURI(DSR2HTML_XSL);
    ext.setWadoSR2TextTemplateURI(DSR2TEXT_XSL);
    ext.setPatientUpdateTemplateURI(HL7_ADT2DCM_XSL);
    ext.setUnzipVendorDataToURI(UNZIP_VENDOR_DATA);
    ext.setQidoMaxNumberOfResults(QIDO_MAX_NUMBER_OF_RESULTS);
    ext.setExportTaskPollingInterval(EXPORT_TASK_POLLING_INTERVAL);
    ext.setExportTaskFetchSize(EXPORT_TASK_FETCH_SIZE);
    ext.setPurgeStoragePollingInterval(PURGE_STORAGE_POLLING_INTERVAL);
    ext.setPurgeStorageFetchSize(PURGE_STORAGE_FETCH_SIZE);
    ext.setDeleteRejectedPollingInterval(DELETE_REJECTED_POLLING_INTERVAL);
    ext.setDeleteRejectedFetchSize(DELETE_REJECTED_FETCH_SIZE);

    ext.setAttributeFilter(Entity.Patient, new AttributeFilter(PATIENT_ATTRS));
    ext.setAttributeFilter(Entity.Study, new AttributeFilter(STUDY_ATTRS));
    ext.setAttributeFilter(Entity.Series, new AttributeFilter(SERIES_ATTRS));
    ext.setAttributeFilter(Entity.Instance, new AttributeFilter(INSTANCE_ATTRS));
    ext.setAttributeFilter(Entity.MPPS, new AttributeFilter(MPPS_ATTRS));

    StorageDescriptor storageDescriptor = new StorageDescriptor(STORAGE_ID);
    storageDescriptor.setStorageURI(STORAGE_URI);
    storageDescriptor.setProperty("pathFormat", PATH_FORMAT);
    storageDescriptor.setProperty("checkMountFile", "NO_MOUNT");
    storageDescriptor.setRetrieveAETitles("DCM4CHEE", "DCM4CHEE_ADMIN");
    storageDescriptor.setDigestAlgorithm("MD5");
    storageDescriptor.setInstanceAvailability(Availability.ONLINE);
    ext.addStorageDescriptor(storageDescriptor);

    for (QueueDescriptor descriptor : QUEUE_DESCRIPTORS) ext.addQueueDescriptor(descriptor);

    ext.addRejectionNote(
        createRejectionNote(
            "Quality",
            REJECTED_FOR_QUALITY_REASONS,
            RejectionNote.AcceptPreviousRejectedInstance.IGNORE));
    ext.addRejectionNote(
        createRejectionNote(
            "Patient Safety",
            REJECT_FOR_PATIENT_SAFETY_REASONS,
            RejectionNote.AcceptPreviousRejectedInstance.REJECT,
            REJECTED_FOR_QUALITY_REASONS));
    ext.addRejectionNote(
        createRejectionNote(
            "Incorrect MWL Entry",
            INCORRECT_MODALITY_WORKLIST_ENTRY,
            RejectionNote.AcceptPreviousRejectedInstance.REJECT,
            REJECTED_FOR_QUALITY_REASONS,
            REJECT_FOR_PATIENT_SAFETY_REASONS));
    RejectionNote retentionExpired =
        createRejectionNote(
            "Retention Expired",
            DATA_RETENTION_POLICY_EXPIRED,
            RejectionNote.AcceptPreviousRejectedInstance.RESTORE,
            REJECTED_FOR_QUALITY_REASONS,
            REJECT_FOR_PATIENT_SAFETY_REASONS,
            INCORRECT_MODALITY_WORKLIST_ENTRY);
    ext.addRejectionNote(retentionExpired);
    ext.addRejectionNote(
        createRejectionNote("Revoke Rejection", REVOKE_REJECTION, null, REJECTION_CODES));

    if (sampleConfig) {
      ExporterDescriptor exportDescriptor = new ExporterDescriptor(EXPORTER_ID);
      exportDescriptor.setExportURI(EXPORT_URI);
      exportDescriptor.setSchedules(
          ScheduleExpression.valueOf("hour=18-6 dayOfWeek=*"),
          ScheduleExpression.valueOf("hour=* dayOfWeek=0,6"));
      exportDescriptor.setQueueName("Export1");
      exportDescriptor.setAETitle("DCM4CHEE");
      ext.addExporterDescriptor(exportDescriptor);

      ExportRule exportRule = new ExportRule("Forward to STORESCP");
      exportRule.getConditions().setSendingAETitle("FORWARD");
      exportRule.getConditions().setCondition("Modality", "CT|MR");
      exportRule.setEntity(Entity.Series);
      exportRule.setExportDelay(Duration.parse("PT1M"));
      exportRule.setExporterIDs(EXPORTER_ID);
      ext.addExportRule(exportRule);

      ext.addCompressionRule(JPEG_BASELINE);
      ext.addCompressionRule(JPEG_EXTENDED);
      ext.addCompressionRule(JPEG_LOSSLESS);
      ext.addCompressionRule(JPEG_LS);
      ext.addCompressionRule(JPEG_2000);

      ext.addAttributeCoercion(
          createAttributeCoercion("Ensure PID", Dimse.C_STORE_RQ, SCU, "ENSURE_PID", ENSURE_PID));
      ext.addAttributeCoercion(
          createAttributeCoercion("Nullify PN", Dimse.C_STORE_RQ, SCP, "NULLIFY_PN", NULLIFY_PN));
    }
  }
 public String getViewID() {
   return qrView.getViewID();
 }