Skip to content

Commit 2b21057

Browse files
authored
refactor(api): add deprecation markers for v1.0 API freeze (#676)
* refactor(api): add deprecation markers for v1.0 API freeze Mark legacy APIs scheduled for removal in v2.0.0 so consumers see compiler warnings during the migration window. The v3.0.0 pass removed legacy types but left transitional surfaces without [[deprecated]] attributes. - compatibility.h: emit #pragma message for thread_system/thread_module/ thread_namespace/utility_module aliases (namespace aliases cannot carry a portable [[deprecated]] attribute). Suppressible via THREAD_SUPPRESS_LEGACY_NAMESPACE_WARNING. - thread_logger.h: attach [[deprecated]] to user-facing methods (log/log_error/set_level/set_enabled/set_lightweight_mode). Keep the SDOF-safe helpers (instance/is_shutting_down/prepare_shutdown) stable because thread_context still depends on them. Leave log_level enum without an attribute to avoid internal self-warnings from member declarations; its deprecation propagates through the deprecated methods that accept it. - lockfree/lockfree_queue.h: emit #pragma message on include of the forwarding header. Suppressible via THREAD_SUPPRESS_LEGACY_LOCKFREE_QUEUE_WARNING. - queue.cppm: define the suppression macro before including lockfree_queue.h so the module re-export path stays quiet. Part of #670 Closes #672 * docs(migration): document v1.0.0 API freeze and deprecation policy Add a v1.0.0 section to MIGRATION.md that records the frozen public surface, the deprecated APIs scheduled for removal in v2.0.0, and the migration paths and suppression macros consumers can use during the migration window. Previously the document only described the v3.0.0 common_system transition. With v1.0.0 being an API stability commitment, consumers need a single place that lists what is frozen, what remains transitional, and how to silence legacy include warnings without editing upstream headers. Part of #670 Closes #672
1 parent 2b70ad1 commit 2b21057

5 files changed

Lines changed: 172 additions & 8 deletions

File tree

docs/advanced/MIGRATION.md

Lines changed: 73 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ category: "MIGR"
1616
1717
## Table of Contents
1818

19+
- [v1.0.0 API Freeze (current)](#v100-api-freeze-current)
1920
- [v3.0.0 Migration (common_system)](#v300-migration-common_system)
2021
- [Overview](#overview)
2122
- [Migration Status](#migration-status)
@@ -35,6 +36,78 @@ category: "MIGR"
3536
- [Current Status (2025-09-13)](#current-status-2025-09-13)
3637
- [Detailed Status Log](#detailed-status-log)
3738

39+
## v1.0.0 API Freeze (current)
40+
41+
**Release Date:** 2026-04-14
42+
43+
v1.0.0 is an **API stability commitment**. From v1.0.0 onward, any breaking change
44+
to the public API requires a major version bump. This section records the surface
45+
that was frozen and the legacy APIs that remain only for migration support.
46+
47+
### Frozen Public Surface
48+
49+
The authoritative public headers live under `include/kcenon/thread/`:
50+
51+
| Subsystem | Path | Notes |
52+
|-----------|------|-------|
53+
| Core threading | `core/` | `thread_pool`, `thread_worker`, `job`, `job_queue`, `cancellation_token`, `future_job`, `submit_options` |
54+
| Queues | `queue/`, `concurrent/` | `adaptive_job_queue`, `concurrent_queue`, `queue_factory` |
55+
| DAG | `dag/` | `dag_scheduler`, `dag_job`, `dag_job_builder` |
56+
| Configuration | `thread_config.h`, `config/` | Unified builder for pool, DAG, and aging settings |
57+
| Error handling | `core/error_handling.h` | `error_code` enum + `common::Result<T>` / `common::VoidResult` helpers |
58+
| Synchronization | `core/sync_primitives.h`, `core/hazard_pointer.h` | Lock-free reclamation helpers |
59+
60+
### Deprecated in v1.0.0 (slated for removal in v2.0.0)
61+
62+
The following APIs emit compiler warnings in v1.0.0 and will be removed in v2.0.0.
63+
64+
| Symbol | Replacement | Trigger |
65+
|--------|-------------|---------|
66+
| `thread_system::` / `thread_module::` / `thread_namespace::` namespace aliases | Use `kcenon::thread::` directly | `#pragma message` on `compatibility.h` include |
67+
| `utility_module::` namespace alias | Use `kcenon::thread::utils::` directly | `#pragma message` on `compatibility.h` include |
68+
| `kcenon::thread::log_level` (enum in `thread_logger.h`) | `kcenon::thread::log_level_v2` or `common::interfaces::log_level` | Warnings via the deprecated `thread_logger` methods that consume it |
69+
| `kcenon::thread::thread_logger::log()`, `log_error()`, `set_enabled()`, `is_enabled()`, `set_level()`, `set_lightweight_mode()`, `is_lightweight_mode()` | `thread_context::log()` with `common::interfaces::ILogger` | `[[deprecated]]` attribute |
70+
| `<kcenon/thread/lockfree/lockfree_queue.h>` (forwarding header) | `<kcenon/thread/concurrent/concurrent_queue.h>` | `#pragma message` on include |
71+
| `<kcenon/thread/core/thread_pool_fmt.h>` (forwarding header) | `<kcenon/thread/formatters.h>` | `#pragma message` on include (pre-existing) |
72+
| `<kcenon/thread/dag/dag_config.h>` (documentation-only deprecation) | `<kcenon/thread/thread_config.h>` builder | Doxygen `@deprecated` |
73+
| `<kcenon/thread/impl/typed_pool/priority_aging_config.h>` (documentation-only deprecation) | `<kcenon/thread/thread_config.h>` builder | Doxygen `@deprecated` |
74+
75+
### Silencing Legacy Warnings During Migration
76+
77+
While migrating a dependent project, warnings emitted by legacy headers can be
78+
silenced by defining the following macros **before** the `#include`:
79+
80+
```cpp
81+
// Legacy namespace aliases in compatibility.h
82+
#define THREAD_SUPPRESS_LEGACY_NAMESPACE_WARNING 1
83+
#include <kcenon/thread/compatibility.h>
84+
85+
// Legacy forwarding header lockfree_queue.h
86+
#define THREAD_SUPPRESS_LEGACY_LOCKFREE_QUEUE_WARNING 1
87+
#include <kcenon/thread/lockfree/lockfree_queue.h>
88+
```
89+
90+
These macros must be removed before v2.0.0 adoption.
91+
92+
### API Changes Since v3.0.0
93+
94+
- `cancellation_token::check_cancelled()` returns `common::VoidResult`
95+
(previously `throw_if_cancelled()` threw `std::runtime_error`). See #671.
96+
- `cancellable_future<T>::get()` / `get_for()` return
97+
`common::Result<T>` / `common::Result<std::optional<T>>`. See #671.
98+
- `thread_pool::submit_wait_any()` returns `common::Result<R>` with
99+
`error_code::invalid_argument` for empty input. See #671.
100+
101+
### Removed in v1.0.0
102+
103+
Previously removed in v3.0.0 (kept for reference):
104+
105+
- `kcenon::thread::result<T>` / `result_void` / `error` — use `common::Result<T>` / `common::VoidResult` / `common::error_info`.
106+
- `kcenon::thread::logger_interface` / `monitoring_interface` / `monitorable_interface` — use `common::interfaces::ILogger` / `IMonitor` / `IMonitorable`.
107+
- `kcenon::thread::throw_if_cancelled()` — removed in #671, replaced by `check_cancelled()` returning `common::VoidResult`.
108+
109+
---
110+
38111
## v3.0.0 Migration (common_system)
39112
40113
**Release Date:** 2025-12-19

include/kcenon/thread/compatibility.h

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,9 +24,28 @@ namespace detail {}
2424

2525
// Legacy namespace aliases. These remain until dependent projects
2626
// migrate to the unified kcenon::thread namespace.
27+
//
28+
// @deprecated Since v1.0.0. These aliases will be removed in v2.0.0.
29+
// Use `kcenon::thread` and `kcenon::thread::utils` directly instead.
30+
//
31+
// NOTE: The C++ standard does not support `[[deprecated]]` on namespace
32+
// aliases (only on namespace definitions). Consumers that need compile-time
33+
// warnings should migrate include-by-include; an include-guard warning is
34+
// emitted once per translation unit below (suppressible by defining
35+
// THREAD_SUPPRESS_LEGACY_NAMESPACE_WARNING before the include).
2736
namespace thread_system = kcenon::thread;
2837
namespace thread_module = kcenon::thread;
2938
namespace thread_namespace = kcenon::thread;
3039

3140
// Legacy utility namespace names still expected by some consumers.
3241
namespace utility_module = kcenon::thread::utils;
42+
43+
#if !defined(THREAD_SUPPRESS_LEGACY_NAMESPACE_WARNING) \
44+
&& !defined(KCENON_THREAD_COMPATIBILITY_H_WARNED)
45+
#define KCENON_THREAD_COMPATIBILITY_H_WARNED 1
46+
#if defined(_MSC_VER)
47+
#pragma message("thread_system/thread_module/thread_namespace/utility_module namespace aliases are deprecated since v1.0.0 and will be removed in v2.0.0. Use 'kcenon::thread' directly. Define THREAD_SUPPRESS_LEGACY_NAMESPACE_WARNING to silence this warning.")
48+
#elif defined(__GNUC__) || defined(__clang__)
49+
#pragma message "thread_system/thread_module/thread_namespace/utility_module namespace aliases are deprecated since v1.0.0 and will be removed in v2.0.0. Use 'kcenon::thread' directly. Define THREAD_SUPPRESS_LEGACY_NAMESPACE_WARNING to silence this warning."
50+
#endif
51+
#endif

include/kcenon/thread/core/thread_logger.h

Lines changed: 65 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,18 @@ namespace kcenon::thread {
2626

2727
/**
2828
* @enum log_level
29-
* @brief Logging severity levels
29+
* @brief Logging severity levels (legacy).
30+
*
31+
* @deprecated Since v1.0.0. Use `kcenon::thread::log_level_v2` (from
32+
* `<kcenon/thread/core/log_level.h>`) or `common::interfaces::log_level`
33+
* (from common_system) instead. Will be removed in v2.0.0.
34+
* See Issue #261 for migration details.
35+
*
36+
* NOTE: `[[deprecated]]` is applied at the `thread_logger` member-function
37+
* level (log/set_level/log_error) rather than on this enum itself, because
38+
* this type is still referenced internally by the SDOF-safe shutdown
39+
* helpers. Using `log_level` via a deprecated API emits a warning; direct
40+
* use without the logger does not.
3041
*/
3142
enum class log_level {
3243
trace,
@@ -108,34 +119,60 @@ class thread_logger {
108119
}
109120

110121
/**
111-
* @brief Enable/disable logging
122+
* @brief Enable/disable logging.
123+
*
124+
* @deprecated Since v1.0.0. Inject a `common::interfaces::ILogger`
125+
* via `thread_context` and control logging through its implementation
126+
* instead. Will be removed in v2.0.0.
112127
*/
128+
[[deprecated(
129+
"Use 'common::interfaces::ILogger' via thread_context instead. "
130+
"Will be removed in v2.0.")]]
113131
void set_enabled(bool enabled) {
114132
enabled_ = enabled;
115133
}
116134

117135
/**
118-
* @brief Check if logging is enabled
136+
* @brief Check if logging is enabled.
137+
*
138+
* @deprecated Since v1.0.0. Check availability through
139+
* `thread_context::has_logger()` instead. Will be removed in v2.0.0.
119140
*/
141+
[[deprecated(
142+
"Use 'thread_context::has_logger()' instead. "
143+
"Will be removed in v2.0.")]]
120144
bool is_enabled() const {
121145
return enabled_;
122146
}
123147

124148
/**
125-
* @brief Set minimum log level
149+
* @brief Set minimum log level.
150+
*
151+
* @deprecated Since v1.0.0. Configure log level on the injected
152+
* `common::interfaces::ILogger` implementation instead.
153+
* Will be removed in v2.0.0.
126154
*/
155+
[[deprecated(
156+
"Configure log level on 'common::interfaces::ILogger' instead. "
157+
"Will be removed in v2.0.")]]
127158
void set_level(log_level level) {
128159
min_level_ = level;
129160
}
130161

131162
/**
132-
* @brief Log a message with context
163+
* @brief Log a message with context.
133164
*
134165
* @param level Severity level
135166
* @param thread_name Thread identifier
136167
* @param message Log message
137168
* @param context Additional context (optional)
169+
*
170+
* @deprecated Since v1.0.0. Use `thread_context::log()` backed by
171+
* `common::interfaces::ILogger` instead. Will be removed in v2.0.0.
138172
*/
173+
[[deprecated(
174+
"Use 'thread_context::log()' with 'common::interfaces::ILogger' "
175+
"instead. Will be removed in v2.0.")]]
139176
void log(log_level level, std::string_view thread_name,
140177
std::string_view message, std::string_view context = "") {
141178
// Early return during shutdown to avoid accessing potentially destroyed resources
@@ -179,9 +216,16 @@ class thread_logger {
179216
}
180217

181218
/**
182-
* @brief Log error with error code
219+
* @brief Log error with error code.
220+
*
221+
* @deprecated Since v1.0.0. Use `thread_context::log()` with a
222+
* `common::interfaces::ILogger` implementation instead. Will be
223+
* removed in v2.0.0.
183224
*/
184225
template<typename ErrorType>
226+
[[deprecated(
227+
"Use 'thread_context::log()' with 'common::interfaces::ILogger' "
228+
"instead. Will be removed in v2.0.")]]
185229
void log_error(std::string_view thread_name, const ErrorType& error) {
186230
// Early return during shutdown
187231
if (is_shutting_down_.load(std::memory_order_acquire) || !enabled_) {
@@ -229,14 +273,21 @@ class thread_logger {
229273

230274
public:
231275
/**
232-
* @brief Enable lightweight mode (disables all logging for maximum performance)
276+
* @brief Enable lightweight mode (disables all logging for maximum performance).
233277
*
234278
* In lightweight mode, all log calls become no-ops with minimal overhead.
235279
* Useful for performance-critical production deployments where diagnostics
236280
* are handled externally.
237281
*
238282
* @param enabled true to enable lightweight mode, false to use normal logging
283+
*
284+
* @deprecated Since v1.0.0. With `common::interfaces::ILogger`, a
285+
* null logger in `thread_context` achieves the same effect without
286+
* this toggle. Will be removed in v2.0.0.
239287
*/
288+
[[deprecated(
289+
"Use a null 'common::interfaces::ILogger' in thread_context to "
290+
"disable logging. Will be removed in v2.0.")]]
240291
void set_lightweight_mode(bool enabled) {
241292
lightweight_mode_ = enabled;
242293
// Disable logging when in lightweight mode
@@ -246,8 +297,14 @@ class thread_logger {
246297
}
247298

248299
/**
249-
* @brief Check if in lightweight mode
300+
* @brief Check if in lightweight mode.
301+
*
302+
* @deprecated Since v1.0.0. See `set_lightweight_mode` deprecation.
303+
* Will be removed in v2.0.0.
250304
*/
305+
[[deprecated(
306+
"Superseded by 'common::interfaces::ILogger' injection. "
307+
"Will be removed in v2.0.")]]
251308
bool is_lightweight_mode() const {
252309
return lightweight_mode_;
253310
}

include/kcenon/thread/lockfree/lockfree_queue.h

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,5 +48,15 @@
4848

4949
#pragma once
5050

51+
#if !defined(THREAD_SUPPRESS_LEGACY_LOCKFREE_QUEUE_WARNING) \
52+
&& !defined(KCENON_THREAD_LOCKFREE_QUEUE_H_WARNED)
53+
#define KCENON_THREAD_LOCKFREE_QUEUE_H_WARNED 1
54+
#if defined(_MSC_VER)
55+
#pragma message("<kcenon/thread/lockfree/lockfree_queue.h> is deprecated since v1.0.0 and will be removed in v2.0.0. Include <kcenon/thread/concurrent/concurrent_queue.h> instead. Define THREAD_SUPPRESS_LEGACY_LOCKFREE_QUEUE_WARNING to silence this warning.")
56+
#elif defined(__GNUC__) || defined(__clang__)
57+
#pragma message "<kcenon/thread/lockfree/lockfree_queue.h> is deprecated since v1.0.0 and will be removed in v2.0.0. Include <kcenon/thread/concurrent/concurrent_queue.h> instead. Define THREAD_SUPPRESS_LEGACY_LOCKFREE_QUEUE_WARNING to silence this warning."
58+
#endif
59+
#endif
60+
5161
// Include the new location
5262
#include <kcenon/thread/concurrent/concurrent_queue.h>

src/modules/queue.cppm

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,11 @@ module;
3838
#include <kcenon/thread/core/job_queue.h>
3939
#include <kcenon/thread/queue/adaptive_job_queue.h>
4040
#include <kcenon/thread/queue/queue_factory.h>
41+
42+
// The legacy lockfree_queue.h re-exports concurrent_queue under the old
43+
// name for backward compatibility. Suppress its deprecation notice here
44+
// because the module itself is the authorized re-exporter.
45+
#define THREAD_SUPPRESS_LEGACY_LOCKFREE_QUEUE_WARNING 1
4146
#include <kcenon/thread/lockfree/lockfree_queue.h>
4247
#include <kcenon/thread/lockfree/lockfree_job_queue.h>
4348
#include <kcenon/thread/lockfree/work_stealing_deque.h>

0 commit comments

Comments
 (0)