On this page

C-Core SDK 7.0.0 migration guide

This guide summarizes the differences between 6.X.X versions and 7.0.0 and shows how to migrate to C-Core SDK 7.0.0.

C-Core SDK version 7.0.0 makes DNS server configuration per-context, replaces the logging subsystem with an advanced pluggable logger architecture, and adds logging methods to the C++ wrapper class. This applies to all C-Core SDK flavors: C-Core, POSIX C, POSIX C++, Windows C, Windows C++, FreeRTOS, and Mbed.

Earlier migration guides

If you are upgrading from a version before 6.0.0, read the C-Core SDK 6.0.0 migration guide first.

What has changed

See the major differences between versions:

FeatureC-Core SDK 6.X.XC-Core SDK 7.0.0
DNS server functions
Global (no context parameter)
Per-context (pubnub_t* pb added as first parameter)
Logging header
#include "core/pubnub_log.h"
#include "core/pubnub_logger.h"
Logging functions
PUBNUB_LOG_PRINTF(...) macros
pubnub_log_text(), pubnub_log_text_formatted(), pubnub_log_object(), pubnub_log_error()
Log level enum
Sequential: NONE=0, ERROR=1, ... TRACE=5
Bitmask: TRACE=1, DEBUG=2, INFO=4, WARNING=8, ERROR=16, NONE=32
Compile-time level macro
PUBNUB_LOG_LEVEL
PUBNUB_LOG_MIN_LEVEL
Custom output / runtime callback
Override PUBNUB_LOG_PRINTF macro or pubnub_set_log_callback(fn)
Register custom pubnub_logger_t with pubnub_logger_add(pb, logger)
WATCH_* macros
WATCH_INT(x), WATCH_STR(x), etc.
Removed. Use structured logging (pubnub_log_object)
C++ wrapper (POSIX C++, Windows C++)
No logging methods
New methods: logger_add, logger_remove, set_log_level, log_text, log_object, log_error
Feature flags
Always compiled in
PUBNUB_USE_LOGGER, PUBNUB_USE_DEFAULT_LOGGER

Breaking changes

ChangePlatforms affected
DNS server API
All (C-Core, POSIX C, POSIX C++, Windows C, Windows C++, FreeRTOS, Mbed)
Logging subsystem
All
Log level changes
All
Build configuration
All
C++ wrapper
POSIX C++, Windows C++
Platform-specific default loggers
POSIX C, POSIX C++, Windows C, Windows C++, FreeRTOS, Microchip Harmony

DNS server API

Applies to: All platforms

Starting with 7.0.0, all 14 DNS server functions in core/pubnub_dns_servers.h require a pubnub_t* context as their first parameter. Previously, these functions operated on global state. Now DNS server configuration is per-context.

This change affects all functions guarded by PUBNUB_SET_DNS_SERVERS.

IPv4 functions

FunctionC-Core SDK 6.X.XC-Core SDK 7.0.0
pubnub_dns_set_primary_server_ipv4
(struct pubnub_ipv4_address ipv4)
(pubnub_t* pb, struct pubnub_ipv4_address ipv4)
pubnub_dns_set_secondary_server_ipv4
(struct pubnub_ipv4_address ipv4)
(pubnub_t* pb, struct pubnub_ipv4_address ipv4)
pubnub_dns_set_primary_server_ipv4_str
(char const* ipv4_str)
(pubnub_t* pb, char const* ipv4_str)
pubnub_dns_set_secondary_server_ipv4_str
(char const* ipv4_str)
(pubnub_t* pb, char const* ipv4_str)
pubnub_get_dns_primary_server_ipv4
(struct pubnub_ipv4_address* o_ipv4)
(pubnub_t* pb, struct pubnub_ipv4_address* o_ipv4)
pubnub_get_dns_secondary_server_ipv4
(struct pubnub_ipv4_address* o_ipv4)
(pubnub_t* pb, struct pubnub_ipv4_address* o_ipv4)
pubnub_dns_read_system_servers_ipv4
(struct pubnub_ipv4_address* o_ipv4, size_t n)
(pubnub_t* pb, struct pubnub_ipv4_address* o_ipv4, size_t n)

