mirror of
https://github.com/gabime/spdlog.git
synced 2024-12-26 18:41:35 +08:00
Merge pull request #2170 from sylveon/std-format
Support C++20 std::format as an alternative to fmtlib
This commit is contained in:
commit
ff80d10820
@ -80,6 +80,7 @@ option(SPDLOG_BUILD_WARNINGS "Enable compiler warnings" OFF)
|
||||
|
||||
# install options
|
||||
option(SPDLOG_INSTALL "Generate the install target" ${SPDLOG_MASTER_PROJECT})
|
||||
option(SPDLOG_USE_STD_FORMAT "Use std::format instead of fmt library. No compile-time format string checking." OFF)
|
||||
option(SPDLOG_FMT_EXTERNAL "Use external fmt library instead of bundled" OFF)
|
||||
option(SPDLOG_FMT_EXTERNAL_HO "Use external fmt header-only library instead of bundled" OFF)
|
||||
option(SPDLOG_NO_EXCEPTIONS "Compile with -fno-exceptions. Call abort() on any spdlog exceptions" OFF)
|
||||
@ -88,6 +89,14 @@ if(SPDLOG_FMT_EXTERNAL AND SPDLOG_FMT_EXTERNAL_HO)
|
||||
message(FATAL_ERROR "SPDLOG_FMT_EXTERNAL and SPDLOG_FMT_EXTERNAL_HO are mutually exclusive")
|
||||
endif()
|
||||
|
||||
if(SPDLOG_USE_STD_FORMAT AND SPDLOG_FMT_EXTERNAL_HO)
|
||||
message(FATAL_ERROR "SPDLOG_USE_STD_FORMAT and SPDLOG_FMT_EXTERNAL_HO are mutually exclusive")
|
||||
endif()
|
||||
|
||||
if(SPDLOG_USE_STD_FORMAT AND SPDLOG_FMT_EXTERNAL)
|
||||
message(FATAL_ERROR "SPDLOG_USE_STD_FORMAT and SPDLOG_FMT_EXTERNAL are mutually exclusive")
|
||||
endif()
|
||||
|
||||
# misc tweakme options
|
||||
if(WIN32)
|
||||
option(SPDLOG_WCHAR_SUPPORT "Support wchar api" OFF)
|
||||
@ -130,7 +139,7 @@ message(STATUS "Build type: " ${CMAKE_BUILD_TYPE})
|
||||
# ---------------------------------------------------------------------------------------
|
||||
set(SPDLOG_SRCS src/spdlog.cpp src/stdout_sinks.cpp src/color_sinks.cpp src/file_sinks.cpp src/async.cpp src/cfg.cpp)
|
||||
|
||||
if(NOT SPDLOG_FMT_EXTERNAL AND NOT SPDLOG_FMT_EXTERNAL_HO)
|
||||
if(NOT SPDLOG_USE_STD_FORMAT AND NOT SPDLOG_FMT_EXTERNAL AND NOT SPDLOG_FMT_EXTERNAL_HO)
|
||||
list(APPEND SPDLOG_SRCS src/fmt.cpp)
|
||||
endif()
|
||||
|
||||
@ -145,7 +154,7 @@ if(SPDLOG_BUILD_SHARED OR BUILD_SHARED_LIBS)
|
||||
target_compile_options(spdlog PUBLIC $<$<AND:$<CXX_COMPILER_ID:MSVC>,$<NOT:$<COMPILE_LANGUAGE:CUDA>>>:/wd4251
|
||||
/wd4275>)
|
||||
endif()
|
||||
if(NOT SPDLOG_FMT_EXTERNAL AND NOT SPDLOG_FMT_EXTERNAL_HO)
|
||||
if(NOT SPDLOG_USE_STD_FORMAT AND NOT SPDLOG_FMT_EXTERNAL AND NOT SPDLOG_FMT_EXTERNAL_HO)
|
||||
target_compile_definitions(spdlog PRIVATE FMT_EXPORT PUBLIC FMT_SHARED)
|
||||
endif()
|
||||
else()
|
||||
@ -222,7 +231,8 @@ foreach(
|
||||
SPDLOG_NO_THREAD_ID
|
||||
SPDLOG_NO_TLS
|
||||
SPDLOG_NO_ATOMIC_LEVELS
|
||||
SPDLOG_DISABLE_DEFAULT_LOGGER)
|
||||
SPDLOG_DISABLE_DEFAULT_LOGGER
|
||||
SPDLOG_USE_STD_FORMAT)
|
||||
if(${SPDLOG_OPTION})
|
||||
target_compile_definitions(spdlog PUBLIC ${SPDLOG_OPTION})
|
||||
target_compile_definitions(spdlog_header_only INTERFACE ${SPDLOG_OPTION})
|
||||
@ -280,7 +290,7 @@ if(SPDLOG_INSTALL)
|
||||
ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
|
||||
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR})
|
||||
|
||||
if(NOT SPDLOG_FMT_EXTERNAL AND NOT SPDLOG_FMT_EXTERNAL_HO)
|
||||
if(NOT SPDLOG_USE_STD_FORMAT AND NOT SPDLOG_FMT_EXTERNAL AND NOT SPDLOG_FMT_EXTERNAL_HO)
|
||||
install(DIRECTORY include/${PROJECT_NAME}/fmt/bundled/
|
||||
DESTINATION "${CMAKE_INSTALL_INCLUDEDIR}/${PROJECT_NAME}/fmt/bundled/")
|
||||
endif()
|
||||
|
29
appveyor.yml
29
appveyor.yml
@ -8,55 +8,82 @@ environment:
|
||||
WCHAR: 'OFF'
|
||||
WCHAR_FILES: 'OFF'
|
||||
BUILD_EXAMPLE: 'ON'
|
||||
USE_STD_FORMAT: 'OFF'
|
||||
CXX_STANDARD: 11
|
||||
- GENERATOR: '"Visual Studio 14 2015"'
|
||||
BUILD_TYPE: Release
|
||||
BUILD_SHARED: 'OFF'
|
||||
WCHAR: 'ON'
|
||||
WCHAR_FILES: 'OFF'
|
||||
BUILD_EXAMPLE: 'ON'
|
||||
USE_STD_FORMAT: 'OFF'
|
||||
CXX_STANDARD: 11
|
||||
- GENERATOR: '"Visual Studio 14 2015 Win64"'
|
||||
BUILD_TYPE: Debug
|
||||
BUILD_SHARED: 'OFF'
|
||||
WCHAR: 'ON'
|
||||
WCHAR_FILES: 'OFF'
|
||||
BUILD_EXAMPLE: 'ON'
|
||||
USE_STD_FORMAT: 'OFF'
|
||||
CXX_STANDARD: 11
|
||||
- GENERATOR: '"Visual Studio 14 2015 Win64"'
|
||||
BUILD_TYPE: Release
|
||||
BUILD_SHARED: 'OFF'
|
||||
WCHAR: 'ON'
|
||||
WCHAR_FILES: 'OFF'
|
||||
BUILD_EXAMPLE: 'ON'
|
||||
USE_STD_FORMAT: 'OFF'
|
||||
CXX_STANDARD: 11
|
||||
- GENERATOR: '"Visual Studio 15 2017 Win64"'
|
||||
BUILD_TYPE: Debug
|
||||
BUILD_SHARED: 'OFF'
|
||||
WCHAR: 'ON'
|
||||
WCHAR_FILES: 'OFF'
|
||||
BUILD_EXAMPLE: 'ON'
|
||||
USE_STD_FORMAT: 'OFF'
|
||||
CXX_STANDARD: 11
|
||||
- GENERATOR: '"Visual Studio 15 2017 Win64"'
|
||||
BUILD_TYPE: Release
|
||||
BUILD_SHARED: 'OFF'
|
||||
WCHAR: 'OFF'
|
||||
WCHAR_FILES: 'OFF'
|
||||
BUILD_EXAMPLE: 'ON'
|
||||
USE_STD_FORMAT: 'OFF'
|
||||
CXX_STANDARD: 11
|
||||
- GENERATOR: '"Visual Studio 15 2017 Win64"'
|
||||
BUILD_TYPE: Release
|
||||
BUILD_SHARED: 'ON'
|
||||
WCHAR: 'OFF'
|
||||
WCHAR_FILES: 'OFF'
|
||||
BUILD_EXAMPLE: 'ON'
|
||||
USE_STD_FORMAT: 'OFF'
|
||||
CXX_STANDARD: 11
|
||||
- GENERATOR: '"Visual Studio 15 2017 Win64"'
|
||||
BUILD_TYPE: Release
|
||||
BUILD_SHARED: 'ON'
|
||||
WCHAR: 'ON'
|
||||
WCHAR_FILES: 'ON'
|
||||
BUILD_EXAMPLE: 'OFF'
|
||||
USE_STD_FORMAT: 'OFF'
|
||||
CXX_STANDARD: 11
|
||||
- GENERATOR: '"Visual Studio 16 2019" -A x64'
|
||||
BUILD_TYPE: Release
|
||||
BUILD_SHARED: 'ON'
|
||||
WCHAR: 'OFF'
|
||||
WCHAR_FILES: 'OFF'
|
||||
BUILD_EXAMPLE: 'OFF'
|
||||
USE_STD_FORMAT: 'OFF'
|
||||
CXX_STANDARD: 17
|
||||
APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2019
|
||||
- GENERATOR: '"Visual Studio 17 2022" -A x64'
|
||||
BUILD_TYPE: Release
|
||||
BUILD_SHARED: 'ON'
|
||||
WCHAR: 'OFF'
|
||||
WCHAR_FILES: 'OFF'
|
||||
BUILD_EXAMPLE: 'OFF'
|
||||
USE_STD_FORMAT: 'ON'
|
||||
CXX_STANDARD: 23 # std::format is only available with /std:c++latest at the moment.
|
||||
APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2022
|
||||
build_script:
|
||||
- cmd: >-
|
||||
set
|
||||
@ -67,7 +94,7 @@ build_script:
|
||||
|
||||
set PATH=%PATH%;C:\Program Files\Git\usr\bin
|
||||
|
||||
cmake -G %GENERATOR% -D CMAKE_BUILD_TYPE=%BUILD_TYPE% -D BUILD_SHARED_LIBS=%BUILD_SHARED% -D SPDLOG_WCHAR_SUPPORT=%WCHAR% -D SPDLOG_WCHAR_FILENAMES=%WCHAR_FILES% -D SPDLOG_BUILD_EXAMPLE=%BUILD_EXAMPLE% -D SPDLOG_BUILD_EXAMPLE_HO=%BUILD_EXAMPLE% -D SPDLOG_BUILD_TESTS=ON -D SPDLOG_BUILD_TESTS_HO=OFF -D SPDLOG_BUILD_WARNINGS=ON ..
|
||||
cmake -G %GENERATOR% -D CMAKE_BUILD_TYPE=%BUILD_TYPE% -D BUILD_SHARED_LIBS=%BUILD_SHARED% -D SPDLOG_WCHAR_SUPPORT=%WCHAR% -D SPDLOG_WCHAR_FILENAMES=%WCHAR_FILES% -D SPDLOG_BUILD_EXAMPLE=%BUILD_EXAMPLE% -D SPDLOG_BUILD_EXAMPLE_HO=%BUILD_EXAMPLE% -D SPDLOG_BUILD_TESTS=ON -D SPDLOG_BUILD_TESTS_HO=OFF -D SPDLOG_BUILD_WARNINGS=ON -D SPDLOG_USE_STD_FORMAT=%USE_STD_FORMAT% -D CMAKE_CXX_STANDARD=%CXX_STANDARD% ..
|
||||
|
||||
cmake --build . --config %BUILD_TYPE%
|
||||
|
||||
|
@ -10,7 +10,9 @@
|
||||
#include "spdlog/async.h"
|
||||
#include "spdlog/sinks/basic_file_sink.h"
|
||||
|
||||
#ifdef SPDLOG_FMT_EXTERNAL
|
||||
#if defined(SPDLOG_USE_STD_FORMAT)
|
||||
# include <format>
|
||||
#elif defined(SPDLOG_FMT_EXTERNAL)
|
||||
# include <fmt/format.h>
|
||||
#else
|
||||
# include "spdlog/fmt/bundled/format.h"
|
||||
|
@ -12,7 +12,9 @@
|
||||
#include "spdlog/sinks/null_sink.h"
|
||||
#include "spdlog/sinks/rotating_file_sink.h"
|
||||
|
||||
#ifdef SPDLOG_FMT_EXTERNAL
|
||||
#if defined(SPDLOG_USE_STD_FORMAT)
|
||||
# include <format>
|
||||
#elif defined(SPDLOG_FMT_EXTERNAL)
|
||||
# include <fmt/locale.h>
|
||||
#else
|
||||
# include "spdlog/fmt/bundled/format.h"
|
||||
@ -38,7 +40,7 @@ static const int max_threads = 1000;
|
||||
void bench_threaded_logging(size_t threads, int iters)
|
||||
{
|
||||
spdlog::info("**************************************************************");
|
||||
spdlog::info(fmt::format(std::locale("en_US.UTF-8"), "Multi threaded: {:L} threads, {:L} messages", threads, iters));
|
||||
spdlog::info(spdlog::fmt_lib::format(std::locale("en_US.UTF-8"), "Multi threaded: {:L} threads, {:L} messages", threads, iters));
|
||||
spdlog::info("**************************************************************");
|
||||
|
||||
auto basic_mt = spdlog::basic_logger_mt("basic_mt", "logs/basic_mt.log", true);
|
||||
@ -74,7 +76,7 @@ void bench_threaded_logging(size_t threads, int iters)
|
||||
void bench_single_threaded(int iters)
|
||||
{
|
||||
spdlog::info("**************************************************************");
|
||||
spdlog::info(fmt::format(std::locale("en_US.UTF-8"), "Single threaded: {} messages", iters));
|
||||
spdlog::info(spdlog::fmt_lib::format(std::locale("en_US.UTF-8"), "Single threaded: {} messages", iters));
|
||||
spdlog::info("**************************************************************");
|
||||
|
||||
auto basic_st = spdlog::basic_logger_st("basic_st", "logs/basic_st.log", true);
|
||||
@ -128,7 +130,7 @@ int main(int argc, char *argv[])
|
||||
|
||||
if (threads > max_threads)
|
||||
{
|
||||
throw std::runtime_error(fmt::format("Number of threads exceeds maximum({})", max_threads));
|
||||
throw std::runtime_error(spdlog::fmt_lib::format("Number of threads exceeds maximum({})", max_threads));
|
||||
}
|
||||
|
||||
bench_single_threaded(iters);
|
||||
@ -159,7 +161,7 @@ void bench(int howmany, std::shared_ptr<spdlog::logger> log)
|
||||
auto delta_d = duration_cast<duration<double>>(delta).count();
|
||||
|
||||
spdlog::info(
|
||||
fmt::format(std::locale("en_US.UTF-8"), "{:<30} Elapsed: {:0.2f} secs {:>16L}/sec", log->name(), delta_d, int(howmany / delta_d)));
|
||||
spdlog::fmt_lib::format(std::locale("en_US.UTF-8"), "{:<30} Elapsed: {:0.2f} secs {:>16L}/sec", log->name(), delta_d, int(howmany / delta_d)));
|
||||
spdlog::drop(log->name());
|
||||
}
|
||||
|
||||
@ -190,7 +192,7 @@ void bench_mt(int howmany, std::shared_ptr<spdlog::logger> log, size_t thread_co
|
||||
auto delta = high_resolution_clock::now() - start;
|
||||
auto delta_d = duration_cast<duration<double>>(delta).count();
|
||||
spdlog::info(
|
||||
fmt::format(std::locale("en_US.UTF-8"), "{:<30} Elapsed: {:0.2f} secs {:>16L}/sec", log->name(), delta_d, int(howmany / delta_d)));
|
||||
spdlog::fmt_lib::format(std::locale("en_US.UTF-8"), "{:<30} Elapsed: {:0.2f} secs {:>16L}/sec", log->name(), delta_d, int(howmany / delta_d)));
|
||||
spdlog::drop(log->name());
|
||||
}
|
||||
|
||||
|
@ -55,9 +55,13 @@ SPDLOG_INLINE spdlog_ex::spdlog_ex(std::string msg)
|
||||
|
||||
SPDLOG_INLINE spdlog_ex::spdlog_ex(const std::string &msg, int last_errno)
|
||||
{
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
msg_ = std::system_error(std::error_code(last_errno, std::generic_category()), msg).what();
|
||||
#else
|
||||
memory_buf_t outbuf;
|
||||
fmt::format_system_error(outbuf, last_errno, msg.c_str());
|
||||
msg_ = fmt::to_string(outbuf);
|
||||
#endif
|
||||
}
|
||||
|
||||
SPDLOG_INLINE const char *spdlog_ex::what() const SPDLOG_NOEXCEPT
|
||||
|
@ -16,6 +16,10 @@
|
||||
#include <functional>
|
||||
#include <cstdio>
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
#include <string_view>
|
||||
#endif
|
||||
|
||||
#ifdef SPDLOG_COMPILED_LIB
|
||||
# undef SPDLOG_HEADER_ONLY
|
||||
# if defined(_WIN32) && defined(SPDLOG_SHARED_LIB)
|
||||
@ -36,8 +40,8 @@
|
||||
|
||||
#include <spdlog/fmt/fmt.h>
|
||||
|
||||
// backward compatibility with fmt versions older than 8
|
||||
#if FMT_VERSION >= 80000
|
||||
#ifndef SPDLOG_USE_STD_FORMAT
|
||||
# if FMT_VERSION >= 80000 // backward compatibility with fmt versions older than 8
|
||||
# define SPDLOG_FMT_RUNTIME(format_string) fmt::runtime(format_string)
|
||||
# if defined(SPDLOG_WCHAR_FILENAMES) || defined(SPDLOG_WCHAR_TO_UTF8_SUPPORT)
|
||||
# include <spdlog/fmt/xchar.h>
|
||||
@ -45,14 +49,21 @@
|
||||
# else
|
||||
# define SPDLOG_FMT_RUNTIME(format_string) format_string
|
||||
# endif
|
||||
#endif
|
||||
|
||||
// visual studio up to 2013 does not support noexcept nor constexpr
|
||||
#if defined(_MSC_VER) && (_MSC_VER < 1900)
|
||||
# define SPDLOG_NOEXCEPT _NOEXCEPT
|
||||
# define SPDLOG_CONSTEXPR
|
||||
# define SPDLOG_CONSTEXPR_FUNC
|
||||
#else
|
||||
# define SPDLOG_NOEXCEPT noexcept
|
||||
# define SPDLOG_CONSTEXPR constexpr
|
||||
# if __cplusplus >= 201402L
|
||||
# define SPDLOG_CONSTEXPR_FUNC constexpr
|
||||
# else
|
||||
# define SPDLOG_CONSTEXPR_FUNC
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#if defined(__GNUC__) || defined(__clang__)
|
||||
@ -112,10 +123,36 @@ using log_clock = std::chrono::system_clock;
|
||||
using sink_ptr = std::shared_ptr<sinks::sink>;
|
||||
using sinks_init_list = std::initializer_list<sink_ptr>;
|
||||
using err_handler = std::function<void(const std::string &err_msg)>;
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
namespace fmt_lib = std;
|
||||
|
||||
using string_view_t = std::string_view;
|
||||
using memory_buf_t = std::string;
|
||||
|
||||
template<typename... Args>
|
||||
using format_string_t = std::string_view;
|
||||
|
||||
template<class T, class Char = char>
|
||||
struct is_convertible_to_basic_format_string
|
||||
: std::integral_constant<bool,
|
||||
std::is_convertible<T, std::basic_string_view<Char>>::value>
|
||||
{};
|
||||
|
||||
# if defined(SPDLOG_WCHAR_FILENAMES) || defined(SPDLOG_WCHAR_TO_UTF8_SUPPORT)
|
||||
using wstring_view_t = std::wstring_view;
|
||||
using memory_buf_t = std::wstring;
|
||||
|
||||
template<typename... Args>
|
||||
using wformat_string_t = std::wstring_view;
|
||||
# endif
|
||||
#else
|
||||
namespace fmt_lib = fmt;
|
||||
|
||||
using string_view_t = fmt::basic_string_view<char>;
|
||||
using wstring_view_t = fmt::basic_string_view<wchar_t>;
|
||||
using memory_buf_t = fmt::basic_memory_buffer<char, 250>;
|
||||
using wmemory_buf_t = fmt::basic_memory_buffer<wchar_t, 250>;
|
||||
|
||||
template<typename... Args>
|
||||
using format_string_t = fmt::format_string<Args...>;
|
||||
|
||||
template<class T>
|
||||
using remove_cvref_t = typename std::remove_cv<typename std::remove_reference<T>::type>::type;
|
||||
@ -128,6 +165,15 @@ struct is_convertible_to_basic_format_string
|
||||
std::is_convertible<T, fmt::basic_string_view<Char>>::value || std::is_same<remove_cvref_t<T>, fmt::basic_runtime<Char>>::value>
|
||||
{};
|
||||
|
||||
# if defined(SPDLOG_WCHAR_FILENAMES) || defined(SPDLOG_WCHAR_TO_UTF8_SUPPORT)
|
||||
using wstring_view_t = fmt::basic_string_view<wchar_t>;
|
||||
using wmemory_buf_t = fmt::basic_memory_buffer<wchar_t, 250>;;
|
||||
|
||||
template<typename... Args>
|
||||
using wformat_string_t = fmt::wformat_string<Args...>;
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#ifdef SPDLOG_WCHAR_TO_UTF8_SUPPORT
|
||||
# ifndef _WIN32
|
||||
# error SPDLOG_WCHAR_TO_UTF8_SUPPORT only supported on windows
|
||||
|
@ -8,6 +8,11 @@
|
||||
#include <spdlog/fmt/fmt.h>
|
||||
#include <spdlog/common.h>
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
#include <charconv>
|
||||
#include <limits>
|
||||
#endif
|
||||
|
||||
// Some fmt helpers to efficiently format and pad ints and strings
|
||||
namespace spdlog {
|
||||
namespace details {
|
||||
@ -24,17 +29,63 @@ inline void append_string_view(spdlog::string_view_t view, memory_buf_t &dest)
|
||||
dest.append(buf_ptr, buf_ptr + view.size());
|
||||
}
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
template<typename T>
|
||||
inline void append_int(T n, memory_buf_t &dest)
|
||||
{
|
||||
// Buffer should be large enough to hold all digits (digits10 + 1) and a sign
|
||||
SPDLOG_CONSTEXPR const auto BUF_SIZE = std::numeric_limits<T>::digits10 + 2;
|
||||
char buf[BUF_SIZE];
|
||||
|
||||
auto [ptr, ec] = std::to_chars(buf, buf + BUF_SIZE, n, 10);
|
||||
if (ec == std::errc())
|
||||
{
|
||||
dest.append(buf, ptr);
|
||||
}
|
||||
else
|
||||
{
|
||||
throw_spdlog_ex("Failed to format int", static_cast<int>(ec));
|
||||
}
|
||||
}
|
||||
#else
|
||||
template<typename T>
|
||||
inline void append_int(T n, memory_buf_t &dest)
|
||||
{
|
||||
fmt::format_int i(n);
|
||||
dest.append(i.data(), i.data() + i.size());
|
||||
}
|
||||
#endif
|
||||
|
||||
template<typename T>
|
||||
SPDLOG_CONSTEXPR_FUNC unsigned int count_digits_fallback(T n)
|
||||
{
|
||||
// taken from fmt: https://github.com/fmtlib/fmt/blob/8.0.1/include/fmt/format.h#L899-L912
|
||||
unsigned int count = 1;
|
||||
for (;;)
|
||||
{
|
||||
// Integer division is slow so do it for a group of four digits instead
|
||||
// of for every digit. The idea comes from the talk by Alexandrescu
|
||||
// "Three Optimization Tips for C++". See speed-test for a comparison.
|
||||
if (n < 10)
|
||||
return count;
|
||||
if (n < 100)
|
||||
return count + 1;
|
||||
if (n < 1000)
|
||||
return count + 2;
|
||||
if (n < 10000)
|
||||
return count + 3;
|
||||
n /= 10000u;
|
||||
count += 4;
|
||||
}
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
inline unsigned int count_digits(T n)
|
||||
{
|
||||
using count_type = typename std::conditional<(sizeof(T) > sizeof(uint32_t)), uint64_t, uint32_t>::type;
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
return count_digits_fallback(static_cast<count_type>(n));
|
||||
#else
|
||||
return static_cast<unsigned int>(fmt::
|
||||
// fmt 7.0.0 renamed the internal namespace to detail.
|
||||
// See: https://github.com/fmtlib/fmt/issues/1538
|
||||
@ -44,6 +95,7 @@ inline unsigned int count_digits(T n)
|
||||
detail
|
||||
#endif
|
||||
::count_digits(static_cast<count_type>(n)));
|
||||
#endif
|
||||
}
|
||||
|
||||
inline void pad2(int n, memory_buf_t &dest)
|
||||
@ -55,7 +107,7 @@ inline void pad2(int n, memory_buf_t &dest)
|
||||
}
|
||||
else // unlikely, but just in case, let fmt deal with it
|
||||
{
|
||||
fmt::format_to(std::back_inserter(dest), SPDLOG_FMT_RUNTIME("{:02}"), n);
|
||||
fmt_lib::format_to(std::back_inserter(dest), "{:02}", n);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -381,7 +381,11 @@ SPDLOG_INLINE std::string filename_to_str(const filename_t &filename)
|
||||
{
|
||||
memory_buf_t buf;
|
||||
wstr_to_utf8buf(filename, buf);
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
return buf;
|
||||
#else
|
||||
return fmt::to_string(buf);
|
||||
#endif
|
||||
}
|
||||
#else
|
||||
SPDLOG_INLINE std::string filename_to_str(const filename_t &filename)
|
||||
@ -476,7 +480,7 @@ SPDLOG_INLINE void wstr_to_utf8buf(wstring_view_t wstr, memory_buf_t &target)
|
||||
}
|
||||
}
|
||||
|
||||
throw_spdlog_ex(fmt::format("WideCharToMultiByte failed. Last error: {}", ::GetLastError()));
|
||||
throw_spdlog_ex(fmt_lib::format("WideCharToMultiByte failed. Last error: {}", ::GetLastError()));
|
||||
}
|
||||
|
||||
SPDLOG_INLINE void utf8_to_wstrbuf(string_view_t str, wmemory_buf_t &target)
|
||||
@ -511,7 +515,7 @@ SPDLOG_INLINE void utf8_to_wstrbuf(string_view_t str, wmemory_buf_t &target)
|
||||
}
|
||||
}
|
||||
|
||||
throw_spdlog_ex(fmt::format("MultiByteToWideChar failed. Last error: {}", ::GetLastError()));
|
||||
throw_spdlog_ex(fmt_lib::format("MultiByteToWideChar failed. Last error: {}", ::GetLastError()));
|
||||
}
|
||||
#endif // (defined(SPDLOG_WCHAR_TO_UTF8_SUPPORT) || defined(SPDLOG_WCHAR_FILENAMES)) && defined(_WIN32)
|
||||
|
||||
|
@ -38,10 +38,10 @@ class tcp_client
|
||||
static void throw_winsock_error_(const std::string &msg, int last_error)
|
||||
{
|
||||
char buf[512];
|
||||
::FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS, NULL, last_error,
|
||||
::FormatMessageA(FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS, NULL, last_error,
|
||||
MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), buf, (sizeof(buf) / sizeof(char)), NULL);
|
||||
|
||||
throw_spdlog_ex(fmt::format("tcp_sink - {}: {}", msg, buf));
|
||||
throw_spdlog_ex(fmt_lib::format("tcp_sink - {}: {}", msg, buf));
|
||||
}
|
||||
|
||||
public:
|
||||
|
@ -67,8 +67,7 @@ public:
|
||||
auto rv = ::getaddrinfo(host.c_str(), port_str.c_str(), &hints, &addrinfo_result);
|
||||
if (rv != 0)
|
||||
{
|
||||
auto msg = fmt::format("::getaddrinfo failed: {}", gai_strerror(rv));
|
||||
throw_spdlog_ex(msg);
|
||||
throw_spdlog_ex(fmt_lib::format("::getaddrinfo failed: {}", gai_strerror(rv)));
|
||||
}
|
||||
|
||||
// Try each address until we successfully connect(2).
|
||||
|
@ -40,10 +40,10 @@ class udp_client
|
||||
static void throw_winsock_error_(const std::string &msg, int last_error)
|
||||
{
|
||||
char buf[512];
|
||||
::FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS, NULL, last_error,
|
||||
::FormatMessageA(FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS, NULL, last_error,
|
||||
MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), buf, (sizeof(buf) / sizeof(char)), NULL);
|
||||
|
||||
throw_spdlog_ex(fmt::format("udp_sink - {}: {}", msg, buf));
|
||||
throw_spdlog_ex(fmt_lib::format("udp_sink - {}: {}", msg, buf));
|
||||
}
|
||||
|
||||
void cleanup_()
|
||||
|
@ -76,10 +76,16 @@ inline details::dump_info<It> to_hex(const It range_begin, const It range_end, s
|
||||
|
||||
} // namespace spdlog
|
||||
|
||||
namespace fmt {
|
||||
namespace
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
std
|
||||
#else
|
||||
fmt
|
||||
#endif
|
||||
{
|
||||
|
||||
template<typename T>
|
||||
struct formatter<spdlog::details::dump_info<T>>
|
||||
struct formatter<spdlog::details::dump_info<T>, char>
|
||||
{
|
||||
const char delimiter = ' ';
|
||||
bool put_newlines = true;
|
||||
@ -90,7 +96,7 @@ struct formatter<spdlog::details::dump_info<T>>
|
||||
|
||||
// parse the format string flags
|
||||
template<typename ParseContext>
|
||||
FMT_CONSTEXPR auto parse(ParseContext &ctx) -> decltype(ctx.begin())
|
||||
SPDLOG_CONSTEXPR_FUNC auto parse(ParseContext &ctx) -> decltype(ctx.begin())
|
||||
{
|
||||
auto it = ctx.begin();
|
||||
while (it != ctx.end() && *it != '}')
|
||||
@ -131,7 +137,7 @@ struct formatter<spdlog::details::dump_info<T>>
|
||||
SPDLOG_CONSTEXPR const char *hex_lower = "0123456789abcdef";
|
||||
const char *hex_chars = use_uppercase ? hex_upper : hex_lower;
|
||||
|
||||
#if FMT_VERSION < 60000
|
||||
#if !defined(SPDLOG_USE_STD_FORMAT) && FMT_VERSION < 60000
|
||||
auto inserter = ctx.begin();
|
||||
#else
|
||||
auto inserter = ctx.out();
|
||||
@ -210,8 +216,8 @@ struct formatter<spdlog::details::dump_info<T>>
|
||||
|
||||
if (put_positions)
|
||||
{
|
||||
fmt::format_to(inserter, "{:04X}: ", pos);
|
||||
spdlog::fmt_lib::format_to(inserter, "{:04X}: ", pos);
|
||||
}
|
||||
}
|
||||
};
|
||||
} // namespace fmt
|
||||
} // namespace fmt/std
|
||||
|
@ -8,6 +8,7 @@
|
||||
// include bundled or external copy of fmtlib's chrono support
|
||||
//
|
||||
|
||||
#if !defined(SPDLOG_USE_STD_FORMAT)
|
||||
# if !defined(SPDLOG_FMT_EXTERNAL)
|
||||
# ifdef SPDLOG_HEADER_ONLY
|
||||
# ifndef FMT_HEADER_ONLY
|
||||
@ -18,3 +19,4 @@
|
||||
# else
|
||||
# include <fmt/chrono.h>
|
||||
# endif
|
||||
#endif
|
||||
|
@ -5,9 +5,10 @@
|
||||
|
||||
#pragma once
|
||||
//
|
||||
// include bundled or external copy of fmtlib's ostream support
|
||||
// include bundled or external copy of fmtlib's compile-time support
|
||||
//
|
||||
|
||||
#if !defined(SPDLOG_USE_STD_FORMAT)
|
||||
# if !defined(SPDLOG_FMT_EXTERNAL)
|
||||
# ifdef SPDLOG_HEADER_ONLY
|
||||
# ifndef FMT_HEADER_ONLY
|
||||
@ -18,3 +19,4 @@
|
||||
# else
|
||||
# include <fmt/compile.h>
|
||||
# endif
|
||||
#endif
|
||||
|
@ -10,7 +10,9 @@
|
||||
// By default spdlog include its own copy.
|
||||
//
|
||||
|
||||
#if !defined(SPDLOG_FMT_EXTERNAL)
|
||||
#if defined(SPDLOG_USE_STD_FORMAT) // SPDLOG_USE_STD_FORMAT is defined - use std::format
|
||||
# include <format>
|
||||
#elif !defined(SPDLOG_FMT_EXTERNAL)
|
||||
# if !defined(SPDLOG_COMPILED_LIB) && !defined(FMT_HEADER_ONLY)
|
||||
# define FMT_HEADER_ONLY
|
||||
# endif
|
||||
|
@ -8,6 +8,7 @@
|
||||
// include bundled or external copy of fmtlib's ostream support
|
||||
//
|
||||
|
||||
#if !defined(SPDLOG_USE_STD_FORMAT)
|
||||
# if !defined(SPDLOG_FMT_EXTERNAL)
|
||||
# ifdef SPDLOG_HEADER_ONLY
|
||||
# ifndef FMT_HEADER_ONLY
|
||||
@ -18,3 +19,4 @@
|
||||
# else
|
||||
# include <fmt/ostream.h>
|
||||
# endif
|
||||
#endif
|
||||
|
@ -5,9 +5,10 @@
|
||||
|
||||
#pragma once
|
||||
//
|
||||
// include bundled or external copy of fmtlib's ostream support
|
||||
// include bundled or external copy of fmtlib's xchar support
|
||||
//
|
||||
|
||||
#if !defined(SPDLOG_USE_STD_FORMAT)
|
||||
# if !defined(SPDLOG_FMT_EXTERNAL)
|
||||
# ifdef SPDLOG_HEADER_ONLY
|
||||
# ifndef FMT_HEADER_ONLY
|
||||
@ -18,3 +19,4 @@
|
||||
# else
|
||||
# include <fmt/xchar.h>
|
||||
# endif
|
||||
#endif
|
||||
|
@ -33,7 +33,7 @@
|
||||
{ \
|
||||
if(location.filename) \
|
||||
{ \
|
||||
err_handler_(fmt::format("{} [{}({})]", ex.what(), location.filename, location.line)); \
|
||||
err_handler_(fmt_lib::format("{} [{}({})]", ex.what(), location.filename, location.line)); \
|
||||
} \
|
||||
else \
|
||||
{ \
|
||||
@ -85,13 +85,13 @@ public:
|
||||
void swap(spdlog::logger &other) SPDLOG_NOEXCEPT;
|
||||
|
||||
template<typename... Args>
|
||||
void log(source_loc loc, level::level_enum lvl, fmt::format_string<Args...> fmt, Args &&...args)
|
||||
void log(source_loc loc, level::level_enum lvl, format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log_(loc, lvl, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void log(level::level_enum lvl, fmt::format_string<Args...> fmt, Args &&...args)
|
||||
void log(level::level_enum lvl, format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(source_loc{}, lvl, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
@ -102,14 +102,7 @@ public:
|
||||
log(source_loc{}, lvl, msg);
|
||||
}
|
||||
|
||||
// T can be statically converted to string_view
|
||||
template<class T, typename std::enable_if<std::is_convertible<const T &, spdlog::string_view_t>::value, int>::type = 0>
|
||||
void log(source_loc loc, level::level_enum lvl, const T &msg)
|
||||
{
|
||||
log(loc, lvl, string_view_t{msg});
|
||||
}
|
||||
|
||||
// T cannot be statically converted to format string (including string_view)
|
||||
// T cannot be statically converted to format string (including string_view/wstring_view)
|
||||
template<class T, typename std::enable_if<!is_convertible_to_any_format_string<const T &>::value, int>::type = 0>
|
||||
void log(source_loc loc, level::level_enum lvl, const T &msg)
|
||||
{
|
||||
@ -148,86 +141,121 @@ public:
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void trace(fmt::format_string<Args...> fmt, Args &&...args)
|
||||
void trace(format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(level::trace, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void debug(fmt::format_string<Args...> fmt, Args &&...args)
|
||||
void debug(format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(level::debug, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void info(fmt::format_string<Args...> fmt, Args &&...args)
|
||||
void info(format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(level::info, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void warn(fmt::format_string<Args...> fmt, Args &&...args)
|
||||
void warn(format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(level::warn, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void error(fmt::format_string<Args...> fmt, Args &&...args)
|
||||
void error(format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(level::err, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void critical(fmt::format_string<Args...> fmt, Args &&...args)
|
||||
void critical(format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(level::critical, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
#ifdef SPDLOG_WCHAR_TO_UTF8_SUPPORT
|
||||
template<typename... Args>
|
||||
void log(level::level_enum lvl, fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(source_loc{}, lvl, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void log(source_loc loc, level::level_enum lvl, fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
void log(source_loc loc, level::level_enum lvl, wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log_(loc, lvl, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void trace(fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
void log(level::level_enum lvl, wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(source_loc{}, lvl, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
void log(log_clock::time_point log_time, source_loc loc, level::level_enum lvl, wstring_view_t msg)
|
||||
{
|
||||
bool log_enabled = should_log(lvl);
|
||||
bool traceback_enabled = tracer_.enabled();
|
||||
if (!log_enabled && !traceback_enabled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
memory_buf_t buf;
|
||||
details::os::wstr_to_utf8buf(wstring_view_t(msg.data(), msg.size()), buf);
|
||||
details::log_msg log_msg(log_time, loc, name_, lvl, string_view_t(buf.data(), buf.size()));
|
||||
log_it_(log_msg, log_enabled, traceback_enabled);
|
||||
}
|
||||
|
||||
void log(source_loc loc, level::level_enum lvl, wstring_view_t msg)
|
||||
{
|
||||
bool log_enabled = should_log(lvl);
|
||||
bool traceback_enabled = tracer_.enabled();
|
||||
if (!log_enabled && !traceback_enabled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
memory_buf_t buf;
|
||||
details::os::wstr_to_utf8buf(wstring_view_t(msg.data(), msg.size()), buf);
|
||||
details::log_msg log_msg(loc, name_, lvl, string_view_t(buf.data(), buf.size()));
|
||||
log_it_(log_msg, log_enabled, traceback_enabled);
|
||||
}
|
||||
|
||||
void log(level::level_enum lvl, wstring_view_t msg)
|
||||
{
|
||||
log(source_loc{}, lvl, msg);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void trace(wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(level::trace, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void debug(fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
void debug(wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(level::debug, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void info(fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
void info(wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(level::info, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void warn(fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
void warn(wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(level::warn, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void error(fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
void error(wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(level::err, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
void critical(fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
void critical(wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
log(level::critical, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
@ -335,8 +363,12 @@ protected:
|
||||
}
|
||||
SPDLOG_TRY
|
||||
{
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
memory_buf_t buf = std::vformat(fmt, std::make_format_args(std::forward<Args>(args)...));
|
||||
#else
|
||||
memory_buf_t buf;
|
||||
fmt::detail::vformat_to(buf, fmt, fmt::make_format_args(args...));
|
||||
fmt::detail::vformat_to(buf, fmt, fmt::make_format_args(std::forward<Args>(args)...));
|
||||
#endif
|
||||
details::log_msg log_msg(loc, name_, lvl, string_view_t(buf.data(), buf.size()));
|
||||
log_it_(log_msg, log_enabled, traceback_enabled);
|
||||
}
|
||||
@ -356,8 +388,13 @@ protected:
|
||||
SPDLOG_TRY
|
||||
{
|
||||
// format to wmemory_buffer and convert to utf8
|
||||
fmt::wmemory_buffer wbuf;
|
||||
fmt::detail::vformat_to(wbuf, fmt, fmt::make_format_args<fmt::wformat_context>(args...));
|
||||
;
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
wmemory_buf_t wbuf = std::vformat(fmt, std::make_wformat_args(std::forward<Args>(args)...));
|
||||
#else
|
||||
wmemory_buf_t wbuf;
|
||||
fmt::detail::vformat_to(wbuf, fmt, fmt::make_format_args<fmt::wformat_context>(std::forward<Args>(args)...));
|
||||
#endif
|
||||
memory_buf_t buf;
|
||||
details::os::wstr_to_utf8buf(wstring_view_t(wbuf.data(), wbuf.size()), buf);
|
||||
details::log_msg log_msg(loc, name_, lvl, string_view_t(buf.data(), buf.size()));
|
||||
|
@ -32,7 +32,7 @@ struct daily_filename_calculator
|
||||
{
|
||||
filename_t basename, ext;
|
||||
std::tie(basename, ext) = details::file_helper::split_by_extension(filename);
|
||||
return fmt::format(
|
||||
return fmt_lib::format(
|
||||
SPDLOG_FILENAME_T("{}_{:04d}-{:02d}-{:02d}{}"), basename, now_tm.tm_year + 1900, now_tm.tm_mon + 1, now_tm.tm_mday, ext);
|
||||
}
|
||||
};
|
||||
@ -48,14 +48,62 @@ struct daily_filename_format_calculator
|
||||
{
|
||||
static filename_t calc_filename(const filename_t &filename, const tm &now_tm)
|
||||
{
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
// adapted from fmtlib: https://github.com/fmtlib/fmt/blob/8.0.1/include/fmt/chrono.h#L522-L546
|
||||
|
||||
filename_t tm_format;
|
||||
tm_format.append(filename);
|
||||
// By appending an extra space we can distinguish an empty result that
|
||||
// indicates insufficient buffer size from a guaranteed non-empty result
|
||||
// https://github.com/fmtlib/fmt/issues/2238
|
||||
tm_format.push_back(' ');
|
||||
|
||||
const size_t MIN_SIZE = 10;
|
||||
filename_t buf;
|
||||
buf.resize(MIN_SIZE);
|
||||
for (;;)
|
||||
{
|
||||
size_t count = strftime(buf.data(), buf.size(), tm_format.c_str(), &now_tm);
|
||||
if (count != 0)
|
||||
{
|
||||
// Remove the extra space.
|
||||
buf.resize(count - 1);
|
||||
break;
|
||||
}
|
||||
buf.resize(buf.size() * 2);
|
||||
}
|
||||
|
||||
return buf;
|
||||
#else
|
||||
// generate fmt datetime format string, e.g. {:%Y-%m-%d}.
|
||||
filename_t fmt_filename = fmt::format(SPDLOG_FILENAME_T("{{:{}}}"), filename);
|
||||
# if defined(_MSC_VER) && defined(SPDLOG_WCHAR_FILENAMES) // for some reason msvc doesn't allow fmt::runtime(..) with wchar here
|
||||
return fmt::format(fmt_filename, now_tm);
|
||||
# else
|
||||
return fmt::format(SPDLOG_FMT_RUNTIME(fmt_filename), now_tm);
|
||||
# endif
|
||||
#endif
|
||||
}
|
||||
|
||||
private:
|
||||
#if defined __GNUC__
|
||||
# pragma GCC diagnostic push
|
||||
# pragma GCC diagnostic ignored "-Wformat-nonliteral"
|
||||
#endif
|
||||
|
||||
static size_t strftime(char *str, size_t count, const char *format, const std::tm *time)
|
||||
{
|
||||
return std::strftime(str, count, format, time);
|
||||
}
|
||||
|
||||
static size_t strftime(wchar_t *str, size_t count, const wchar_t *format, const std::tm *time)
|
||||
{
|
||||
return std::wcsftime(str, count, format, time);
|
||||
}
|
||||
|
||||
#if defined(__GNUC__)
|
||||
# pragma GCC diagnostic pop
|
||||
#endif
|
||||
};
|
||||
|
||||
/*
|
||||
|
@ -31,7 +31,7 @@ struct hourly_filename_calculator
|
||||
{
|
||||
filename_t basename, ext;
|
||||
std::tie(basename, ext) = details::file_helper::split_by_extension(filename);
|
||||
return fmt::format(SPDLOG_FILENAME_T("{}_{:04d}-{:02d}-{:02d}_{:02d}{}"), basename, now_tm.tm_year + 1900, now_tm.tm_mon + 1,
|
||||
return fmt_lib::format(SPDLOG_FILENAME_T("{}_{:04d}-{:02d}-{:02d}_{:02d}{}"), basename, now_tm.tm_year + 1900, now_tm.tm_mon + 1,
|
||||
now_tm.tm_mday, now_tm.tm_hour, ext);
|
||||
}
|
||||
};
|
||||
|
@ -30,7 +30,11 @@ protected:
|
||||
{
|
||||
memory_buf_t formatted;
|
||||
base_sink<Mutex>::formatter_->format(msg, formatted);
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
OutputDebugStringA(formatted.c_str());
|
||||
#else
|
||||
OutputDebugStringA(fmt::to_string(formatted).c_str());
|
||||
#endif
|
||||
}
|
||||
|
||||
void flush_() override {}
|
||||
|
@ -50,7 +50,11 @@ public:
|
||||
{
|
||||
memory_buf_t formatted;
|
||||
base_sink<Mutex>::formatter_->format(q_.at(i), formatted);
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
ret.push_back(std::move(formatted));
|
||||
#else
|
||||
ret.push_back(fmt::to_string(formatted));
|
||||
#endif
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
@ -51,7 +51,7 @@ SPDLOG_INLINE filename_t rotating_file_sink<Mutex>::calc_filename(const filename
|
||||
|
||||
filename_t basename, ext;
|
||||
std::tie(basename, ext) = details::file_helper::split_by_extension(filename);
|
||||
return fmt::format(SPDLOG_FILENAME_T("{}.{}{}"), basename, index, ext);
|
||||
return fmt_lib::format(SPDLOG_FILENAME_T("{}.{}{}"), basename, index, ext);
|
||||
}
|
||||
|
||||
template<typename Mutex>
|
||||
|
@ -47,6 +47,24 @@ namespace win_eventlog {
|
||||
|
||||
namespace internal {
|
||||
|
||||
struct local_alloc_t
|
||||
{
|
||||
HLOCAL hlocal_;
|
||||
|
||||
SPDLOG_CONSTEXPR local_alloc_t() SPDLOG_NOEXCEPT : hlocal_(nullptr) {}
|
||||
|
||||
local_alloc_t(local_alloc_t const&) = delete;
|
||||
local_alloc_t& operator=(local_alloc_t const&) = delete;
|
||||
|
||||
~local_alloc_t() SPDLOG_NOEXCEPT
|
||||
{
|
||||
if (hlocal_)
|
||||
{
|
||||
LocalFree(hlocal_);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/** Windows error */
|
||||
struct win32_error : public spdlog_ex
|
||||
{
|
||||
@ -55,22 +73,17 @@ struct win32_error : public spdlog_ex
|
||||
{
|
||||
std::string system_message;
|
||||
|
||||
LPSTR format_message_result{};
|
||||
local_alloc_t format_message_result{};
|
||||
auto format_message_succeeded =
|
||||
::FormatMessageA(FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS, nullptr,
|
||||
error_code, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPSTR)&format_message_result, 0, nullptr);
|
||||
error_code, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPSTR)&format_message_result.hlocal_, 0, nullptr);
|
||||
|
||||
if (format_message_succeeded && format_message_result)
|
||||
if (format_message_succeeded && format_message_result.hlocal_)
|
||||
{
|
||||
system_message = fmt::format(" ({})", format_message_result);
|
||||
system_message = fmt_lib::format(" ({})", (LPSTR)format_message_result.hlocal_);
|
||||
}
|
||||
|
||||
if (format_message_result)
|
||||
{
|
||||
LocalFree((HLOCAL)format_message_result);
|
||||
}
|
||||
|
||||
return fmt::format("{}: {}{}", user_message, error_code, system_message);
|
||||
return fmt_lib::format("{}: {}{}", user_message, error_code, system_message);
|
||||
}
|
||||
|
||||
explicit win32_error(std::string const &func_name, DWORD error = GetLastError())
|
||||
|
@ -128,49 +128,49 @@ SPDLOG_API spdlog::logger *default_logger_raw();
|
||||
SPDLOG_API void set_default_logger(std::shared_ptr<spdlog::logger> default_logger);
|
||||
|
||||
template<typename... Args>
|
||||
inline void log(source_loc source, level::level_enum lvl, fmt::format_string<Args...> fmt, Args &&...args)
|
||||
inline void log(source_loc source, level::level_enum lvl, format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->log(source, lvl, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
inline void log(level::level_enum lvl, fmt::format_string<Args...> fmt, Args &&...args)
|
||||
inline void log(level::level_enum lvl, format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->log(source_loc{}, lvl, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
inline void trace(fmt::format_string<Args...> fmt, Args &&...args)
|
||||
inline void trace(format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->trace(fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
inline void debug(fmt::format_string<Args...> fmt, Args &&...args)
|
||||
inline void debug(format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->debug(fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
inline void info(fmt::format_string<Args...> fmt, Args &&...args)
|
||||
inline void info(format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->info(fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
inline void warn(fmt::format_string<Args...> fmt, Args &&...args)
|
||||
inline void warn(format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->warn(fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
inline void error(fmt::format_string<Args...> fmt, Args &&...args)
|
||||
inline void error(format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->error(fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
inline void critical(fmt::format_string<Args...> fmt, Args &&...args)
|
||||
inline void critical(format_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->critical(fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
@ -189,49 +189,49 @@ inline void log(level::level_enum lvl, const T &msg)
|
||||
|
||||
#ifdef SPDLOG_WCHAR_TO_UTF8_SUPPORT
|
||||
template<typename... Args>
|
||||
inline void log(source_loc source, level::level_enum lvl, fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
inline void log(source_loc source, level::level_enum lvl, wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->log(source, lvl, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
inline void log(level::level_enum lvl, fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
inline void log(level::level_enum lvl, wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->log(source_loc{}, lvl, fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
inline void trace(fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
inline void trace(wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->trace(fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
inline void debug(fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
inline void debug(wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->debug(fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
inline void info(fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
inline void info(wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->info(fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
inline void warn(fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
inline void warn(wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->warn(fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
inline void error(fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
inline void error(wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->error(fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
inline void critical(fmt::wformat_string<Args...> fmt, Args &&...args)
|
||||
inline void critical(wformat_string_t<Args...> fmt, Args &&...args)
|
||||
{
|
||||
default_logger_raw()->critical(fmt, std::forward<Args>(args)...);
|
||||
}
|
||||
|
@ -48,7 +48,14 @@ public:
|
||||
} // namespace spdlog
|
||||
|
||||
// Support for fmt formatting (e.g. "{:012.9}" or just "{}")
|
||||
namespace fmt {
|
||||
namespace
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
std
|
||||
#else
|
||||
fmt
|
||||
#endif
|
||||
{
|
||||
|
||||
template<>
|
||||
struct formatter<spdlog::stopwatch> : formatter<double>
|
||||
{
|
||||
@ -58,4 +65,4 @@ struct formatter<spdlog::stopwatch> : formatter<double>
|
||||
return formatter<double>::format(sw.elapsed().count(), ctx);
|
||||
}
|
||||
};
|
||||
} // namespace fmt
|
||||
} // namespace fmt/std
|
||||
|
@ -74,6 +74,13 @@
|
||||
// #define SPDLOG_FMT_EXTERNAL
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
// Uncomment to use C++20 std::format instead of fmt. This removes compile
|
||||
// time checking of format strings, but doesn't depend on the fmt library.
|
||||
//
|
||||
// #define SPDLOG_USE_STD_FORMAT
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
// Uncomment to enable wchar_t support (convert to utf8)
|
||||
//
|
||||
|
@ -6,7 +6,7 @@
|
||||
# error Please define SPDLOG_COMPILED_LIB to compile this file.
|
||||
#endif
|
||||
|
||||
#if !defined(SPDLOG_FMT_EXTERNAL)
|
||||
#if !defined(SPDLOG_FMT_EXTERNAL) && !defined(SPDLOG_USE_STD_FORMAT)
|
||||
# include <spdlog/fmt/bundled/format-inl.h>
|
||||
|
||||
FMT_BEGIN_NAMESPACE
|
||||
|
@ -166,7 +166,7 @@ TEST_CASE("to_file", "[async]")
|
||||
require_message_count(TEST_FILENAME, messages);
|
||||
auto contents = file_contents(TEST_FILENAME);
|
||||
using spdlog::details::os::default_eol;
|
||||
REQUIRE(ends_with(contents, fmt::format("Hello message #1023{}", default_eol)));
|
||||
REQUIRE(ends_with(contents, spdlog::fmt_lib::format("Hello message #1023{}", default_eol)));
|
||||
}
|
||||
|
||||
TEST_CASE("to_file multi-workers", "[async]")
|
||||
|
@ -3,7 +3,11 @@
|
||||
*/
|
||||
#include "includes.h"
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
using filename_memory_buf_t = std::basic_string<spdlog::filename_t::value_type>;
|
||||
#else
|
||||
using filename_memory_buf_t = fmt::basic_memory_buffer<spdlog::filename_t::value_type, 250>;
|
||||
#endif
|
||||
|
||||
TEST_CASE("daily_logger with dateonly calculator", "[daily_logger]")
|
||||
{
|
||||
@ -15,7 +19,7 @@ TEST_CASE("daily_logger with dateonly calculator", "[daily_logger]")
|
||||
spdlog::filename_t basename = SPDLOG_FILENAME_T("test_logs/daily_dateonly");
|
||||
std::tm tm = spdlog::details::os::localtime();
|
||||
filename_memory_buf_t w;
|
||||
fmt::format_to(
|
||||
spdlog::fmt_lib::format_to(
|
||||
std::back_inserter(w), SPDLOG_FILENAME_T("{}_{:04d}-{:02d}-{:02d}"), basename, tm.tm_year + 1900, tm.tm_mon + 1, tm.tm_mday);
|
||||
|
||||
auto logger = spdlog::create<sink_type>("logger", basename, 0, 0);
|
||||
@ -29,9 +33,17 @@ TEST_CASE("daily_logger with dateonly calculator", "[daily_logger]")
|
||||
#ifdef SPDLOG_WCHAR_FILENAMES
|
||||
spdlog::memory_buf_t buf;
|
||||
spdlog::details::os::wstr_to_utf8buf(fmt::to_string(w), buf);
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
auto &filename = buf;
|
||||
#else
|
||||
auto filename = fmt::to_string(buf);
|
||||
#endif
|
||||
#else
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
auto &filename = w;
|
||||
#else
|
||||
auto filename = fmt::to_string(w);
|
||||
#endif
|
||||
#endif
|
||||
require_message_count(filename, 10);
|
||||
}
|
||||
@ -41,9 +53,13 @@ struct custom_daily_file_name_calculator
|
||||
static spdlog::filename_t calc_filename(const spdlog::filename_t &basename, const tm &now_tm)
|
||||
{
|
||||
filename_memory_buf_t w;
|
||||
fmt::format_to(std::back_inserter(w), SPDLOG_FILENAME_T("{}{:04d}{:02d}{:02d}"), basename, now_tm.tm_year + 1900, now_tm.tm_mon + 1,
|
||||
spdlog::fmt_lib::format_to(std::back_inserter(w), SPDLOG_FILENAME_T("{}{:04d}{:02d}{:02d}"), basename, now_tm.tm_year + 1900, now_tm.tm_mon + 1,
|
||||
now_tm.tm_mday);
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
return w;
|
||||
#else
|
||||
return fmt::to_string(w);
|
||||
#endif
|
||||
}
|
||||
};
|
||||
|
||||
@ -57,7 +73,7 @@ TEST_CASE("daily_logger with custom calculator", "[daily_logger]")
|
||||
spdlog::filename_t basename = SPDLOG_FILENAME_T("test_logs/daily_dateonly");
|
||||
std::tm tm = spdlog::details::os::localtime();
|
||||
filename_memory_buf_t w;
|
||||
fmt::format_to(
|
||||
spdlog::fmt_lib::format_to(
|
||||
std::back_inserter(w), SPDLOG_FILENAME_T("{}{:04d}{:02d}{:02d}"), basename, tm.tm_year + 1900, tm.tm_mon + 1, tm.tm_mday);
|
||||
|
||||
auto logger = spdlog::create<sink_type>("logger", basename, 0, 0);
|
||||
@ -71,9 +87,17 @@ TEST_CASE("daily_logger with custom calculator", "[daily_logger]")
|
||||
#ifdef SPDLOG_WCHAR_FILENAMES
|
||||
spdlog::memory_buf_t buf;
|
||||
spdlog::details::os::wstr_to_utf8buf(fmt::to_string(w), buf);
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
auto &filename = buf;
|
||||
#else
|
||||
auto filename = fmt::to_string(buf);
|
||||
#endif
|
||||
#else
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
auto &filename = w;
|
||||
#else
|
||||
auto filename = fmt::to_string(w);
|
||||
#endif
|
||||
#endif
|
||||
require_message_count(filename, 10);
|
||||
}
|
||||
@ -118,6 +142,16 @@ TEST_CASE("daily_file_sink::daily_filename_calculator", "[daily_file_sink]]")
|
||||
}
|
||||
#endif
|
||||
|
||||
TEST_CASE("daily_file_sink::daily_filename_format_calculator", "[daily_file_sink]]")
|
||||
{
|
||||
std::tm tm = spdlog::details::os::localtime();
|
||||
// example-YYYY-MM-DD.log
|
||||
auto filename =
|
||||
spdlog::sinks::daily_filename_format_calculator::calc_filename(SPDLOG_FILENAME_T("example-%Y-%m-%d.log"), tm);
|
||||
|
||||
REQUIRE(filename == spdlog::fmt_lib::format(SPDLOG_FILENAME_T("example-{:04d}-{:02d}-{:02d}.log"), tm.tm_year + 1900, tm.tm_mon + 1, tm.tm_mday));
|
||||
}
|
||||
|
||||
/* Test removal of old files */
|
||||
static spdlog::details::log_msg create_msg(std::chrono::seconds offset)
|
||||
{
|
||||
|
@ -29,12 +29,16 @@ TEST_CASE("default_error_handler", "[errors]]")
|
||||
|
||||
auto logger = spdlog::create<spdlog::sinks::basic_file_sink_mt>("test-error", filename, true);
|
||||
logger->set_pattern("%v");
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
logger->info("Test message {} {}", 1);
|
||||
#else
|
||||
logger->info(fmt::runtime("Test message {} {}"), 1);
|
||||
#endif
|
||||
logger->info("Test message {}", 2);
|
||||
logger->flush();
|
||||
|
||||
using spdlog::details::os::default_eol;
|
||||
REQUIRE(file_contents(SIMPLE_LOG) == fmt::format("Test message 2{}", default_eol));
|
||||
REQUIRE(file_contents(SIMPLE_LOG) == spdlog::fmt_lib::format("Test message 2{}", default_eol));
|
||||
REQUIRE(count_lines(SIMPLE_LOG) == 1);
|
||||
}
|
||||
|
||||
@ -49,7 +53,11 @@ TEST_CASE("custom_error_handler", "[errors]]")
|
||||
logger->set_error_handler([=](const std::string &) { throw custom_ex(); });
|
||||
logger->info("Good message #1");
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE_THROWS_AS(logger->info("Bad format msg {} {}", "xxx"), custom_ex);
|
||||
#else
|
||||
REQUIRE_THROWS_AS(logger->info(fmt::runtime("Bad format msg {} {}"), "xxx"), custom_ex);
|
||||
#endif
|
||||
logger->info("Good message #2");
|
||||
require_message_count(SIMPLE_LOG, 2);
|
||||
}
|
||||
@ -88,7 +96,11 @@ TEST_CASE("async_error_handler", "[errors]]")
|
||||
ofs << err_msg;
|
||||
});
|
||||
logger->info("Good message #1");
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
logger->info("Bad format msg {} {}", "xxx");
|
||||
#else
|
||||
logger->info(fmt::runtime("Bad format msg {} {}"), "xxx");
|
||||
#endif
|
||||
logger->info("Good message #2");
|
||||
spdlog::drop("logger"); // force logger to drain the queue and shutdown
|
||||
}
|
||||
|
@ -10,7 +10,7 @@ using spdlog::details::file_helper;
|
||||
static void write_with_helper(file_helper &helper, size_t howmany)
|
||||
{
|
||||
spdlog::memory_buf_t formatted;
|
||||
fmt::format_to(std::back_inserter(formatted), "{}", std::string(howmany, '1'));
|
||||
spdlog::fmt_lib::format_to(std::back_inserter(formatted), "{}", std::string(howmany, '1'));
|
||||
helper.write(formatted);
|
||||
helper.flush();
|
||||
}
|
||||
|
@ -20,7 +20,7 @@ TEST_CASE("simple_file_logger", "[simple_logger]]")
|
||||
logger->flush();
|
||||
require_message_count(SIMPLE_LOG, 2);
|
||||
using spdlog::details::os::default_eol;
|
||||
REQUIRE(file_contents(SIMPLE_LOG) == fmt::format("Test message 1{}Test message 2{}", default_eol, default_eol));
|
||||
REQUIRE(file_contents(SIMPLE_LOG) == spdlog::fmt_lib::format("Test message 1{}Test message 2{}", default_eol, default_eol));
|
||||
}
|
||||
|
||||
TEST_CASE("flush_on", "[flush_on]]")
|
||||
@ -41,7 +41,7 @@ TEST_CASE("flush_on", "[flush_on]]")
|
||||
require_message_count(SIMPLE_LOG, 3);
|
||||
using spdlog::details::os::default_eol;
|
||||
REQUIRE(file_contents(SIMPLE_LOG) ==
|
||||
fmt::format("Should not be flushed{}Test message 1{}Test message 2{}", default_eol, default_eol, default_eol));
|
||||
spdlog::fmt_lib::format("Should not be flushed{}Test message 1{}Test message 2{}", default_eol, default_eol, default_eol));
|
||||
}
|
||||
|
||||
TEST_CASE("rotating_file_logger1", "[rotating_logger]]")
|
||||
|
@ -8,28 +8,48 @@ void test_pad2(int n, const char *expected)
|
||||
{
|
||||
memory_buf_t buf;
|
||||
spdlog::details::fmt_helper::pad2(n, buf);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(buf == expected);
|
||||
#else
|
||||
REQUIRE(fmt::to_string(buf) == expected);
|
||||
#endif
|
||||
}
|
||||
|
||||
void test_pad3(uint32_t n, const char *expected)
|
||||
{
|
||||
memory_buf_t buf;
|
||||
spdlog::details::fmt_helper::pad3(n, buf);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(buf == expected);
|
||||
#else
|
||||
REQUIRE(fmt::to_string(buf) == expected);
|
||||
#endif
|
||||
}
|
||||
|
||||
void test_pad6(std::size_t n, const char *expected)
|
||||
{
|
||||
memory_buf_t buf;
|
||||
spdlog::details::fmt_helper::pad6(n, buf);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(buf == expected);
|
||||
#else
|
||||
REQUIRE(fmt::to_string(buf) == expected);
|
||||
#endif
|
||||
}
|
||||
|
||||
void test_pad9(std::size_t n, const char *expected)
|
||||
{
|
||||
memory_buf_t buf;
|
||||
spdlog::details::fmt_helper::pad9(n, buf);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(buf == expected);
|
||||
#else
|
||||
REQUIRE(fmt::to_string(buf) == expected);
|
||||
#endif
|
||||
}
|
||||
|
||||
TEST_CASE("pad2", "[fmt_helper]")
|
||||
|
@ -25,7 +25,7 @@ TEST_CASE("debug and trace w/o format string", "[macros]]")
|
||||
logger->flush();
|
||||
|
||||
using spdlog::details::os::default_eol;
|
||||
REQUIRE(ends_with(file_contents(TEST_FILENAME), fmt::format("Test message 2{}", default_eol)));
|
||||
REQUIRE(ends_with(file_contents(TEST_FILENAME), spdlog::fmt_lib::format("Test message 2{}", default_eol)));
|
||||
REQUIRE(count_lines(TEST_FILENAME) == 1);
|
||||
|
||||
spdlog::set_default_logger(logger);
|
||||
@ -35,7 +35,7 @@ TEST_CASE("debug and trace w/o format string", "[macros]]")
|
||||
logger->flush();
|
||||
|
||||
require_message_count(TEST_FILENAME, 2);
|
||||
REQUIRE(ends_with(file_contents(TEST_FILENAME), fmt::format("Test message 4{}", default_eol)));
|
||||
REQUIRE(ends_with(file_contents(TEST_FILENAME), spdlog::fmt_lib::format("Test message 4{}", default_eol)));
|
||||
}
|
||||
|
||||
TEST_CASE("disable param evaluation", "[macros]")
|
||||
|
@ -64,7 +64,7 @@ TEST_CASE("color range test1", "[pattern_formatter]")
|
||||
auto formatter = std::make_shared<spdlog::pattern_formatter>("%^%v%$", spdlog::pattern_time_type::local, "\n");
|
||||
|
||||
memory_buf_t buf;
|
||||
fmt::format_to(std::back_inserter(buf), "Hello");
|
||||
spdlog::fmt_lib::format_to(std::back_inserter(buf), "Hello");
|
||||
memory_buf_t formatted;
|
||||
std::string logger_name = "test";
|
||||
spdlog::details::log_msg msg(logger_name, spdlog::level::info, spdlog::string_view_t(buf.data(), buf.size()));
|
||||
@ -273,7 +273,11 @@ TEST_CASE("clone-default-formatter", "[pattern_formatter]")
|
||||
formatter_1->format(msg, formatted_1);
|
||||
formatter_2->format(msg, formatted_2);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(formatted_1 == formatted_2);
|
||||
#else
|
||||
REQUIRE(fmt::to_string(formatted_1) == fmt::to_string(formatted_2));
|
||||
#endif
|
||||
}
|
||||
|
||||
TEST_CASE("clone-default-formatter2", "[pattern_formatter]")
|
||||
@ -288,7 +292,11 @@ TEST_CASE("clone-default-formatter2", "[pattern_formatter]")
|
||||
formatter_1->format(msg, formatted_1);
|
||||
formatter_2->format(msg, formatted_2);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(formatted_1 == formatted_2);
|
||||
#else
|
||||
REQUIRE(fmt::to_string(formatted_1) == fmt::to_string(formatted_2));
|
||||
#endif
|
||||
}
|
||||
|
||||
TEST_CASE("clone-formatter", "[pattern_formatter]")
|
||||
@ -302,7 +310,12 @@ TEST_CASE("clone-formatter", "[pattern_formatter]")
|
||||
memory_buf_t formatted_2;
|
||||
formatter_1->format(msg, formatted_1);
|
||||
formatter_2->format(msg, formatted_2);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(formatted_1 == formatted_2);
|
||||
#else
|
||||
REQUIRE(fmt::to_string(formatted_1) == fmt::to_string(formatted_2));
|
||||
#endif
|
||||
}
|
||||
|
||||
TEST_CASE("clone-formatter-2", "[pattern_formatter]")
|
||||
@ -317,7 +330,12 @@ TEST_CASE("clone-formatter-2", "[pattern_formatter]")
|
||||
memory_buf_t formatted_2;
|
||||
formatter_1->format(msg, formatted_1);
|
||||
formatter_2->format(msg, formatted_2);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(formatted_1 == formatted_2);
|
||||
#else
|
||||
REQUIRE(fmt::to_string(formatted_1) == fmt::to_string(formatted_2));
|
||||
#endif
|
||||
}
|
||||
|
||||
class custom_test_flag : public spdlog::custom_flag_formatter
|
||||
@ -362,9 +380,15 @@ TEST_CASE("clone-custom_formatter", "[pattern_formatter]")
|
||||
formatter_1->format(msg, formatted_1);
|
||||
formatter_2->format(msg, formatted_2);
|
||||
|
||||
auto expected = fmt::format("[logger-name] [custom_output] some message{}", spdlog::details::os::default_eol);
|
||||
auto expected = spdlog::fmt_lib::format("[logger-name] [custom_output] some message{}", spdlog::details::os::default_eol);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(formatted_1 == expected);
|
||||
REQUIRE(formatted_2 == expected);
|
||||
#else
|
||||
REQUIRE(fmt::to_string(formatted_1) == expected);
|
||||
REQUIRE(fmt::to_string(formatted_2) == expected);
|
||||
#endif
|
||||
}
|
||||
|
||||
//
|
||||
@ -385,7 +409,12 @@ TEST_CASE("short filename formatter-1", "[pattern_formatter]")
|
||||
spdlog::source_loc source_loc{test_path, 123, "some_func()"};
|
||||
spdlog::details::log_msg msg(source_loc, "logger-name", spdlog::level::info, "Hello");
|
||||
formatter.format(msg, formatted);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(formatted == "myfile.cpp");
|
||||
#else
|
||||
REQUIRE(fmt::to_string(formatted) == "myfile.cpp");
|
||||
#endif
|
||||
}
|
||||
|
||||
TEST_CASE("short filename formatter-2", "[pattern_formatter]")
|
||||
@ -396,7 +425,12 @@ TEST_CASE("short filename formatter-2", "[pattern_formatter]")
|
||||
spdlog::source_loc source_loc{"myfile.cpp", 123, "some_func()"};
|
||||
spdlog::details::log_msg msg(source_loc, "logger-name", spdlog::level::info, "Hello");
|
||||
formatter.format(msg, formatted);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(formatted == "myfile.cpp:123");
|
||||
#else
|
||||
REQUIRE(fmt::to_string(formatted) == "myfile.cpp:123");
|
||||
#endif
|
||||
}
|
||||
|
||||
TEST_CASE("short filename formatter-3", "[pattern_formatter]")
|
||||
@ -407,7 +441,12 @@ TEST_CASE("short filename formatter-3", "[pattern_formatter]")
|
||||
spdlog::source_loc source_loc{"", 123, "some_func()"};
|
||||
spdlog::details::log_msg msg(source_loc, "logger-name", spdlog::level::info, "Hello");
|
||||
formatter.format(msg, formatted);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(formatted == " Hello");
|
||||
#else
|
||||
REQUIRE(fmt::to_string(formatted) == " Hello");
|
||||
#endif
|
||||
}
|
||||
|
||||
TEST_CASE("full filename formatter", "[pattern_formatter]")
|
||||
@ -418,7 +457,12 @@ TEST_CASE("full filename formatter", "[pattern_formatter]")
|
||||
spdlog::source_loc source_loc{test_path, 123, "some_func()"};
|
||||
spdlog::details::log_msg msg(source_loc, "logger-name", spdlog::level::info, "Hello");
|
||||
formatter.format(msg, formatted);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(formatted == test_path);
|
||||
#else
|
||||
REQUIRE(fmt::to_string(formatted) == test_path);
|
||||
#endif
|
||||
}
|
||||
|
||||
TEST_CASE("custom flags", "[pattern_formatter]")
|
||||
@ -430,8 +474,13 @@ TEST_CASE("custom flags", "[pattern_formatter]")
|
||||
|
||||
spdlog::details::log_msg msg(spdlog::source_loc{}, "logger-name", spdlog::level::info, "some message");
|
||||
formatter->format(msg, formatted);
|
||||
auto expected = fmt::format("[logger-name] [custom1] [custom2] some message{}", spdlog::details::os::default_eol);
|
||||
auto expected = spdlog::fmt_lib::format("[logger-name] [custom1] [custom2] some message{}", spdlog::details::os::default_eol);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(formatted == expected);
|
||||
#else
|
||||
REQUIRE(fmt::to_string(formatted) == expected);
|
||||
#endif
|
||||
}
|
||||
|
||||
TEST_CASE("custom flags-padding", "[pattern_formatter]")
|
||||
@ -443,8 +492,13 @@ TEST_CASE("custom flags-padding", "[pattern_formatter]")
|
||||
|
||||
spdlog::details::log_msg msg(spdlog::source_loc{}, "logger-name", spdlog::level::info, "some message");
|
||||
formatter->format(msg, formatted);
|
||||
auto expected = fmt::format("[logger-name] [custom1] [ custom2] some message{}", spdlog::details::os::default_eol);
|
||||
auto expected = spdlog::fmt_lib::format("[logger-name] [custom1] [ custom2] some message{}", spdlog::details::os::default_eol);
|
||||
|
||||
#ifdef SPDLOG_USE_STD_FORMAT
|
||||
REQUIRE(formatted == expected);
|
||||
#else
|
||||
REQUIRE(fmt::to_string(formatted) == expected);
|
||||
#endif
|
||||
}
|
||||
|
||||
TEST_CASE("custom flags-exception", "[pattern_formatter]")
|
||||
|
Loading…
Reference in New Issue
Block a user