Mercurial > hg > orthanc
changeset 6740:9551353f3e03
refactored OrthancConfiguration and OrthancRestSystem to have a single definition of keys and default values
| author | Alain Mazy <am@orthanc.team> |
|---|---|
| date | Wed, 06 May 2026 16:55:22 +0200 |
| parents | ace9135428dd |
| children | 7318f5f73ace |
| files | NEWS OrthancServer/Sources/OrthancConfiguration.cpp OrthancServer/Sources/OrthancConfiguration.h OrthancServer/Sources/OrthancRestApi/OrthancRestResources.cpp OrthancServer/Sources/OrthancRestApi/OrthancRestSystem.cpp OrthancServer/Sources/ServerContext.cpp OrthancServer/Sources/main.cpp |
| diffstat | 7 files changed, 176 insertions(+), 99 deletions(-) [+] |
line wrap: on
line diff
--- a/NEWS Wed May 06 14:38:37 2026 +0200 +++ b/NEWS Wed May 06 16:55:22 2026 +0200 @@ -20,6 +20,7 @@ * New fields reported in the /system route: - "OverwriteInstancesMode" (note, the boolean "OverwriteInstances" field is kept for backward compatibility) + - "MaximumStorageCacheSize", "StoreMD5ForAttachments" * The "LocalAet" field of the payload to "/modalities/../move", "/modalities/../store", "/modalities/../get", "queries/../answers/../retrieve" now always overwrites the "DicomAet" and the "DicomModalities.LocalAet" configurations.
--- a/OrthancServer/Sources/OrthancConfiguration.cpp Wed May 06 14:38:37 2026 +0200 +++ b/OrthancServer/Sources/OrthancConfiguration.cpp Wed May 06 16:55:22 2026 +0200 @@ -44,7 +44,6 @@ static const char* const ORTHANC_PEERS = "OrthancPeers"; static const char* const ORTHANC_PEERS_IN_DB = "OrthancPeersInDatabase"; static const char* const TEMPORARY_DIRECTORY = "TemporaryDirectory"; -static const char* const DATABASE_SERVER_IDENTIFIER = "DatabaseServerIdentifier"; static const char* const WARNINGS = "Warnings"; static const char* const JOBS_ENGINE_THREADS_COUNT = "JobsEngineThreadsCount"; static const char* const DICOM_LOSSY_TRANSCODING_QUALITY = "DicomLossyTranscodingQuality"; @@ -1143,12 +1142,12 @@ { std::string id; - if (LookupStringParameter(id, DATABASE_SERVER_IDENTIFIER)) + if (LookupStringParameter(id, ORTHANC_CONFIG_DATABASE_SERVER_IDENTIFIER)) { if (id.empty()) { throw OrthancException(ErrorCode_ParameterOutOfRange, "Global configuration option \"" + - std::string(DATABASE_SERVER_IDENTIFIER) + "\" cannot be empty"); + std::string(ORTHANC_CONFIG_DATABASE_SERVER_IDENTIFIER) + "\" cannot be empty"); } else { @@ -1169,9 +1168,9 @@ } } - items.insert("aet=" + GetStringParameter("DicomAet", "ORTHANC")); - items.insert("dicom-port=" + boost::lexical_cast<std::string>(GetUnsignedIntegerParameter("DicomPort", 4242))); - items.insert("http-port=" + boost::lexical_cast<std::string>(GetUnsignedIntegerParameter("HttpPort", 8042))); + items.insert("aet=" + GetOrthancAET()); + items.insert("dicom-port=" + boost::lexical_cast<std::string>(GetDicomPort())); + items.insert("http-port=" + boost::lexical_cast<std::string>(GetHttpPort())); for (std::set<std::string>::const_iterator it = items.begin(); it != items.end(); ++it) {
--- a/OrthancServer/Sources/OrthancConfiguration.h Wed May 06 14:38:37 2026 +0200 +++ b/OrthancServer/Sources/OrthancConfiguration.h Wed May 06 16:55:22 2026 +0200 @@ -37,6 +37,25 @@ class DcmDataset; +#define ORTHANC_CONFIG_NAME "Name" +#define ORTHANC_CONFIG_DICOM_AET "DicomAet" +#define ORTHANC_CONFIG_DICOM_PORT "DicomPort" +#define ORTHANC_CONFIG_HTTP_PORT "HttpPort" +#define ORTHANC_CONFIG_MAXIMUM_STORAGE_CACHE_SIZE "MaximumStorageCacheSize" +#define ORTHANC_CONFIG_MAXIMUM_STORAGE_SIZE "MaximumStorageSize" +#define ORTHANC_CONFIG_MAXIMUM_STORAGE_MODE "MaximumStorageMode" +#define ORTHANC_CONFIG_MAXIMUM_PATIENT_COUNT "MaximumPatientCount" +#define ORTHANC_CONFIG_CHECK_REVISIONS "CheckRevisions" +#define ORTHANC_CONFIG_STORE_MD5_FOR_ATTACHMENTS "StoreMD5ForAttachments" +#define ORTHANC_CONFIG_STORAGE_COMPRESSION "StorageCompression" +#define ORTHANC_CONFIG_OVERWRITE_INSTANCES "OverwriteInstances" +#define ORTHANC_CONFIG_INGEST_TRANSCODING "IngestTranscoding" +#define ORTHANC_CONFIG_DATABASE_SERVER_IDENTIFIER "DatabaseServerIdentifier" +#define ORTHANC_CONFIG_DICOM_DEFAULT_RETRIEVE_METHOD "DicomDefaultRetrieveMethod" +#define ORTHANC_CONFIG_PATIENT_LEVEL_ENABLED "PatientLevelEnabled" +#define ORTHANC_CONFIG_READ_ONLY "ReadOnly" + + namespace Orthanc { class DicomMap; @@ -264,11 +283,6 @@ std::string GetDefaultPrivateCreator() const; - std::string GetOrthancAET() const - { - return GetStringParameter("DicomAet", "ORTHANC"); - } - void GetAcceptedTransferSyntaxes(std::set<DicomTransferSyntax>& target) const; std::string GetDatabaseServerIdentifier() const; @@ -278,6 +292,75 @@ return disabledWarnings_.count(warning) == 0; } + std::string GetOrthancAET() const + { + return GetStringParameter(ORTHANC_CONFIG_DICOM_AET, "ORTHANC"); + } + + std::string GetOrthancName() const + { + return GetStringParameter(ORTHANC_CONFIG_NAME, "ORTHANC"); + } + + std::string GetIngestTranscoding() const + { + return GetStringParameter(ORTHANC_CONFIG_INGEST_TRANSCODING, ""); + } + + std::string GetMaximumStorageMode() const + { + return GetStringParameter(ORTHANC_CONFIG_MAXIMUM_STORAGE_MODE, "Recycle"); + } + + std::string GetDicomDefaultRetrieveMethod() const + { + return GetStringParameter(ORTHANC_CONFIG_DICOM_DEFAULT_RETRIEVE_METHOD, "C-MOVE"); + } + unsigned int GetMaximumStorageCacheSize() const + { + return GetUnsignedIntegerParameter(ORTHANC_CONFIG_MAXIMUM_STORAGE_CACHE_SIZE, 128); + } + + unsigned int GetMaximumStorageSize() const + { + return GetUnsignedIntegerParameter(ORTHANC_CONFIG_MAXIMUM_STORAGE_SIZE, 0); + } + + unsigned int GetMaximumPatientCount() const + { + return GetUnsignedIntegerParameter(ORTHANC_CONFIG_MAXIMUM_PATIENT_COUNT, 0); + } + + unsigned int GetDicomPort() const + { + return GetUnsignedIntegerParameter(ORTHANC_CONFIG_DICOM_PORT, 4242); + } + + unsigned int GetHttpPort() const + { + return GetUnsignedIntegerParameter(ORTHANC_CONFIG_HTTP_PORT, 8042); + } + + bool HasCheckRevisions() const + { + return GetBooleanParameter(ORTHANC_CONFIG_CHECK_REVISIONS, false); + } + + bool HasStoreMD5ForAttachments() const + { + return GetBooleanParameter(ORTHANC_CONFIG_STORE_MD5_FOR_ATTACHMENTS, true); + } + + bool HasStorageCompression() const + { + return GetBooleanParameter(ORTHANC_CONFIG_STORAGE_COMPRESSION, false); + } + + bool HasPatientLevelEnabled() const + { + return GetBooleanParameter(ORTHANC_CONFIG_PATIENT_LEVEL_ENABLED, true); + } + static void DefaultExtractDicomSummary(DicomMap& target, const ParsedDicomFile& dicom);
--- a/OrthancServer/Sources/OrthancRestApi/OrthancRestResources.cpp Wed May 06 14:38:37 2026 +0200 +++ b/OrthancServer/Sources/OrthancRestApi/OrthancRestResources.cpp Wed May 06 16:55:22 2026 +0200 @@ -60,8 +60,6 @@ static Orthanc::Semaphore throttlingSemaphore_(4); // TODO => PARAMETER? -static const std::string CHECK_REVISIONS = "CheckRevisions"; - static const char* const IGNORE_LENGTH = "ignore-length"; static const char* const RECONSTRUCT_FILES = "ReconstructFiles"; static const char* const LIMIT_TO_THIS_LEVEL_MAIN_DICOM_TAGS = "LimitToThisLevelMainDicomTags"; @@ -1949,7 +1947,7 @@ .SetUriArgument("id", "Orthanc identifier of the " + r + " of interest") .SetUriArgument("name", "The name of the metadata, or its index (cf. `UserMetadata` configuration option)") .SetHttpHeader("If-Match", "Revision of the metadata, to check if its content has not changed and can " - "be deleted. This header is mandatory if `CheckRevisions` option is `true`."); + "be deleted. This header is mandatory if `" + std::string(ORTHANC_CONFIG_CHECK_REVISIONS) + "` option is `true`."); return; } @@ -1971,10 +1969,10 @@ else { OrthancConfiguration::ReaderLock lock; - if (lock.GetConfiguration().GetBooleanParameter(CHECK_REVISIONS, false)) + if (lock.GetConfiguration().HasCheckRevisions()) { throw OrthancException(ErrorCode_Revision, - "HTTP header \"If-Match\" is missing, as \"CheckRevisions\" is \"true\""); + "HTTP header \"If-Match\" is missing, as \"" + std::string(ORTHANC_CONFIG_CHECK_REVISIONS) + "\" is \"true\""); } else { @@ -2034,7 +2032,7 @@ if (!hasOldRevision) { OrthancConfiguration::ReaderLock lock; - if (lock.GetConfiguration().GetBooleanParameter(CHECK_REVISIONS, false)) + if (lock.GetConfiguration().HasCheckRevisions()) { // "StatelessDatabaseOperations::SetMetadata()" will ignore // the actual value of "oldRevision" if the metadata is @@ -2654,7 +2652,7 @@ if (!hasOldRevision) { OrthancConfiguration::ReaderLock lock; - if (lock.GetConfiguration().GetBooleanParameter(CHECK_REVISIONS, false)) + if (lock.GetConfiguration().HasCheckRevisions()) { // "StatelessDatabaseOperations::AddAttachment()" will ignore // the actual value of "oldRevision" if the metadata is @@ -2738,10 +2736,10 @@ else { OrthancConfiguration::ReaderLock lock; - if (lock.GetConfiguration().GetBooleanParameter(CHECK_REVISIONS, false)) + if (lock.GetConfiguration().HasCheckRevisions()) { throw OrthancException(ErrorCode_Revision, - "HTTP header \"If-Match\" is missing, as \"CheckRevisions\" is \"true\""); + "HTTP header \"If-Match\" is missing, as \"" + std::string(ORTHANC_CONFIG_CHECK_REVISIONS) + "\" is \"true\""); } else {
--- a/OrthancServer/Sources/OrthancRestApi/OrthancRestSystem.cpp Wed May 06 14:38:37 2026 +0200 +++ b/OrthancServer/Sources/OrthancRestApi/OrthancRestSystem.cpp Wed May 06 16:55:22 2026 +0200 @@ -71,27 +71,14 @@ static void GetSystemInformation(RestApiGetCall& call) { static const char* const API_VERSION = "ApiVersion"; - static const char* const CHECK_REVISIONS = "CheckRevisions"; static const char* const DATABASE_BACKEND_PLUGIN = "DatabaseBackendPlugin"; static const char* const DATABASE_VERSION = "DatabaseVersion"; - static const char* const DATABASE_SERVER_IDENTIFIER = "DatabaseServerIdentifier"; - static const char* const DICOM_DEFAULT_RETRIEVE_METHOD = "DicomDefaultRetrieveMethod"; - static const char* const DICOM_AET = "DicomAet"; - static const char* const DICOM_PORT = "DicomPort"; - static const char* const HTTP_PORT = "HttpPort"; static const char* const IS_HTTP_SERVER_SECURE = "IsHttpServerSecure"; - static const char* const NAME = "Name"; static const char* const PLUGINS_ENABLED = "PluginsEnabled"; static const char* const STORAGE_AREA_PLUGIN = "StorageAreaPlugin"; static const char* const VERSION = "Version"; static const char* const MAIN_DICOM_TAGS = "MainDicomTags"; - static const char* const STORAGE_COMPRESSION = "StorageCompression"; - static const char* const OVERWRITE_INSTANCES = "OverwriteInstances"; static const char* const OVERWRITE_INSTANCES_MODE = "OverwriteInstancesMode"; - static const char* const INGEST_TRANSCODING = "IngestTranscoding"; - static const char* const MAXIMUM_STORAGE_SIZE = "MaximumStorageSize"; - static const char* const MAXIMUM_PATIENT_COUNT = "MaximumPatientCount"; - static const char* const MAXIMUM_STORAGE_MODE = "MaximumStorageMode"; static const char* const USER_METADATA = "UserMetadata"; static const char* const HAS_LABELS = "HasLabels"; static const char* const CAPABILITIES = "Capabilities"; @@ -99,9 +86,7 @@ static const char* const HAS_KEY_VALUE_STORES = "HasKeyValueStores"; static const char* const HAS_QUEUES = "HasQueues"; static const char* const HAS_EXTENDED_FIND = "HasExtendedFind"; - static const char* const READ_ONLY = "ReadOnly"; static const char* const HAS_RESERVE_QUEUE_VALUE = "HasReserveQueueValue"; - static const char* const PATIENT_LEVEL_ENABLED = "PatientLevelEnabled"; if (call.IsDocumentation()) { @@ -113,7 +98,7 @@ .SetAnswerField(VERSION, RestApiCallDocumentation::Type_String, "Version of Orthanc") .SetAnswerField(DATABASE_VERSION, RestApiCallDocumentation::Type_Number, "Version of the database: https://orthanc.uclouvain.be/book/developers/db-versioning.html") - .SetAnswerField(DATABASE_SERVER_IDENTIFIER, RestApiCallDocumentation::Type_String, + .SetAnswerField(ORTHANC_CONFIG_DATABASE_SERVER_IDENTIFIER, RestApiCallDocumentation::Type_String, "ID of the server in the database (when running multiple Orthanc on the same DB)") .SetAnswerField(IS_HTTP_SERVER_SECURE, RestApiCallDocumentation::Type_Boolean, "Whether the REST API is properly secured (assuming no reverse proxy is in use): https://orthanc.uclouvain.be/book/faq/security.html#securing-the-http-server") @@ -121,32 +106,36 @@ "Information about the installed storage area plugin (`null` if no such plugin is installed)") .SetAnswerField(DATABASE_BACKEND_PLUGIN, RestApiCallDocumentation::Type_String, "Information about the installed database index plugin (`null` if no such plugin is installed)") - .SetAnswerField(DICOM_DEFAULT_RETRIEVE_METHOD, RestApiCallDocumentation::Type_String, "The DicomDefaultRetrieveMethod configuration") - .SetAnswerField(DICOM_AET, RestApiCallDocumentation::Type_String, "The DICOM AET of Orthanc") - .SetAnswerField(DICOM_PORT, RestApiCallDocumentation::Type_Number, "The port to the DICOM server of Orthanc") - .SetAnswerField(HTTP_PORT, RestApiCallDocumentation::Type_Number, "The port to the HTTP server of Orthanc") - .SetAnswerField(NAME, RestApiCallDocumentation::Type_String, - "The name of the Orthanc server, cf. the `Name` configuration option") + .SetAnswerField(ORTHANC_CONFIG_DICOM_DEFAULT_RETRIEVE_METHOD, RestApiCallDocumentation::Type_String, "The " + std::string(ORTHANC_CONFIG_DICOM_DEFAULT_RETRIEVE_METHOD) + " configuration") + .SetAnswerField(ORTHANC_CONFIG_DICOM_AET, RestApiCallDocumentation::Type_String, "The DICOM AET of Orthanc") + .SetAnswerField(ORTHANC_CONFIG_DICOM_PORT, RestApiCallDocumentation::Type_Number, "The port to the DICOM server of Orthanc") + .SetAnswerField(ORTHANC_CONFIG_HTTP_PORT, RestApiCallDocumentation::Type_Number, "The port to the HTTP server of Orthanc") + .SetAnswerField(ORTHANC_CONFIG_NAME, RestApiCallDocumentation::Type_String, + "The name of the Orthanc server, cf. the `" + std::string(ORTHANC_CONFIG_NAME) + "` configuration option") .SetAnswerField(PLUGINS_ENABLED, RestApiCallDocumentation::Type_Boolean, "Whether Orthanc was built with support for plugins") - .SetAnswerField(CHECK_REVISIONS, RestApiCallDocumentation::Type_Boolean, + .SetAnswerField(ORTHANC_CONFIG_CHECK_REVISIONS, RestApiCallDocumentation::Type_Boolean, "Whether Orthanc handle revisions of metadata and attachments to deal with multiple writers (new in Orthanc 1.9.2)") .SetAnswerField(MAIN_DICOM_TAGS, RestApiCallDocumentation::Type_JsonObject, "The list of MainDicomTags saved in DB for each resource level (new in Orthanc 1.11.0)") - .SetAnswerField(STORAGE_COMPRESSION, RestApiCallDocumentation::Type_Boolean, + .SetAnswerField(ORTHANC_CONFIG_STORAGE_COMPRESSION, RestApiCallDocumentation::Type_Boolean, "Whether storage compression is enabled (new in Orthanc 1.11.0)") - .SetAnswerField(OVERWRITE_INSTANCES, RestApiCallDocumentation::Type_Boolean, + .SetAnswerField(ORTHANC_CONFIG_OVERWRITE_INSTANCES, RestApiCallDocumentation::Type_Boolean, "Whether instances are overwritten when re-ingested (new in Orthanc 1.11.0 and kept as a bool for backward compatibility)") .SetAnswerField(OVERWRITE_INSTANCES_MODE, RestApiCallDocumentation::Type_String, "Whether instances are overwritten when re-ingested (new in Orthanc 1.12.12)") - .SetAnswerField(INGEST_TRANSCODING, RestApiCallDocumentation::Type_String, + .SetAnswerField(ORTHANC_CONFIG_INGEST_TRANSCODING, RestApiCallDocumentation::Type_String, "Whether instances are transcoded when ingested into Orthanc (`""` if no transcoding is performed) (new in Orthanc 1.11.0)") - .SetAnswerField(MAXIMUM_STORAGE_SIZE, RestApiCallDocumentation::Type_Number, - "The configured MaximumStorageSize in MB (new in Orthanc 1.11.3)") - .SetAnswerField(MAXIMUM_PATIENT_COUNT, RestApiCallDocumentation::Type_Number, - "The configured MaximumPatientCount (new in Orthanc 1.12.4)") - .SetAnswerField(MAXIMUM_STORAGE_MODE, RestApiCallDocumentation::Type_String, - "The configured MaximumStorageMode (new in Orthanc 1.11.3)") + .SetAnswerField(ORTHANC_CONFIG_MAXIMUM_STORAGE_CACHE_SIZE, RestApiCallDocumentation::Type_Number, + std::string("The configured ") + ORTHANC_CONFIG_MAXIMUM_STORAGE_CACHE_SIZE + " in MB (new in Orthanc 1.12.12)") + .SetAnswerField(ORTHANC_CONFIG_STORE_MD5_FOR_ATTACHMENTS, RestApiCallDocumentation::Type_Boolean, + std::string("The configured ") + ORTHANC_CONFIG_STORE_MD5_FOR_ATTACHMENTS + " (new in Orthanc 1.12.12)") + .SetAnswerField(ORTHANC_CONFIG_MAXIMUM_STORAGE_SIZE, RestApiCallDocumentation::Type_Number, + "The configured " + std::string(ORTHANC_CONFIG_MAXIMUM_STORAGE_SIZE) + " in MB (new in Orthanc 1.11.3)") + .SetAnswerField(ORTHANC_CONFIG_MAXIMUM_PATIENT_COUNT, RestApiCallDocumentation::Type_Number, + "The configured " + std::string(ORTHANC_CONFIG_MAXIMUM_PATIENT_COUNT) + " (new in Orthanc 1.12.4)") + .SetAnswerField(ORTHANC_CONFIG_MAXIMUM_STORAGE_MODE, RestApiCallDocumentation::Type_String, + "The configured " + std::string(ORTHANC_CONFIG_MAXIMUM_STORAGE_MODE) + " (new in Orthanc 1.11.3)") .SetAnswerField(USER_METADATA, RestApiCallDocumentation::Type_JsonObject, "The configured UserMetadata (new in Orthanc 1.12.0)") .SetAnswerField(HAS_LABELS, RestApiCallDocumentation::Type_Boolean, @@ -155,9 +144,9 @@ "Whether the database back-end supports optional features like 'HasExtendedChanges', 'HasExtendedFind' " "(new in Orthanc 1.12.5), 'HasKeyValueStores', 'HasQueues' (new in Orthanc 1.12.8), " "and 'HasReserveQueueValue' (new in Orthanc 1.12.10)") - .SetAnswerField(READ_ONLY, RestApiCallDocumentation::Type_Boolean, + .SetAnswerField(ORTHANC_CONFIG_READ_ONLY, RestApiCallDocumentation::Type_Boolean, "Whether Orthanc is running in read only mode (new in Orthanc 1.12.5)") - .SetAnswerField(PATIENT_LEVEL_ENABLED, RestApiCallDocumentation::Type_Boolean, + .SetAnswerField(ORTHANC_CONFIG_PATIENT_LEVEL_ENABLED, RestApiCallDocumentation::Type_Boolean, "Whether Patient level routes and sanity checks are enabled (new in Orthanc 1.12.11)") .SetHttpGetSample("https://orthanc.uclouvain.be/demo/system", true); return; @@ -174,26 +163,29 @@ { OrthancConfiguration::ReaderLock lock; - result[DICOM_AET] = lock.GetConfiguration().GetOrthancAET(); - result[DICOM_PORT] = lock.GetConfiguration().GetUnsignedIntegerParameter(DICOM_PORT, 4242); - result[HTTP_PORT] = lock.GetConfiguration().GetUnsignedIntegerParameter(HTTP_PORT, 8042); - result[NAME] = lock.GetConfiguration().GetStringParameter(NAME, ""); - result[CHECK_REVISIONS] = lock.GetConfiguration().GetBooleanParameter(CHECK_REVISIONS, false); // New in Orthanc 1.9.2 - result[STORAGE_COMPRESSION] = lock.GetConfiguration().GetBooleanParameter(STORAGE_COMPRESSION, false); // New in Orthanc 1.11.0 - result[OVERWRITE_INSTANCES] = context.IsOverwriteInstances(); // New in Orthanc 1.11.0 - result[OVERWRITE_INSTANCES_MODE] = EnumerationToString(context.GetOverwriteInstances()); // New in Orthanc 1.12.12 - result[INGEST_TRANSCODING] = lock.GetConfiguration().GetStringParameter(INGEST_TRANSCODING, ""); // New in Orthanc 1.11.0 - result[DATABASE_SERVER_IDENTIFIER] = lock.GetConfiguration().GetDatabaseServerIdentifier(); - result[MAXIMUM_STORAGE_SIZE] = lock.GetConfiguration().GetUnsignedIntegerParameter(MAXIMUM_STORAGE_SIZE, 0); // New in Orthanc 1.11.3 - result[MAXIMUM_PATIENT_COUNT] = lock.GetConfiguration().GetUnsignedIntegerParameter(MAXIMUM_PATIENT_COUNT, 0); // New in Orthanc 1.12.4 - result[MAXIMUM_STORAGE_MODE] = lock.GetConfiguration().GetStringParameter(MAXIMUM_STORAGE_MODE, "Recycle"); // New in Orthanc 1.11.3 - result[DICOM_DEFAULT_RETRIEVE_METHOD] = lock.GetConfiguration().GetStringParameter(DICOM_DEFAULT_RETRIEVE_METHOD, "C-MOVE"); + result[ORTHANC_CONFIG_NAME] = lock.GetConfiguration().GetOrthancName(); + result[ORTHANC_CONFIG_DICOM_AET] = lock.GetConfiguration().GetOrthancAET(); + result[ORTHANC_CONFIG_DICOM_PORT] = lock.GetConfiguration().GetDicomPort(); + result[ORTHANC_CONFIG_HTTP_PORT] = lock.GetConfiguration().GetHttpPort(); + result[ORTHANC_CONFIG_CHECK_REVISIONS] = lock.GetConfiguration().HasCheckRevisions(); // New in Orthanc 1.9.2 + result[ORTHANC_CONFIG_MAXIMUM_STORAGE_CACHE_SIZE] = lock.GetConfiguration().GetMaximumStorageCacheSize(); // New in Orthanc 1.12.12 + result[ORTHANC_CONFIG_STORE_MD5_FOR_ATTACHMENTS] = lock.GetConfiguration().HasStoreMD5ForAttachments(); // New in Orthanc 1.12.12 + result[ORTHANC_CONFIG_STORAGE_COMPRESSION] = lock.GetConfiguration().HasStorageCompression(); // New in Orthanc 1.11.0 + result[ORTHANC_CONFIG_INGEST_TRANSCODING] = lock.GetConfiguration().GetIngestTranscoding(); // New in Orthanc 1.11.0 + result[ORTHANC_CONFIG_DATABASE_SERVER_IDENTIFIER] = lock.GetConfiguration().GetDatabaseServerIdentifier(); + result[ORTHANC_CONFIG_MAXIMUM_STORAGE_SIZE] = lock.GetConfiguration().GetMaximumStorageSize(); // New in Orthanc 1.11.3 + result[ORTHANC_CONFIG_MAXIMUM_PATIENT_COUNT] = lock.GetConfiguration().GetMaximumPatientCount(); // New in Orthanc 1.12.4 + result[ORTHANC_CONFIG_MAXIMUM_STORAGE_MODE] = lock.GetConfiguration().GetMaximumStorageMode(); // New in Orthanc 1.11.3 + result[ORTHANC_CONFIG_DICOM_DEFAULT_RETRIEVE_METHOD] = lock.GetConfiguration().GetDicomDefaultRetrieveMethod(); } + result[ORTHANC_CONFIG_OVERWRITE_INSTANCES] = context.IsOverwriteInstances(); // New in Orthanc 1.11.0 + result[OVERWRITE_INSTANCES_MODE] = EnumerationToString(context.GetOverwriteInstances()); // New in Orthanc 1.12.12 + result[ORTHANC_CONFIG_PATIENT_LEVEL_ENABLED] = context.IsPatientLevelEnabled(); // New in Orthanc 1.12.11 + result[STORAGE_AREA_PLUGIN] = Json::nullValue; result[DATABASE_BACKEND_PLUGIN] = Json::nullValue; - result[READ_ONLY] = context.IsReadOnly(); - result[PATIENT_LEVEL_ENABLED] = context.IsPatientLevelEnabled(); + result[ORTHANC_CONFIG_READ_ONLY] = context.IsReadOnly(); #if ORTHANC_ENABLE_PLUGINS == 1 result[PLUGINS_ENABLED] = true;
--- a/OrthancServer/Sources/ServerContext.cpp Wed May 06 14:38:37 2026 +0200 +++ b/OrthancServer/Sources/ServerContext.cpp Wed May 06 16:55:22 2026 +0200 @@ -440,7 +440,7 @@ builtinDecoderTranscoderOrder_ = StringToBuiltinDecoderTranscoderOrder(lock.GetConfiguration().GetStringParameter("BuiltinDecoderTranscoderOrder", "After")); std::string s; - if (lock.GetConfiguration().LookupStringParameter(s, "IngestTranscoding")) + if (lock.GetConfiguration().LookupStringParameter(s, ORTHANC_CONFIG_INGEST_TRANSCODING)) { if (LookupTransferSyntax(ingestTransferSyntax_, s)) { @@ -533,7 +533,7 @@ SetAcceptedSopClasses(acceptedSopClasses, rejectedSopClasses); - defaultDicomRetrieveMethod_ = StringToRetrieveMethod(lock.GetConfiguration().GetStringParameter("DicomDefaultRetrieveMethod", "C-MOVE")); + defaultDicomRetrieveMethod_ = StringToRetrieveMethod(lock.GetConfiguration().GetDicomDefaultRetrieveMethod()); dynamic_cast<DcmtkTranscoder&>(*dcmtkTranscoder_).SetDefaultLossyQuality(lock.GetConfiguration().GetDicomLossyTranscodingQuality()); }
--- a/OrthancServer/Sources/main.cpp Wed May 06 14:38:37 2026 +0200 +++ b/OrthancServer/Sources/main.cpp Wed May 06 16:55:22 2026 +0200 @@ -71,7 +71,6 @@ static const char* const KEY_DICOM_TLS_MINIMUM_PROTOCOL_VERSION = "DicomTlsMinimumProtocolVersion"; static const char* const KEY_DICOM_TLS_ACCEPTED_CIPHERS = "DicomTlsCiphersAccepted"; static const char* const KEY_MAXIMUM_PDU_LENGTH = "MaximumPduLength"; -static const char* const KEY_READ_ONLY = "ReadOnly"; static const char* const KEY_MAXIMUM_CONCURRENT_DCMTK_TRANSCODERS = "MaximumConcurrentDcmtkTranscoders"; @@ -1117,7 +1116,7 @@ // HTTP server httpServer.SetThreadsCount(lock.GetConfiguration().GetUnsignedIntegerParameter("HttpThreadsCount", 50)); - httpServer.SetPortNumber(lock.GetConfiguration().GetUnsignedIntegerParameter("HttpPort", 8042)); + httpServer.SetPortNumber(lock.GetConfiguration().GetHttpPort()); std::set<std::string> httpBindAddresses; lock.GetConfiguration().GetSetOfStringsParameter(httpBindAddresses, "HttpBindAddresses"); httpServer.SetBindAddresses(httpBindAddresses); @@ -1394,7 +1393,7 @@ OrthancConfiguration::ReaderLock lock; dicomServer.SetCalledApplicationEntityTitleCheck(lock.GetConfiguration().GetBooleanParameter("DicomCheckCalledAet", false)); dicomServer.SetAssociationTimeout(lock.GetConfiguration().GetUnsignedIntegerParameter("DicomScpTimeout", 30)); - dicomServer.SetPortNumber(lock.GetConfiguration().GetUnsignedIntegerParameter("DicomPort", 4242)); + dicomServer.SetPortNumber(lock.GetConfiguration().GetDicomPort()); dicomServer.SetThreadsCount(lock.GetConfiguration().GetUnsignedIntegerParameter("DicomThreadsCount", 4)); dicomServer.SetApplicationEntityTitle(lock.GetConfiguration().GetOrthancAET()); @@ -1680,7 +1679,7 @@ } // New option in Orthanc 1.12.5 - readOnly = lock.GetConfiguration().GetBooleanParameter(KEY_READ_ONLY, false); + readOnly = lock.GetConfiguration().GetBooleanParameter(ORTHANC_CONFIG_READ_ONLY, false); // New option in Orthanc 1.12.6 maxDcmtkConcurrentTranscoders = lock.GetConfiguration().GetUnsignedIntegerParameter(KEY_MAXIMUM_CONCURRENT_DCMTK_TRANSCODERS, 0); @@ -1708,43 +1707,43 @@ { OrthancConfiguration::ReaderLock lock; - context.SetPatientLevelEnabled(lock.GetConfiguration().GetBooleanParameter("PatientLevelEnabled", true)); + context.SetPatientLevelEnabled(lock.GetConfiguration().HasPatientLevelEnabled()); if (context.IsReadOnly()) { - LOG(WARNING) << "READ-ONLY SYSTEM: ignoring these configurations: StorageCompression, StoreMD5ForAttachments, OverwriteInstances, MaximumPatientCount, MaximumStorageSize, MaximumStorageMode, SaveJobs"; + LOG(WARNING) << "READ-ONLY SYSTEM: ignoring these configurations: " << ORTHANC_CONFIG_STORAGE_COMPRESSION << ", " << ORTHANC_CONFIG_STORE_MD5_FOR_ATTACHMENTS << ", " << ORTHANC_CONFIG_OVERWRITE_INSTANCES << ", " << ORTHANC_CONFIG_MAXIMUM_PATIENT_COUNT << ", " << ORTHANC_CONFIG_MAXIMUM_STORAGE_SIZE <<", " << ORTHANC_CONFIG_MAXIMUM_STORAGE_MODE << ", SaveJobs"; } else { - context.SetCompressionEnabled(lock.GetConfiguration().GetBooleanParameter("StorageCompression", false)); - context.SetStoreMD5ForAttachments(lock.GetConfiguration().GetBooleanParameter("StoreMD5ForAttachments", true)); + context.SetCompressionEnabled(lock.GetConfiguration().HasStorageCompression()); + context.SetStoreMD5ForAttachments(lock.GetConfiguration().HasStoreMD5ForAttachments()); // New option in Orthanc 1.4.2 (bool), changed to a string in 1.12.12 OverwriteInstancesMode overwriteInstancesMode = OverwriteInstancesMode_Never; - if (lock.GetJson().isMember("OverwriteInstances")) + if (lock.GetJson().isMember(ORTHANC_CONFIG_OVERWRITE_INSTANCES)) { std::string strOverwriteInstancesMode; - if (lock.GetJson()["OverwriteInstances"].isString() && - lock.GetConfiguration().LookupStringParameter(strOverwriteInstancesMode, "OverwriteInstances")) + if (lock.GetJson()[ORTHANC_CONFIG_OVERWRITE_INSTANCES].isString() && + lock.GetConfiguration().LookupStringParameter(strOverwriteInstancesMode, ORTHANC_CONFIG_OVERWRITE_INSTANCES)) { overwriteInstancesMode = StringToOverwriteInstancesMode(strOverwriteInstancesMode); if (overwriteInstancesMode == OverwriteInstancesMode_IfChanged && !context.IsStoreMD5ForAttachments()) { - LOG(ERROR) << "Can not set \"OverwriteInstances\" to \"IfChanged\" when \"StoreMD5ForAttachments\" is set to false."; + LOG(ERROR) << "Can not set \"" << ORTHANC_CONFIG_OVERWRITE_INSTANCES << "\" to \"IfChanged\" when \"" << ORTHANC_CONFIG_STORE_MD5_FOR_ATTACHMENTS << "\" is set to false."; return false; } } - else if (lock.GetJson()["OverwriteInstances"].isBool()) + else if (lock.GetJson()[ORTHANC_CONFIG_OVERWRITE_INSTANCES].isBool()) { - bool overwriteInstancesLegacy = lock.GetConfiguration().GetBooleanParameter("OverwriteInstances", false); + bool overwriteInstancesLegacy = lock.GetConfiguration().GetBooleanParameter(ORTHANC_CONFIG_OVERWRITE_INSTANCES, false); overwriteInstancesMode = (overwriteInstancesLegacy ? OverwriteInstancesMode_Always : OverwriteInstancesMode_Never); } } context.SetOverwriteInstances(overwriteInstancesMode); - unsigned int maximumPatientCount = lock.GetConfiguration().GetUnsignedIntegerParameter("MaximumPatientCount", 0); - unsigned int maximumStorageSize = lock.GetConfiguration().GetUnsignedIntegerParameter("MaximumStorageSize", 0); + unsigned int maximumPatientCount = lock.GetConfiguration().GetMaximumPatientCount(); + unsigned int maximumStorageSize = lock.GetConfiguration().GetMaximumStorageSize(); if (!context.IsPatientLevelEnabled() && (maximumPatientCount != 0 || maximumStorageSize != 0)) { @@ -1773,7 +1772,7 @@ try { - std::string mode = lock.GetConfiguration().GetStringParameter("MaximumStorageMode", "Recycle"); + std::string mode = lock.GetConfiguration().GetMaximumStorageMode(); context.GetIndex().SetMaximumStorageMode(StringToMaxStorageMode(mode)); } catch (...) @@ -1785,7 +1784,16 @@ // note: this config is valid in ReadOnlyMode try { - uint64_t size = lock.GetConfiguration().GetUnsignedIntegerParameter("MaximumStorageCacheSize", 128); + uint64_t size = lock.GetConfiguration().GetMaximumStorageCacheSize(); + if (size == 0) + { + LOG(WARNING) << "Storage cache is disabled"; + } + else + { + LOG(WARNING) << "Storage cache size is " << size << " MB"; + } + context.SetMaximumStorageCacheSize(size * 1024 * 1024); } catch (...) @@ -1833,11 +1841,9 @@ } { - static const char* const CHECK_REVISIONS = "CheckRevisions"; - OrthancConfiguration::ReaderLock lock; - if (lock.GetConfiguration().GetBooleanParameter(CHECK_REVISIONS, false)) + if (lock.GetConfiguration().HasCheckRevisions()) { if (database.GetDatabaseCapabilities().HasRevisionsSupport()) { @@ -1847,17 +1853,15 @@ else { LOG(WARNING) << "The custom database back-end has *no* support for revisions of metadata and attachments, " - << "but configuration option \"" << CHECK_REVISIONS << "\" is set to \"true\""; + << "but configuration option \"" << ORTHANC_CONFIG_CHECK_REVISIONS << "\" is set to \"true\""; } - static const char* const STORE_MD5 = "StoreMD5ForAttachments"; - - if (!lock.GetConfiguration().GetBooleanParameter(STORE_MD5, true)) + if (!lock.GetConfiguration().HasStoreMD5ForAttachments()) { throw OrthancException( ErrorCode_ParameterOutOfRange, - "The revision system is enabled by configuration option \"" + std::string(CHECK_REVISIONS) + - "\", but won't work properly for attachments if \"" + std::string(STORE_MD5) + "\" is set to \"false\""); + "The revision system is enabled by configuration option \"" + std::string(ORTHANC_CONFIG_CHECK_REVISIONS) + + "\", but won't work properly for attachments if \"" + std::string(ORTHANC_CONFIG_STORE_MD5_FOR_ATTACHMENTS) + "\" is set to \"false\""); } } }