IPv6 functions (require PUBNUB_USE_IPV6)

FunctionC-Core SDK 6.X.XC-Core SDK 7.0.0
pubnub_dns_set_primary_server_ipv6
(struct pubnub_ipv6_address ipv6)
(pubnub_t* pb, struct pubnub_ipv6_address ipv6)
pubnub_dns_set_secondary_server_ipv6
(struct pubnub_ipv6_address ipv6)
(pubnub_t* pb, struct pubnub_ipv6_address ipv6)
pubnub_dns_set_primary_server_ipv6_str
(char const* ipv6_str)
(pubnub_t* pb, char const* ipv6_str)
pubnub_dns_set_secondary_server_ipv6_str
(char const* ipv6_str)
(pubnub_t* pb, char const* ipv6_str)
pubnub_get_dns_primary_server_ipv6
(struct pubnub_ipv6_address* o_ipv6)
(pubnub_t* pb, struct pubnub_ipv6_address* o_ipv6)
pubnub_get_dns_secondary_server_ipv6
(struct pubnub_ipv6_address* o_ipv6)
(pubnub_t* pb, struct pubnub_ipv6_address* o_ipv6)
pubnub_dns_read_system_servers_ipv6
N/A (new in 6.2.0)
(pubnub_t* pb, struct pubnub_ipv6_address* o_ipv6, size_t n)
Fallback macros

The fallback macros (when PUBNUB_SET_DNS_SERVERS is disabled) also gained the pb parameter, so code using the macro forms also needs updating.

#include "core/pubnub_dns_servers.h"

/* DNS servers were global — no context needed */
struct pubnub_ipv4_address dns = {{8, 8, 8, 8}};
pubnub_dns_set_primary_server_ipv4(dns);
pubnub_dns_set_secondary_server_ipv4_str("8.8.4.4");

/* Read system DNS servers */
struct pubnub_ipv4_address servers[4];
int count = pubnub_dns_read_system_servers_ipv4(servers, 4);

Logging subsystem

Applies to: All platforms

Starting with 7.0.0, the SDK replaces its legacy logging subsystem (core/pubnub_log.h) with a new advanced logging system (core/pubnub_logger.h). The new system introduces per-context logging, multiple simultaneous logger support, structured data logging, network request/response logging, and runtime log level control.

The files core/pubnub_log.h and core/pubnub_log.c are deleted. Any direct references to them cause compilation errors.

Removed APIs

The following are deleted and cause compilation errors if referenced:

Removed APIReplacement
#include "core/pubnub_log.h"
#include "core/pubnub_logger.h"
PUBNUB_LOG_PRINTF(...)
pubnub_log_text_formatted(pb, level, location, format, ...)
PUBNUB_LOG_ERROR(...), PUBNUB_LOG_WARNING(...), PUBNUB_LOG_INFO(...), PUBNUB_LOG_DEBUG(...), PUBNUB_LOG_TRACE(...)
pubnub_log_text_formatted(pb, level, location, format, ...)
WATCH_INT(x), WATCH_STR(x), WATCH_ENUM(x), WATCH_ULONG(x)
pubnub_log_object(pb, level, location, value, details)
pubnub_set_log_callback(fn) / PUBNUB_USE_LOG_CALLBACK
Create a custom pubnub_logger_t and register with pubnub_logger_add(pb, logger). PUBNUB_USE_LOGGER controls whether the logging subsystem is compiled in.
PUBNUB_LOG_LEVEL (compile-time macro)
PUBNUB_LOG_MIN_LEVEL

New logging public API

All functions are part of the public C API in core/pubnub_logger.h.

