PACS System 0.1.0
PACS DICOM system library
Loading...
Searching...
No Matches
network_adapter.h
Go to the documentation of this file.
1// BSD 3-Clause License
2// Copyright (c) 2021-2025, 🍀☀🌕🌥 🌊
3// See the LICENSE file in the project root for full license information.
4
19#pragma once
20
22
23#include <chrono>
24#include <cstdint>
25#include <filesystem>
26#include <functional>
27#include <memory>
28#include <string>
29#include <string_view>
30#include <vector>
31
32// KCENON_HAS_COMMON_SYSTEM is defined by CMake when common_system is available
33#ifndef KCENON_HAS_COMMON_SYSTEM
34#define KCENON_HAS_COMMON_SYSTEM 0
35#endif
36
37#if KCENON_HAS_COMMON_SYSTEM
38#include <kcenon/common/patterns/result.h>
39#endif
40
41// Forward declarations for public network_system interfaces
43class i_session;
44class i_protocol_client;
45} // namespace kcenon::network::interfaces
46
47// Forward declarations for legacy session types (used by wrap_session overloads)
50class secure_session;
51} // namespace kcenon::network::session
52
53// Legacy namespace aliases for backward compatibility
55using messaging_session = kcenon::network::session::messaging_session;
56using secure_session = kcenon::network::session::secure_session;
57} // namespace network_system::session
58
59namespace kcenon::pacs::network {
60class dicom_server;
61} // namespace kcenon::pacs::network
62
64
65// Forward declarations
66class dicom_session;
67
68// =============================================================================
69// Result Type and Error Info
70// =============================================================================
71
72#if KCENON_HAS_COMMON_SYSTEM
73template <typename T>
75
76using error_info = kcenon::common::error_info;
77#else
81struct error_info {
82 int code = -1;
83 std::string message;
84 std::string module;
85
86 error_info() = default;
87 error_info(const std::string& msg) : message(msg) {}
88 error_info(int c, const std::string& msg, const std::string& mod = "")
89 : code(c), message(msg), module(mod) {}
90};
91
95template <typename T>
96class Result {
97public:
98 Result(T value) : data_(std::move(value)), has_value_(true) {}
99 Result(const error_info& err) : error_(err), has_value_(false) {}
100
101 [[nodiscard]] bool is_ok() const noexcept { return has_value_; }
102 [[nodiscard]] bool is_err() const noexcept { return !has_value_; }
103 [[nodiscard]] T& value() & { return data_; }
104 [[nodiscard]] const T& value() const& { return data_; }
105 [[nodiscard]] T&& value() && { return std::move(data_); }
106 [[nodiscard]] const error_info& error() const { return error_; }
107
108private:
109 T data_{};
111 bool has_value_;
112};
113#endif
114
115// =============================================================================
116// TLS Configuration
117// =============================================================================
118
128 bool enabled = false;
129
131 std::filesystem::path cert_path;
132
134 std::filesystem::path key_path;
135
137 std::filesystem::path ca_path;
138
140 bool verify_peer = true;
141
144
149 [[nodiscard]] bool is_valid() const noexcept {
150 if (!enabled) return true;
151 return !cert_path.empty() && !key_path.empty();
152 }
153};
154
155// =============================================================================
156// Connection Configuration
157// =============================================================================
158
165 std::string host;
166
168 uint16_t port = 104; // Standard DICOM port
169
171 std::chrono::milliseconds timeout{30000};
172
175
176 connection_config() = default;
177 connection_config(std::string h, uint16_t p)
178 : host(std::move(h)), port(p) {}
179};
180
181// =============================================================================
182// Network Adapter Class
183// =============================================================================
184
224public:
225 // ─────────────────────────────────────────────────────
226 // Type Aliases
227 // ─────────────────────────────────────────────────────
228
230 using session_ptr = std::shared_ptr<dicom_session>;
231
233 using connection_callback = std::function<void(session_ptr)>;
234
236 using disconnection_callback = std::function<void(const std::string&)>;
237
239 using error_callback = std::function<void(session_ptr, std::error_code)>;
240
241 // ─────────────────────────────────────────────────────
242 // Server Creation
243 // ─────────────────────────────────────────────────────
244
257 [[nodiscard]] static std::unique_ptr<network::dicom_server>
259 const tls_config& tls_cfg = {});
260
261 // ─────────────────────────────────────────────────────
262 // Client Connection
263 // ─────────────────────────────────────────────────────
264
286 [[nodiscard]] static Result<session_ptr> connect(
287 const connection_config& config);
288
297 [[nodiscard]] static Result<session_ptr> connect(
298 const std::string& host,
299 uint16_t port,
300 std::chrono::milliseconds timeout = std::chrono::seconds{30});
301
302 // ─────────────────────────────────────────────────────
303 // TLS Configuration
304 // ─────────────────────────────────────────────────────
305
331 [[nodiscard]] static Result<std::monostate> configure_tls(
332 const tls_config& config);
333
334 // ─────────────────────────────────────────────────────
335 // Session Wrapping
336 // ─────────────────────────────────────────────────────
337
347 [[nodiscard]] static session_ptr wrap_session(
348 std::shared_ptr<network_system::session::messaging_session> session);
349
356 [[nodiscard]] static session_ptr wrap_session(
357 std::shared_ptr<network_system::session::secure_session> session);
358
365 [[nodiscard]] static session_ptr wrap_session(
366 std::shared_ptr<kcenon::network::interfaces::i_session> session);
367
368private:
369 // Prevent instantiation
370 network_adapter() = delete;
374};
375
376} // namespace kcenon::pacs::integration
Simple result type for error handling when common_system is unavailable.
const error_info & error() const
Adapter for integrating network_system for DICOM protocol.
static Result< std::monostate > configure_tls(const tls_config &config)
std::function< void(session_ptr, std::error_code)> error_callback
Error callback type.
static std::unique_ptr< network::dicom_server > create_server(const network::server_config &config, const tls_config &tls_cfg={})
Create a DICOM server using network_system.
std::shared_ptr< dicom_session > session_ptr
Session pointer type.
std::function< void(const std::string &)> disconnection_callback
Disconnection callback type.
static session_ptr wrap_session(std::shared_ptr< network_system::session::messaging_session > session)
Wrap a network_system session for DICOM communication.
std::function< void(session_ptr)> connection_callback
Connection callback type.
static Result< session_ptr > connect(const connection_config &config)
network_adapter & operator=(const network_adapter &)=delete
network_adapter(const network_adapter &)=delete
kcenon::common::Result< T > Result
Result type alias for PACS operations.
Definition result.h:30
kcenon::common::error_info error_info
Error information type.
Definition result.h:40
kcenon::network::session::messaging_session messaging_session
kcenon::network::session::secure_session secure_session
DICOM Server configuration structures.
Configuration for client connections.
std::chrono::milliseconds timeout
Connection timeout.
tls_config tls
TLS configuration (optional)
Simple error info for fallback when common_system is unavailable.
error_info(int c, const std::string &msg, const std::string &mod="")
Configuration for TLS/SSL secure transport.
bool enabled
Enable TLS for connections.
enum kcenon::pacs::integration::tls_config::tls_version min_version
bool is_valid() const noexcept
Check if TLS configuration is valid.
std::filesystem::path cert_path
Path to certificate file (PEM format)
tls_version
Minimum TLS version (1.2 recommended for DICOM)
std::filesystem::path ca_path
Path to CA certificate file for verification (optional)
bool verify_peer
Verify peer certificate.
std::filesystem::path key_path
Path to private key file (PEM format)