{"id":13419188,"url":"https://github.com/mattiasflodin/reckless","last_synced_at":"2025-12-16T20:52:12.390Z","repository":{"id":25100192,"uuid":"28521323","full_name":"mattiasflodin/reckless","owner":"mattiasflodin","description":"Reckless logging. Low-latency, high-throughput, asynchronous logging library for C++.","archived":false,"fork":false,"pushed_at":"2023-10-22T08:41:31.000Z","size":3446,"stargazers_count":486,"open_issues_count":14,"forks_count":48,"subscribers_count":27,"default_branch":"master","last_synced_at":"2024-07-31T22:46:10.673Z","etag":null,"topics":["asynchronous","cpp","logging","logging-library","performance"],"latest_commit_sha":null,"homepage":"","language":"C++","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"other","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/mattiasflodin.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE.txt","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null}},"created_at":"2014-12-26T21:12:42.000Z","updated_at":"2024-07-29T03:36:22.000Z","dependencies_parsed_at":"2024-01-08T21:18:50.770Z","dependency_job_id":null,"html_url":"https://github.com/mattiasflodin/reckless","commit_stats":null,"previous_names":[],"tags_count":9,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mattiasflodin%2Freckless","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mattiasflodin%2Freckless/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mattiasflodin%2Freckless/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mattiasflodin%2Freckless/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/mattiasflodin","download_url":"https://codeload.github.com/mattiasflodin/reckless/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":243690121,"owners_count":20331725,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["asynchronous","cpp","logging","logging-library","performance"],"created_at":"2024-07-30T22:01:12.514Z","updated_at":"2025-12-16T20:52:12.327Z","avatar_url":"https://github.com/mattiasflodin.png","language":"C++","funding_links":[],"categories":["TODO scan for Android support in followings","Logging","进程间通信","C++"],"sub_categories":["日志"],"readme":"[![Performance chart for a quad-core CPU](doc/images/performance_mandelbrot_difference.png)](doc/performance.md)\n\nIntroduction\n============\nReckless is an [extremely low-latency, high-throughput logging\nlibrary](doc/performance.md). It was created because I needed to perform\nextensive diagnostic logging without worrying about performance. [Other\nlogging libraries](http://www.pantheios.org/performance.html) boast the\nability to throw log messages away very quickly. Reckless boasts the ability\nto keep them all, without worrying about the performance impact. Filtering can\nand should wait until you want to read the log, or need to clean up disk\nspace.\n\nHow it works\n============\nBy low latency I mean that the time from calling the library and\nreturning to the caller is as short as I could make it. The code\ngenerated at the call site consists only of pushing the arguments on a\nshared, lockless queue. In the non-contended case this has roughly the\nsame cost as a making a function call. The actual message formatting\nand writing is performed asynchronously by a separate thread. This\nremoves or hides several costs:\n\n* No transition to the kernel at the call site. The kernel is an easily\n  overlooked but important cost, not only because the transition costs\n  time, but because it pollutes the CPU cache. In other words, avoiding\n  this *makes your non-logging code run faster* than if you were using a\n  library that has to enter the kernel to perform its work.\n* No locks need to be taken for synchronization between threads (unless\n  the queue fills up; see the performance article for more information\n  about the implications of this).\n* No text formatting needs to be performed before resuming the main\n  task of the program.\n* It doesn't have to wait for the actual I/O operation to complete.\n* If there are bursts of log calls, multiple items on the queue can be\n  batched into a single I/O operation, improving throughput without sacrificing\n  write latency.\n\nFor a more detailed performance discussion and statistics, see the\n[performance article](doc/performance.md).\n\nWhat's the catch?\n=================\nAs all string formatting and I/O is done asynchronously and in a single\nthread, there are a few caveats you need to be aware of:\n* If you choose to pass log arguments by reference or pointer, then you\n  must ensure that the referenced data remains valid at least until the\n  log has been flushed or closed (unless you're only interested in\n  logging the value of the pointer itself). The best option for\n  dynamically allocated data is typically `std::string`,\n  `std::shared_ptr` or `std::unique_ptr`.\n* You must take special care to handle crashes if you want to make sure\n  that all log data prior to the crash is saved. This is not unique to\n  asynchronous logging\u0026mdash;for example fprintf will buffer data until you\n  flush it\u0026mdash;but asynchronous logging arguably makes the issue worse. The\n  library provides convenience functions to aid with this.\n* As all string formatting is done in a single thread, it could\n  theoretically limit the scalability of your application if\n  formatting is expensive or your program generates a high volume of\n  log entries in parallel.\n* Performance becomes somewhat less predictable and harder to measure. Rather\n  than putting the cost of the logging on the thread that calls the logging\n  library, the OS may suspend some other thread to make room for the logging\n  thread to run.\n\nBasic use\n=========\n```c++\n#include \u003creckless/severity_log.hpp\u003e\n#include \u003creckless/file_writer.hpp\u003e\n\n// It is possible to build custom loggers for various ways of formatting the\n// log. The severity log is a stock policy-based logger that allows you to\n// configure fields that should be put on each line, including a severity\n// marker for debug/info/warning/error.\nusing log_t = reckless::severity_log\u003c\n    reckless::indent\u003c4\u003e,       // 4 spaces of indent\n    ' ',                       // Field separator\n    reckless::severity_field,  // Show severity marker (D/I/W/E) first\n    reckless::timestamp_field  // Then timestamp field\n    \u003e;\n\nreckless::file_writer writer(\"log.txt\");\nlog_t g_log(\u0026writer);\n\nint main()\n{\n    std::string s(\"Hello World!\");\n\n    // You can use ordinary printf-style syntax, but unlike stdio this\n    // is type-safe and extensible.\n    g_log.debug(\"Pointer: %p\", s.c_str());\n    g_log.info(\"Info line: %s\", s);\n\n    for(int i=0; i!=4; ++i) {\n        reckless::scoped_indent indent;  // The indent object causes the lines\n        g_log.warn(\"Warning: %d\", i);    // within this scope to be indented.\n    }\n\n    g_log.error(\"Error: %f\", 3.14);\n\n    return 0;\n}\n```\nThis would give the following output:\n```\nD 2019-03-09 12:53:54.280 Pointer: 0x7fff58378850\nI 2019-03-09 12:53:54.280 Info line: Hello World!\nW 2019-03-09 12:53:54.280     Warning: 0\nW 2019-03-09 12:53:54.280     Warning: 1\nW 2019-03-09 12:53:54.280     Warning: 2\nW 2019-03-09 12:53:54.280     Warning: 3\nE 2019-03-09 12:53:54.280 Error: 3.140000\n```\n\nPlatforms\n=========\nThe library works on Windows and Linux. BSD is on the roadmap. I don't\nown any Apple computers, so OS X won't happen unless someone sends me\na patch or buys me hardware.\n\nBuilding\n========\n\nAlternative 1: Using Visual Studio\n----------------------------------\nOn Windows it is recommended to use Visual Studio for building the library.\nSimply open reckless.sln, choose \"batch build\" and \"select all\". Then press Build.\nThe library files will be placed in the `build` subdirectory.\n\nTo build a program against the library you need to set your library path to\npoint to the appropriate library build for your configuration, and set the\ninclude path to `$(RECKLESS)/reckless/include`, where `RECKLESS`, given that\nRECKLESS is a property that points to the reckless source directory.\n\nAlternative 2: using Make\n-------------------------\nTo build the library using GNU Make, clone the git repository and run make.\nThis only works with GCC-compatible compilers.\n\nTo build a program against the library, given the variable RECKLESS\npointing to the reckless root directory, use e.g.:\n\n```bash\ng++ -std=c++11 myprogram.cpp -I$(RECKLESS)/reckless/include -L$(RECKLESS)/reckless/lib -lreckless -lpthread\n```\n\nAlternative 3: using CMake\n--------------------------\nTo build the library using CMake, clone the git repository and run the following commands:\n\n```\nmkdir build; cd build\ncmake ..\nmake\n```\n\nTo build a program against this library using CMake, add the following line to your program's CMakeLists.txt:\n\n```\nadd_subdirectory(path/to/reckless)\n```\n\nSubsequently, to link this library to a program (e.g. *your_executable*), add the following to your program's CMakeLists.txt:\n\n```\ntarget_link_libraries(your_executable reckless pthread)\n```\n\nMore information\n================\nFor more details, see the [manual](doc/manual.md).\n\nAlternatives\n============\nOther logging libraries with similar, asynchronous design are\n* [spdlog](https://github.com/gabime/spdlog/)\n* [g3log](https://github.com/KjellKod/g3log/)\n* [NanoLog](https://github.com/Iyengar111/NanoLog) (there is [another\n  NanoLog](https://github.com/PlatformLab/NanoLog) which deviates in design\n  since it logs binary data and requires postprocessing to read the log file)\n* [mini-async-log](https://github.com/RafaGago/mini-async-log)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmattiasflodin%2Freckless","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmattiasflodin%2Freckless","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmattiasflodin%2Freckless/lists"}