Logger lifecycle
FunctionDescription
pubnub_logger_alloc(vtable, user_data)
Create a custom logger with a vtable and optional user data. Returns NULL on failure.
pubnub_logger_user_data(logger)
Retrieve user data associated with a custom logger.
pubnub_logger_free(logger)
Free a custom logger. Calls the logger's destroy() callback if provided. Sets *logger to NULL.
Logger registration
FunctionDescription
pubnub_logger_add(pb, logger)
Register a custom logger with a PubNub context. Multiple loggers can be registered. Returns 0 on success.
pubnub_logger_remove(pb, logger)
Unregister a custom logger. Caller must still call pubnub_logger_free(). Returns 0 on success.
pubnub_logger_remove_all(pb)
Unregister all custom loggers. Caller must free each logger individually.
Log level control
FunctionDescription
pubnub_logger_set_log_level(pb, level)
Set the minimum log level. Messages below this level are not dispatched.
pubnub_logger_log_level(pb)
Get the current minimum log level. Default: PUBNUB_LOG_LEVEL_DEBUG.
Logging functions
FunctionDescription
pubnub_log_text(pb, level, location, message)
Log a plain text message.
pubnub_log_text_formatted(pb, level, location, format, ...)
Log a formatted text message (printf-style).
pubnub_log_object(pb, level, location, value, details)
Log a structured object/data.
pubnub_log_error(pb, location, error_code, error_message, details)
Log an error. Level is always PUBNUB_LOG_LEVEL_ERROR.

Replace logging macros

#include "core/pubnub_log.h"

PUBNUB_LOG_ERROR("Failed to publish: %d", result);
PUBNUB_LOG_DEBUG("Channel: %s", channel);

Replace PUBNUB_LOG_PRINTF override

/* Compile-time macro override */
#define PUBNUB_LOG_PRINTF(...) my_log_func(__VA_ARGS__)

Replace pubnub_set_log_callback

void my_callback(enum pubnub_log_level level, const char* message) {
fprintf(log_file, "[%d] %s", level, message);
}
pubnub_set_log_callback(my_callback);

Replace WATCH_* macros

WATCH_INT(result);
WATCH_STR(channel);
Structured logging scope

All pubnub_log_value_t structures and their string pointers live on the stack. All values, containers, and the log call must be in the same scope. If a value goes out of scope before the logging function reads it, you get undefined behavior.

Log level changes

Applies to: All platforms

The log level enum changed from sequential integers with reversed ordering to bitmask powers of 2 with natural ordering.

/* Sequential integers, REVERSED ordering (NONE is lowest) */
enum pubnub_log_level {
PUBNUB_LOG_LEVEL_NONE = 0, /* Logging disabled */
PUBNUB_LOG_LEVEL_ERROR = 1,
PUBNUB_LOG_LEVEL_WARNING = 2,
PUBNUB_LOG_LEVEL_INFO = 3,
PUBNUB_LOG_LEVEL_DEBUG = 4,
PUBNUB_LOG_LEVEL_TRACE = 5 /* Most verbose */
};
/* Filter: if (level <= PUBNUB_LOG_LEVEL) → emit */
Comparison direction changed

If your code compares log level values numerically (for example, if (level <= PUBNUB_LOG_LEVEL_INFO)), the comparison direction has changed. In the old system NONE < ERROR < TRACE. In the new system TRACE < DEBUG < INFO < WARNING < ERROR < NONE.

Build configuration

Applies to: All platforms

Compile-time log level stripping

The compile-time macro for log level filtering has changed.

# Old build flag
-DPUBNUB_LOG_LEVEL=PUBNUB_LOG_LEVEL_WARNING

C++ wrapper

Applies to: POSIX C++, Windows C++

New methods are added to the pubnub::context class in cpp/pubnub_common.hpp, guarded by #if PUBNUB_USE_LOGGER. These delegate directly to the C public API functions.

MethodDescription
logger_add(pubnub_logger_t* logger)
Register a custom logger. Returns 0 on success.
logger_remove(pubnub_logger_t* logger)
Unregister a custom logger. Returns 0 on success.
logger_remove_all()
Unregister all custom loggers.
set_log_level(pubnub_log_level level)
Set minimum log level for this context.
log_level()
Get current minimum log level. Default: PUBNUB_LOG_LEVEL_DEBUG.
log_text(pubnub_log_level level, char const* location, char const* message)
Log a plain text message.
log_text(pubnub_log_level level, char const* location, std::string const& message)
Log a text message from std::string.
log_object(pubnub_log_level level, char const* location, pubnub_log_value_t const* message, char const* details)
Log a structured object with optional details.
log_error(char const* location, int error_code, char const* error_message, char const* details)
Log an error (always PUBNUB_LOG_LEVEL_ERROR).

Basic C++ logging

#include "pubnub_common.hpp"

pubnub::context ctx("demo", "demo");

/* Log simple text messages */
ctx.log_text(PUBNUB_LOG_LEVEL_INFO,
"main.cpp:10",
"PubNub context initialized");

/* Log with std::string */
std::string msg = "Subscribing to channel: " + channel_name;
ctx.log_text(PUBNUB_LOG_LEVEL_DEBUG, "main.cpp:15", msg);

/* Log an error */
ctx.log_error("main.cpp:25", -1, "Connection failed", "Timeout after 30s");

Custom logger in C++

#include "pubnub_common.hpp"
#include "core/pubnub_logger.h"

static void my_info_handler(const pubnub_logger_t* logger,
const pubnub_log_message_t* message) {
if (message->message_type == PUBNUB_LOG_MESSAGE_TYPE_TEXT) {
const pubnub_log_message_text_t* text =
(const pubnub_log_message_text_t*)message;
std::cout << "[INFO] " << text->message << std::endl;
}
}

static const struct pubnub_logger_interface my_vtable = {
.trace = NULL,
.debug = NULL,
show all 37 lines

Feature flags

Two new macros control the logging subsystem. Both are defined in each platform's pubnub_config.h and default to 1 (enabled).

MacroDefaultDescription
PUBNUB_USE_LOGGER
1
Enable/disable the entire logging subsystem. When 0, all logging macros become no-ops and logger API functions are not compiled.
PUBNUB_USE_DEFAULT_LOGGER
1
Enable/disable the built-in default platform logger. When 0, no logger is registered automatically — you must register your own via pubnub_logger_add().

New source files

If you maintain custom build scripts or Makefiles, add the following files.

Always required when PUBNUB_USE_LOGGER=1
FilePurpose
core/pubnub_logger.c
Public logger API implementation
core/pbcc_logger_manager.c
Logger manager (dispatches to registered loggers)
core/pubnub_log_value.c
Structured log value types
Required only when PUBNUB_USE_DEFAULT_LOGGER=1

Add exactly one platform-specific default logger:

PlatformFile
POSIX / Windows
core/pubnub_stdio_logger.c
FreeRTOS
freertos/pubnub_freertos_logger.c
Microchip Harmony
microchip_harmony/pubnub_harmony_logger.c

Platform-specific default loggers

Applies to: All platforms (each platform uses its own logger implementation)

When PUBNUB_USE_DEFAULT_LOGGER is 1 (default), each new PubNub context automatically registers a platform-appropriate logger.

PlatformFileOutputTimestamps
POSIX / Windows
core/pubnub_stdio_logger.c
fprintf(stdout) for TRACE/DEBUG/INFO/WARN; fprintf(stderr) for ERROR
ISO 8601 with milliseconds
FreeRTOS
freertos/pubnub_freertos_logger.c
printf() for all levels
ISO 8601 when wall-clock available; xTaskGetTickCount() tick-based fallback
Microchip Harmony
microchip_harmony/pubnub_harmony_logger.c
SYS_CONSOLE_PRINT() for all levels
Raw Unix timestamp; SYS_TMR_TickCountGet() fallback
Output format example (POSIX/Windows)
2026-03-03T10:11:31.456Z PubNub-a1b2c3d4 DEBUG core/pubnub_coreapi.c:123 Publishing to channel 'my-channel'

Migration steps

To migrate to C-Core SDK 7.0.0:

  1. Update DNS server function calls. Add pubnub_t* context as the first argument to all DNS server functions:

    ActionDescription
    Add pb as the first argument to all pubnub_dns_set_*, pubnub_get_dns_*, and pubnub_dns_read_system_servers_* calls
    All 14 DNS functions (7 IPv4 + 7 IPv6) now require a pubnub_t* context. This also applies to fallback macros when PUBNUB_SET_DNS_SERVERS is disabled.
  2. Update logging includes:

    ActionDescription
    Replace #include "core/pubnub_log.h" with #include "core/pubnub_logger.h"
    The old header file is deleted. For structured log values and convenience macros, also include core/pubnub_log_value.h.
  3. Replace old logging macros with public API functions:

    ActionDescription
    Replace PUBNUB_LOG_ERROR(...), PUBNUB_LOG_WARNING(...), etc. with pubnub_log_text_formatted()
    The new function requires a pubnub_t* context, a log level, a location string, and a format string with arguments.
    Replace pubnub_log_text() for non-formatted messages
    Use when you don't need printf-style formatting.
  4. Replace PUBNUB_LOG_PRINTF override with runtime custom logger registration:

    ActionDescription
    Remove #define PUBNUB_LOG_PRINTF(...) overrides
    Create a pubnub_logger_interface vtable and register a custom logger at runtime using pubnub_logger_alloc() and pubnub_logger_add().
  5. Replace pubnub_set_log_callback with custom logger:

    ActionDescription
    Remove pubnub_set_log_callback() calls
    Create a custom logger with a vtable and register it with pubnub_logger_add(). Use pubnub_logger_user_data() to access custom state from within callbacks.
  6. Replace WATCH_* macros with structured logging:

    ActionDescription
    Replace WATCH_INT(x), WATCH_STR(x), etc.
    Use pubnub_log_value_t types and pubnub_log_object(). Convenience macros like PUBNUB_LOG_MAP_SET_NUMBER and PUBNUB_LOG_MAP_SET_STRING are available in core/pubnub_log_value.h.
  7. Update compile-time level configuration:

    ActionDescription
    Replace -DPUBNUB_LOG_LEVEL=PUBNUB_LOG_LEVEL_WARNING with -DPUBNUB_LOG_MIN_LEVEL=WARNING
    The new macro uses short level names: TRACE, DEBUG, INFO, WARNING, ERROR, NONE.
  8. Update runtime level filtering:

    ActionDescription
    Use pubnub_logger_set_log_level(pb, level) to control runtime filtering
    The old system only supported compile-time filtering. The new system supports both compile-time stripping and runtime filtering per context.
  9. (C++ only) Use new context methods for logging:

    ActionDescription
    Use ctx.logger_add(), ctx.set_log_level(), ctx.log_text(), etc.
    The pubnub::context class in pubnub_common.hpp provides C++ wrappers for all logging API functions. No include changes needed — core/pubnub_logger.h is automatically included when PUBNUB_USE_LOGGER is enabled.
  10. Update build scripts. Add new source files if you maintain custom build scripts:

    ActionDescription
    Add core/pubnub_logger.c, core/pbcc_logger_manager.c, core/pubnub_log_value.c
    Always required when PUBNUB_USE_LOGGER=1 (default).
    Add exactly one platform-specific default logger file
    Required when PUBNUB_USE_DEFAULT_LOGGER=1 (default). See New source files for platform-specific file names.
  11. Clean up custom loggers before freeing the PubNub context:

    ActionDescription
    Call pubnub_logger_remove(pb, logger) and pubnub_logger_free(&logger) before pubnub_free(pb)
    Custom loggers must be unregistered and freed before the context is freed. pubnub_logger_free() calls the logger's destroy() callback if provided.
  12. Test your application. Pay special attention to DNS configuration, logging output, and any custom logging integrations.

Additional resources

For API details, see the C-Core SDK documentation. For the full logging reference, see Logging. For questions or issues, contact PubNub support.

Last updated on