Photon 1.0.0
Loading...
Searching...
No Matches
pattern_formatter-inl.h
Go to the documentation of this file.
1// Copyright(c) 2015-present, Gabi Melman & spdlog contributors.
2// Distributed under the MIT License (http://opensource.org/licenses/MIT)
3
4#pragma once
5
6#ifndef SPDLOG_HEADER_ONLY
8#endif
9
12#include <spdlog/details/os.h>
13#include <spdlog/fmt/fmt.h>
14#include <spdlog/formatter.h>
15
16#include <algorithm>
17#include <array>
18#include <chrono>
19#include <ctime>
20#include <cctype>
21#include <cstring>
22#include <iterator>
23#include <memory>
24#include <mutex>
25#include <string>
26#include <thread>
27#include <utility>
28#include <vector>
29
30namespace spdlog
31{
32 namespace details
33 {
34
36 // name & level pattern appender
38
40 {
41 public:
42 scoped_padder(size_t wrapped_size, const padding_info& padinfo, memory_buf_t& dest)
43 : padinfo_(padinfo), dest_(dest)
44 {
45 remaining_pad_ = static_cast<long>(padinfo.width_) - static_cast<long>(wrapped_size);
46 if (remaining_pad_ <= 0)
47 {
48 return;
49 }
50
52 {
55 }
57 {
58 auto half_pad = remaining_pad_ / 2;
59 auto reminder = remaining_pad_ & 1;
60 pad_it(half_pad);
61 remaining_pad_ = half_pad + reminder; // for the right side
62 }
63 }
64
65 template <typename T>
66 static unsigned int count_digits(T n)
67 {
69 }
70
72 {
73 if (remaining_pad_ >= 0)
74 {
76 }
77 else if (padinfo_.truncate_)
78 {
79 long new_size = static_cast<long>(dest_.size()) + remaining_pad_;
80 dest_.resize(static_cast<size_t>(new_size));
81 }
82 }
83
84 private:
85 void pad_it(long count)
86 {
87 fmt_helper::append_string_view(string_view_t(spaces_.data(), static_cast<size_t>(count)), dest_);
88 }
89
94 };
95
97 {
98 null_scoped_padder(size_t /*wrapped_size*/, const padding_info& /*padinfo*/, memory_buf_t& /*dest*/)
99 {
100 }
101
102 template <typename T>
103 static unsigned int count_digits(T /* number */)
104 {
105 return 0;
106 }
107 };
108
109 template <typename ScopedPadder>
110 class name_formatter final : public flag_formatter
111 {
112 public:
113 explicit name_formatter(padding_info padinfo)
114 : flag_formatter(padinfo)
115 {
116 }
117
118 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
119 {
120 ScopedPadder p(msg.logger_name.size(), padinfo_, dest);
122 }
123 };
124
125 // log level appender
126 template <typename ScopedPadder>
127 class level_formatter final : public flag_formatter
128 {
129 public:
131 : flag_formatter(padinfo)
132 {
133 }
134
135 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
136 {
137 const string_view_t& level_name = level::to_string_view(msg.level);
138 ScopedPadder p(level_name.size(), padinfo_, dest);
139 fmt_helper::append_string_view(level_name, dest);
140 }
141 };
142
143 // short log level appender
144 template <typename ScopedPadder>
146 {
147 public:
149 : flag_formatter(padinfo)
150 {
151 }
152
153 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
154 {
156 ScopedPadder p(level_name.size(), padinfo_, dest);
157 fmt_helper::append_string_view(level_name, dest);
158 }
159 };
160
162 // Date time pattern appenders
164
165 static const char* ampm(const tm& t)
166 {
167 return t.tm_hour >= 12 ? "PM" : "AM";
168 }
169
170 static int to12h(const tm& t)
171 {
172 return t.tm_hour > 12 ? t.tm_hour - 12 : t.tm_hour;
173 }
174
175 // Abbreviated weekday name
176 static std::array<const char*, 7> days{{"Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"}};
177
178 template <typename ScopedPadder>
179 class a_formatter final : public flag_formatter
180 {
181 public:
182 explicit a_formatter(padding_info padinfo)
183 : flag_formatter(padinfo)
184 {
185 }
186
187 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
188 {
189 string_view_t field_value{days[static_cast<size_t>(tm_time.tm_wday)]};
190 ScopedPadder p(field_value.size(), padinfo_, dest);
191 fmt_helper::append_string_view(field_value, dest);
192 }
193 };
194
195 // Full weekday name
196 static std::array<const char*, 7> full_days{{"Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"}};
197
198 template <typename ScopedPadder>
200 {
201 public:
202 explicit A_formatter(padding_info padinfo)
203 : flag_formatter(padinfo)
204 {
205 }
206
207 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
208 {
209 string_view_t field_value{full_days[static_cast<size_t>(tm_time.tm_wday)]};
210 ScopedPadder p(field_value.size(), padinfo_, dest);
211 fmt_helper::append_string_view(field_value, dest);
212 }
213 };
214
215 // Abbreviated month
216 static const std::array<const char*, 12> months{{"Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sept", "Oct", "Nov", "Dec"}};
217
218 template <typename ScopedPadder>
219 class b_formatter final : public flag_formatter
220 {
221 public:
222 explicit b_formatter(padding_info padinfo)
223 : flag_formatter(padinfo)
224 {
225 }
226
227 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
228 {
229 string_view_t field_value{months[static_cast<size_t>(tm_time.tm_mon)]};
230 ScopedPadder p(field_value.size(), padinfo_, dest);
231 fmt_helper::append_string_view(field_value, dest);
232 }
233 };
234
235 // Full month name
236 static const std::array<const char*, 12> full_months{
237 {"January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"}};
238
239 template <typename ScopedPadder>
240 class B_formatter final : public flag_formatter
241 {
242 public:
243 explicit B_formatter(padding_info padinfo)
244 : flag_formatter(padinfo)
245 {
246 }
247
248 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
249 {
250 string_view_t field_value{full_months[static_cast<size_t>(tm_time.tm_mon)]};
251 ScopedPadder p(field_value.size(), padinfo_, dest);
252 fmt_helper::append_string_view(field_value, dest);
253 }
254 };
255
256 // Date and time representation (Thu Aug 23 15:35:46 2014)
257 template <typename ScopedPadder>
258 class c_formatter final : public flag_formatter
259 {
260 public:
261 explicit c_formatter(padding_info padinfo)
262 : flag_formatter(padinfo)
263 {
264 }
265
266 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
267 {
268 const size_t field_size = 24;
269 ScopedPadder p(field_size, padinfo_, dest);
270
271 fmt_helper::append_string_view(days[static_cast<size_t>(tm_time.tm_wday)], dest);
272 dest.push_back(' ');
273 fmt_helper::append_string_view(months[static_cast<size_t>(tm_time.tm_mon)], dest);
274 dest.push_back(' ');
275 fmt_helper::append_int(tm_time.tm_mday, dest);
276 dest.push_back(' ');
277 // time
278
279 fmt_helper::pad2(tm_time.tm_hour, dest);
280 dest.push_back(':');
281 fmt_helper::pad2(tm_time.tm_min, dest);
282 dest.push_back(':');
283 fmt_helper::pad2(tm_time.tm_sec, dest);
284 dest.push_back(' ');
285 fmt_helper::append_int(tm_time.tm_year + 1900, dest);
286 }
287 };
288
289 // year - 2 digit
290 template <typename ScopedPadder>
291 class C_formatter final : public flag_formatter
292 {
293 public:
294 explicit C_formatter(padding_info padinfo)
295 : flag_formatter(padinfo)
296 {
297 }
298
299 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
300 {
301 const size_t field_size = 2;
302 ScopedPadder p(field_size, padinfo_, dest);
303 fmt_helper::pad2(tm_time.tm_year % 100, dest);
304 }
305 };
306
307 // Short MM/DD/YY date, equivalent to %m/%d/%y 08/23/01
308 template <typename ScopedPadder>
309 class D_formatter final : public flag_formatter
310 {
311 public:
312 explicit D_formatter(padding_info padinfo)
313 : flag_formatter(padinfo)
314 {
315 }
316
317 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
318 {
319 const size_t field_size = 10;
320 ScopedPadder p(field_size, padinfo_, dest);
321
322 fmt_helper::pad2(tm_time.tm_mon + 1, dest);
323 dest.push_back('/');
324 fmt_helper::pad2(tm_time.tm_mday, dest);
325 dest.push_back('/');
326 fmt_helper::pad2(tm_time.tm_year % 100, dest);
327 }
328 };
329
330 // year - 4 digit
331 template <typename ScopedPadder>
332 class Y_formatter final : public flag_formatter
333 {
334 public:
335 explicit Y_formatter(padding_info padinfo)
336 : flag_formatter(padinfo)
337 {
338 }
339
340 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
341 {
342 const size_t field_size = 4;
343 ScopedPadder p(field_size, padinfo_, dest);
344 fmt_helper::append_int(tm_time.tm_year + 1900, dest);
345 }
346 };
347
348 // month 1-12
349 template <typename ScopedPadder>
350 class m_formatter final : public flag_formatter
351 {
352 public:
353 explicit m_formatter(padding_info padinfo)
354 : flag_formatter(padinfo)
355 {
356 }
357
358 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
359 {
360 const size_t field_size = 2;
361 ScopedPadder p(field_size, padinfo_, dest);
362 fmt_helper::pad2(tm_time.tm_mon + 1, dest);
363 }
364 };
365
366 // day of month 1-31
367 template <typename ScopedPadder>
368 class d_formatter final : public flag_formatter
369 {
370 public:
371 explicit d_formatter(padding_info padinfo)
372 : flag_formatter(padinfo)
373 {
374 }
375
376 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
377 {
378 const size_t field_size = 2;
379 ScopedPadder p(field_size, padinfo_, dest);
380 fmt_helper::pad2(tm_time.tm_mday, dest);
381 }
382 };
383
384 // hours in 24 format 0-23
385 template <typename ScopedPadder>
386 class H_formatter final : public flag_formatter
387 {
388 public:
389 explicit H_formatter(padding_info padinfo)
390 : flag_formatter(padinfo)
391 {
392 }
393
394 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
395 {
396 const size_t field_size = 2;
397 ScopedPadder p(field_size, padinfo_, dest);
398 fmt_helper::pad2(tm_time.tm_hour, dest);
399 }
400 };
401
402 // hours in 12 format 1-12
403 template <typename ScopedPadder>
404 class I_formatter final : public flag_formatter
405 {
406 public:
407 explicit I_formatter(padding_info padinfo)
408 : flag_formatter(padinfo)
409 {
410 }
411
412 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
413 {
414 const size_t field_size = 2;
415 ScopedPadder p(field_size, padinfo_, dest);
416 fmt_helper::pad2(to12h(tm_time), dest);
417 }
418 };
419
420 // minutes 0-59
421 template <typename ScopedPadder>
422 class M_formatter final : public flag_formatter
423 {
424 public:
425 explicit M_formatter(padding_info padinfo)
426 : flag_formatter(padinfo)
427 {
428 }
429
430 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
431 {
432 const size_t field_size = 2;
433 ScopedPadder p(field_size, padinfo_, dest);
434 fmt_helper::pad2(tm_time.tm_min, dest);
435 }
436 };
437
438 // seconds 0-59
439 template <typename ScopedPadder>
440 class S_formatter final : public flag_formatter
441 {
442 public:
443 explicit S_formatter(padding_info padinfo)
444 : flag_formatter(padinfo)
445 {
446 }
447
448 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
449 {
450 const size_t field_size = 2;
451 ScopedPadder p(field_size, padinfo_, dest);
452 fmt_helper::pad2(tm_time.tm_sec, dest);
453 }
454 };
455
456 // milliseconds
457 template <typename ScopedPadder>
458 class e_formatter final : public flag_formatter
459 {
460 public:
461 explicit e_formatter(padding_info padinfo)
462 : flag_formatter(padinfo)
463 {
464 }
465
466 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
467 {
468 auto millis = fmt_helper::time_fraction<std::chrono::milliseconds>(msg.time);
469 const size_t field_size = 3;
470 ScopedPadder p(field_size, padinfo_, dest);
471 fmt_helper::pad3(static_cast<uint32_t>(millis.count()), dest);
472 }
473 };
474
475 // microseconds
476 template <typename ScopedPadder>
477 class f_formatter final : public flag_formatter
478 {
479 public:
480 explicit f_formatter(padding_info padinfo)
481 : flag_formatter(padinfo)
482 {
483 }
484
485 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
486 {
487 auto micros = fmt_helper::time_fraction<std::chrono::microseconds>(msg.time);
488
489 const size_t field_size = 6;
490 ScopedPadder p(field_size, padinfo_, dest);
491 fmt_helper::pad6(static_cast<size_t>(micros.count()), dest);
492 }
493 };
494
495 // nanoseconds
496 template <typename ScopedPadder>
497 class F_formatter final : public flag_formatter
498 {
499 public:
500 explicit F_formatter(padding_info padinfo)
501 : flag_formatter(padinfo)
502 {
503 }
504
505 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
506 {
507 auto ns = fmt_helper::time_fraction<std::chrono::nanoseconds>(msg.time);
508 const size_t field_size = 9;
509 ScopedPadder p(field_size, padinfo_, dest);
510 fmt_helper::pad9(static_cast<size_t>(ns.count()), dest);
511 }
512 };
513
514 // seconds since epoch
515 template <typename ScopedPadder>
516 class E_formatter final : public flag_formatter
517 {
518 public:
519 explicit E_formatter(padding_info padinfo)
520 : flag_formatter(padinfo)
521 {
522 }
523
524 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
525 {
526 const size_t field_size = 10;
527 ScopedPadder p(field_size, padinfo_, dest);
528 auto duration = msg.time.time_since_epoch();
529 auto seconds = std::chrono::duration_cast<std::chrono::seconds>(duration).count();
530 fmt_helper::append_int(seconds, dest);
531 }
532 };
533
534 // AM/PM
535 template <typename ScopedPadder>
536 class p_formatter final : public flag_formatter
537 {
538 public:
539 explicit p_formatter(padding_info padinfo)
540 : flag_formatter(padinfo)
541 {
542 }
543
544 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
545 {
546 const size_t field_size = 2;
547 ScopedPadder p(field_size, padinfo_, dest);
548 fmt_helper::append_string_view(ampm(tm_time), dest);
549 }
550 };
551
552 // 12 hour clock 02:55:02 pm
553 template <typename ScopedPadder>
554 class r_formatter final : public flag_formatter
555 {
556 public:
557 explicit r_formatter(padding_info padinfo)
558 : flag_formatter(padinfo)
559 {
560 }
561
562 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
563 {
564 const size_t field_size = 11;
565 ScopedPadder p(field_size, padinfo_, dest);
566
567 fmt_helper::pad2(to12h(tm_time), dest);
568 dest.push_back(':');
569 fmt_helper::pad2(tm_time.tm_min, dest);
570 dest.push_back(':');
571 fmt_helper::pad2(tm_time.tm_sec, dest);
572 dest.push_back(' ');
573 fmt_helper::append_string_view(ampm(tm_time), dest);
574 }
575 };
576
577 // 24-hour HH:MM time, equivalent to %H:%M
578 template <typename ScopedPadder>
579 class R_formatter final : public flag_formatter
580 {
581 public:
582 explicit R_formatter(padding_info padinfo)
583 : flag_formatter(padinfo)
584 {
585 }
586
587 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
588 {
589 const size_t field_size = 5;
590 ScopedPadder p(field_size, padinfo_, dest);
591
592 fmt_helper::pad2(tm_time.tm_hour, dest);
593 dest.push_back(':');
594 fmt_helper::pad2(tm_time.tm_min, dest);
595 }
596 };
597
598 // ISO 8601 time format (HH:MM:SS), equivalent to %H:%M:%S
599 template <typename ScopedPadder>
600 class T_formatter final : public flag_formatter
601 {
602 public:
603 explicit T_formatter(padding_info padinfo)
604 : flag_formatter(padinfo)
605 {
606 }
607
608 void format(const details::log_msg&, const std::tm& tm_time, memory_buf_t& dest) override
609 {
610 const size_t field_size = 8;
611 ScopedPadder p(field_size, padinfo_, dest);
612
613 fmt_helper::pad2(tm_time.tm_hour, dest);
614 dest.push_back(':');
615 fmt_helper::pad2(tm_time.tm_min, dest);
616 dest.push_back(':');
617 fmt_helper::pad2(tm_time.tm_sec, dest);
618 }
619 };
620
621 // ISO 8601 offset from UTC in timezone (+-HH:MM)
622 template <typename ScopedPadder>
623 class z_formatter final : public flag_formatter
624 {
625 public:
626 explicit z_formatter(padding_info padinfo)
627 : flag_formatter(padinfo)
628 {
629 }
630
631 z_formatter() = default;
632 z_formatter(const z_formatter&) = delete;
634
635 void format(const details::log_msg& msg, const std::tm& tm_time, memory_buf_t& dest) override
636 {
637 const size_t field_size = 6;
638 ScopedPadder p(field_size, padinfo_, dest);
639
640 auto total_minutes = get_cached_offset(msg, tm_time);
641 bool is_negative = total_minutes < 0;
642 if (is_negative)
643 {
644 total_minutes = -total_minutes;
645 dest.push_back('-');
646 }
647 else
648 {
649 dest.push_back('+');
650 }
651
652 fmt_helper::pad2(total_minutes / 60, dest); // hours
653 dest.push_back(':');
654 fmt_helper::pad2(total_minutes % 60, dest); // minutes
655 }
656
657 private:
658 log_clock::time_point last_update_{std::chrono::seconds(0)};
660
661 int get_cached_offset(const log_msg& msg, const std::tm& tm_time)
662 {
663 // refresh every 10 seconds
664 if (msg.time - last_update_ >= std::chrono::seconds(10))
665 {
667 last_update_ = msg.time;
668 }
669 return offset_minutes_;
670 }
671 };
672
673 // Thread id
674 template <typename ScopedPadder>
675 class t_formatter final : public flag_formatter
676 {
677 public:
678 explicit t_formatter(padding_info padinfo)
679 : flag_formatter(padinfo)
680 {
681 }
682
683 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
684 {
685 const auto field_size = ScopedPadder::count_digits(msg.thread_id);
686 ScopedPadder p(field_size, padinfo_, dest);
688 }
689 };
690
691 // Current pid
692 template <typename ScopedPadder>
693 class pid_formatter final : public flag_formatter
694 {
695 public:
696 explicit pid_formatter(padding_info padinfo)
697 : flag_formatter(padinfo)
698 {
699 }
700
701 void format(const details::log_msg&, const std::tm&, memory_buf_t& dest) override
702 {
703 const auto pid = static_cast<uint32_t>(details::os::pid());
704 auto field_size = ScopedPadder::count_digits(pid);
705 ScopedPadder p(field_size, padinfo_, dest);
706 fmt_helper::append_int(pid, dest);
707 }
708 };
709
710 template <typename ScopedPadder>
711 class v_formatter final : public flag_formatter
712 {
713 public:
714 explicit v_formatter(padding_info padinfo)
715 : flag_formatter(padinfo)
716 {
717 }
718
719 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
720 {
721 ScopedPadder p(msg.payload.size(), padinfo_, dest);
723 }
724 };
725
726 class ch_formatter final : public flag_formatter
727 {
728 public:
729 explicit ch_formatter(char ch)
730 : ch_(ch)
731 {
732 }
733
734 void format(const details::log_msg&, const std::tm&, memory_buf_t& dest) override
735 {
736 dest.push_back(ch_);
737 }
738
739 private:
740 char ch_;
741 };
742
743 // aggregate user chars to display as is
745 {
746 public:
748
749 void add_ch(char ch)
750 {
751 str_ += ch;
752 }
753 void format(const details::log_msg&, const std::tm&, memory_buf_t& dest) override
754 {
756 }
757
758 private:
759 std::string str_;
760 };
761
762 // mark the color range. expect it to be in the form of "%^colored text%$"
764 {
765 public:
767 : flag_formatter(padinfo)
768 {
769 }
770
771 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
772 {
773 msg.color_range_start = dest.size();
774 }
775 };
776
778 {
779 public:
781 : flag_formatter(padinfo)
782 {
783 }
784
785 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
786 {
787 msg.color_range_end = dest.size();
788 }
789 };
790
791 // print source location
792 template <typename ScopedPadder>
794 {
795 public:
797 : flag_formatter(padinfo)
798 {
799 }
800
801 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
802 {
803 if (msg.source.empty())
804 {
805 ScopedPadder p(0, padinfo_, dest);
806 return;
807 }
808
809 size_t text_size;
810 if (padinfo_.enabled())
811 {
812 // calc text size for padding based on "filename:line"
813 text_size = std::char_traits<char>::length(msg.source.filename) + ScopedPadder::count_digits(msg.source.line) + 1;
814 }
815 else
816 {
817 text_size = 0;
818 }
819
820 ScopedPadder p(text_size, padinfo_, dest);
822 dest.push_back(':');
824 }
825 };
826
827 // print source filename
828 template <typename ScopedPadder>
830 {
831 public:
833 : flag_formatter(padinfo)
834 {
835 }
836
837 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
838 {
839 if (msg.source.empty())
840 {
841 ScopedPadder p(0, padinfo_, dest);
842 return;
843 }
844 size_t text_size = padinfo_.enabled() ? std::char_traits<char>::length(msg.source.filename) : 0;
845 ScopedPadder p(text_size, padinfo_, dest);
847 }
848 };
849
850 template <typename ScopedPadder>
852 {
853 public:
855 : flag_formatter(padinfo)
856 {
857 }
858
859#ifdef _MSC_VER
860#pragma warning(push)
861#pragma warning(disable : 4127) // consider using 'if constexpr' instead
862#endif // _MSC_VER
863 static const char* basename(const char* filename)
864 {
865 // if the size is 2 (1 character + null terminator) we can use the more efficient strrchr
866 // the branch will be elided by optimizations
867 if (sizeof(os::folder_seps) == 2)
868 {
869 const char* rv = std::strrchr(filename, os::folder_seps[0]);
870 return rv != nullptr ? rv + 1 : filename;
871 }
872 else
873 {
874 const std::reverse_iterator<const char*> begin(filename + std::strlen(filename));
875 const std::reverse_iterator<const char*> end(filename);
876
877 const auto it = std::find_first_of(begin, end, std::begin(os::folder_seps), std::end(os::folder_seps) - 1);
878 return it != end ? it.base() : filename;
879 }
880 }
881#ifdef _MSC_VER
882#pragma warning(pop)
883#endif // _MSC_VER
884
885 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
886 {
887 if (msg.source.empty())
888 {
889 ScopedPadder p(0, padinfo_, dest);
890 return;
891 }
892 auto filename = basename(msg.source.filename);
893 size_t text_size = padinfo_.enabled() ? std::char_traits<char>::length(filename) : 0;
894 ScopedPadder p(text_size, padinfo_, dest);
895 fmt_helper::append_string_view(filename, dest);
896 }
897 };
898
899 template <typename ScopedPadder>
901 {
902 public:
904 : flag_formatter(padinfo)
905 {
906 }
907
908 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
909 {
910 if (msg.source.empty())
911 {
912 ScopedPadder p(0, padinfo_, dest);
913 return;
914 }
915
916 auto field_size = ScopedPadder::count_digits(msg.source.line);
917 ScopedPadder p(field_size, padinfo_, dest);
919 }
920 };
921
922 // print source funcname
923 template <typename ScopedPadder>
925 {
926 public:
928 : flag_formatter(padinfo)
929 {
930 }
931
932 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
933 {
934 if (msg.source.empty())
935 {
936 ScopedPadder p(0, padinfo_, dest);
937 return;
938 }
939 size_t text_size = padinfo_.enabled() ? std::char_traits<char>::length(msg.source.funcname) : 0;
940 ScopedPadder p(text_size, padinfo_, dest);
942 }
943 };
944
945 // print elapsed time since last message
946 template <typename ScopedPadder, typename Units>
948 {
949 public:
950 using DurationUnits = Units;
951
954 {
955 }
956
957 void format(const details::log_msg& msg, const std::tm&, memory_buf_t& dest) override
958 {
959 auto delta = (std::max)(msg.time - last_message_time_, log_clock::duration::zero());
960 auto delta_units = std::chrono::duration_cast<DurationUnits>(delta);
962 auto delta_count = static_cast<size_t>(delta_units.count());
963 auto n_digits = static_cast<size_t>(ScopedPadder::count_digits(delta_count));
964 ScopedPadder p(n_digits, padinfo_, dest);
965 fmt_helper::append_int(delta_count, dest);
966 }
967
968 private:
969 log_clock::time_point last_message_time_;
970 };
971
972 // Full info formatter
973 // pattern: [%Y-%m-%d %H:%M:%S.%e] [%n] [%l] [%s:%#] %v
974 class full_formatter final : public flag_formatter
975 {
976 public:
977 explicit full_formatter(padding_info padinfo)
978 : flag_formatter(padinfo)
979 {
980 }
981
982 void format(const details::log_msg& msg, const std::tm& tm_time, memory_buf_t& dest) override
983 {
984 using std::chrono::duration_cast;
985 using std::chrono::milliseconds;
986 using std::chrono::seconds;
987
988 // cache the date/time part for the next second.
989 auto duration = msg.time.time_since_epoch();
990 auto secs = duration_cast<seconds>(duration);
991
992 if (cache_timestamp_ != secs || cached_datetime_.size() == 0)
993 {
994 cached_datetime_.clear();
995 cached_datetime_.push_back('[');
996 fmt_helper::append_int(tm_time.tm_year + 1900, cached_datetime_);
997 cached_datetime_.push_back('-');
998
999 fmt_helper::pad2(tm_time.tm_mon + 1, cached_datetime_);
1000 cached_datetime_.push_back('-');
1001
1002 fmt_helper::pad2(tm_time.tm_mday, cached_datetime_);
1003 cached_datetime_.push_back(' ');
1004
1005 fmt_helper::pad2(tm_time.tm_hour, cached_datetime_);
1006 cached_datetime_.push_back(':');
1007
1008 fmt_helper::pad2(tm_time.tm_min, cached_datetime_);
1009 cached_datetime_.push_back(':');
1010
1011 fmt_helper::pad2(tm_time.tm_sec, cached_datetime_);
1012 cached_datetime_.push_back('.');
1013
1014 cache_timestamp_ = secs;
1015 }
1016 dest.append(cached_datetime_.begin(), cached_datetime_.end());
1017
1018 auto millis = fmt_helper::time_fraction<milliseconds>(msg.time);
1019 fmt_helper::pad3(static_cast<uint32_t>(millis.count()), dest);
1020 dest.push_back(']');
1021 dest.push_back(' ');
1022
1023 // append logger name if exists
1024 if (msg.logger_name.size() > 0)
1025 {
1026 dest.push_back('[');
1028 dest.push_back(']');
1029 dest.push_back(' ');
1030 }
1031
1032 dest.push_back('[');
1033 // wrap the level name with color
1034 msg.color_range_start = dest.size();
1035 // fmt_helper::append_string_view(level::to_c_str(msg.level), dest);
1037 msg.color_range_end = dest.size();
1038 dest.push_back(']');
1039 dest.push_back(' ');
1040
1041 // add source location if present
1042 if (!msg.source.empty())
1043 {
1044 dest.push_back('[');
1046 fmt_helper::append_string_view(filename, dest);
1047 dest.push_back(':');
1049 dest.push_back(']');
1050 dest.push_back(' ');
1051 }
1052 // fmt_helper::append_string_view(msg.msg(), dest);
1054 }
1055
1056 private:
1057 std::chrono::seconds cache_timestamp_{0};
1059 };
1060
1061 } // namespace details
1062
1064 std::string pattern, pattern_time_type time_type, std::string eol, custom_flags custom_user_flags)
1065 : pattern_(std::move(pattern)), eol_(std::move(eol)), pattern_time_type_(time_type), need_localtime_(false), last_log_secs_(0), custom_handlers_(std::move(custom_user_flags))
1066 {
1067 std::memset(&cached_tm_, 0, sizeof(cached_tm_));
1069 }
1070
1071 // use by default full formatter for if pattern is not given
1073 : pattern_("%+"), eol_(std::move(eol)), pattern_time_type_(time_type), need_localtime_(true), last_log_secs_(0)
1074 {
1075 std::memset(&cached_tm_, 0, sizeof(cached_tm_));
1076 formatters_.push_back(details::make_unique<details::full_formatter>(details::padding_info{}));
1077 }
1078
1079 SPDLOG_INLINE std::unique_ptr<formatter> pattern_formatter::clone() const
1080 {
1081 custom_flags cloned_custom_formatters;
1082 for (auto& it : custom_handlers_)
1083 {
1084 cloned_custom_formatters[it.first] = it.second->clone();
1085 }
1086 auto cloned = details::make_unique<pattern_formatter>(pattern_, pattern_time_type_, eol_, std::move(cloned_custom_formatters));
1087 cloned->need_localtime(need_localtime_);
1088#if defined(__GNUC__) && __GNUC__ < 5
1089 return std::move(cloned);
1090#else
1091 return cloned;
1092#endif
1093 }
1094
1096 {
1097 if (need_localtime_)
1098 {
1099 const auto secs = std::chrono::duration_cast<std::chrono::seconds>(msg.time.time_since_epoch());
1100 if (secs != last_log_secs_)
1101 {
1102 cached_tm_ = get_time_(msg);
1103 last_log_secs_ = secs;
1104 }
1105 }
1106
1107 for (auto& f : formatters_)
1108 {
1109 f->format(msg, cached_tm_, dest);
1110 }
1111 // write eol
1113 }
1114
1116 {
1117 pattern_ = std::move(pattern);
1118 need_localtime_ = false;
1120 }
1121
1123 {
1124 need_localtime_ = need;
1125 }
1126
1128 {
1130 {
1131 return details::os::localtime(log_clock::to_time_t(msg.time));
1132 }
1133 return details::os::gmtime(log_clock::to_time_t(msg.time));
1134 }
1135
1136 template <typename Padder>
1138 {
1139 // process custom flags
1140 auto it = custom_handlers_.find(flag);
1141 if (it != custom_handlers_.end())
1142 {
1143 auto custom_handler = it->second->clone();
1144 custom_handler->set_padding_info(padding);
1145 formatters_.push_back(std::move(custom_handler));
1146 return;
1147 }
1148
1149 // process built-in flags
1150 switch (flag)
1151 {
1152 case ('+'): // default formatter
1153 formatters_.push_back(details::make_unique<details::full_formatter>(padding));
1154 need_localtime_ = true;
1155 break;
1156
1157 case 'n': // logger name
1159 break;
1160
1161 case 'l': // level
1163 break;
1164
1165 case 'L': // short level
1167 break;
1168
1169 case ('t'): // thread id
1171 break;
1172
1173 case ('v'): // the message text
1175 break;
1176
1177 case ('a'): // weekday
1179 need_localtime_ = true;
1180 break;
1181
1182 case ('A'): // short weekday
1184 need_localtime_ = true;
1185 break;
1186
1187 case ('b'):
1188 case ('h'): // month
1190 need_localtime_ = true;
1191 break;
1192
1193 case ('B'): // short month
1195 need_localtime_ = true;
1196 break;
1197
1198 case ('c'): // datetime
1200 need_localtime_ = true;
1201 break;
1202
1203 case ('C'): // year 2 digits
1205 need_localtime_ = true;
1206 break;
1207
1208 case ('Y'): // year 4 digits
1210 need_localtime_ = true;
1211 break;
1212
1213 case ('D'):
1214 case ('x'): // datetime MM/DD/YY
1216 need_localtime_ = true;
1217 break;
1218
1219 case ('m'): // month 1-12
1221 need_localtime_ = true;
1222 break;
1223
1224 case ('d'): // day of month 1-31
1226 need_localtime_ = true;
1227 break;
1228
1229 case ('H'): // hours 24
1231 need_localtime_ = true;
1232 break;
1233
1234 case ('I'): // hours 12
1236 need_localtime_ = true;
1237 break;
1238
1239 case ('M'): // minutes
1241 need_localtime_ = true;
1242 break;
1243
1244 case ('S'): // seconds
1246 need_localtime_ = true;
1247 break;
1248
1249 case ('e'): // milliseconds
1251 break;
1252
1253 case ('f'): // microseconds
1255 break;
1256
1257 case ('F'): // nanoseconds
1259 break;
1260
1261 case ('E'): // seconds since epoch
1263 break;
1264
1265 case ('p'): // am/pm
1267 need_localtime_ = true;
1268 break;
1269
1270 case ('r'): // 12 hour clock 02:55:02 pm
1272 need_localtime_ = true;
1273 break;
1274
1275 case ('R'): // 24-hour HH:MM time
1277 need_localtime_ = true;
1278 break;
1279
1280 case ('T'):
1281 case ('X'): // ISO 8601 time format (HH:MM:SS)
1283 need_localtime_ = true;
1284 break;
1285
1286 case ('z'): // timezone
1288 need_localtime_ = true;
1289 break;
1290
1291 case ('P'): // pid
1293 break;
1294
1295 case ('^'): // color range start
1296 formatters_.push_back(details::make_unique<details::color_start_formatter>(padding));
1297 break;
1298
1299 case ('$'): // color range end
1300 formatters_.push_back(details::make_unique<details::color_stop_formatter>(padding));
1301 break;
1302
1303 case ('@'): // source location (filename:filenumber)
1305 break;
1306
1307 case ('s'): // short source filename - without directory name
1309 break;
1310
1311 case ('g'): // full source filename
1313 break;
1314
1315 case ('#'): // source line number
1317 break;
1318
1319 case ('!'): // source funcname
1321 break;
1322
1323 case ('%'): // % char
1324 formatters_.push_back(details::make_unique<details::ch_formatter>('%'));
1325 break;
1326
1327 case ('u'): // elapsed time since last log message in nanos
1329 break;
1330
1331 case ('i'): // elapsed time since last log message in micros
1333 break;
1334
1335 case ('o'): // elapsed time since last log message in millis
1337 break;
1338
1339 case ('O'): // elapsed time since last log message in seconds
1341 break;
1342
1343 default: // Unknown flag appears as is
1344 auto unknown_flag = details::make_unique<details::aggregate_formatter>();
1345
1346 if (!padding.truncate_)
1347 {
1348 unknown_flag->add_ch('%');
1349 unknown_flag->add_ch(flag);
1350 formatters_.push_back((std::move(unknown_flag)));
1351 }
1352 // fix issue #1617 (prev char was '!' and should have been treated as funcname flag instead of truncating flag)
1353 // spdlog::set_pattern("[%10!] %v") => "[ main] some message"
1354 // spdlog::set_pattern("[%3!!] %v") => "[mai] some message"
1355 else
1356 {
1357 padding.truncate_ = false;
1359 unknown_flag->add_ch(flag);
1360 formatters_.push_back((std::move(unknown_flag)));
1361 }
1362
1363 break;
1364 }
1365 }
1366
1367 // Extract given pad spec (e.g. %8X, %=8X, %-8!X, %8!X, %=8!X, %-8!X, %+8!X)
1368 // Advance the given it pass the end of the padding spec found (if any)
1369 // Return padding.
1370 SPDLOG_INLINE details::padding_info pattern_formatter::handle_padspec_(std::string::const_iterator& it, std::string::const_iterator end)
1371 {
1374 const size_t max_width = 64;
1375 if (it == end)
1376 {
1377 return padding_info{};
1378 }
1379
1380 padding_info::pad_side side;
1381 switch (*it)
1382 {
1383 case '-':
1384 side = padding_info::pad_side::right;
1385 ++it;
1386 break;
1387 case '=':
1388 side = padding_info::pad_side::center;
1389 ++it;
1390 break;
1391 default:
1393 break;
1394 }
1395
1396 if (it == end || !std::isdigit(static_cast<unsigned char>(*it)))
1397 {
1398 return padding_info{}; // no padding if no digit found here
1399 }
1400
1401 auto width = static_cast<size_t>(*it) - '0';
1402 for (++it; it != end && std::isdigit(static_cast<unsigned char>(*it)); ++it)
1403 {
1404 auto digit = static_cast<size_t>(*it) - '0';
1405 width = width * 10 + digit;
1406 }
1407
1408 // search for the optional truncate marker '!'
1409 bool truncate;
1410 if (it != end && *it == '!')
1411 {
1412 truncate = true;
1413 ++it;
1414 }
1415 else
1416 {
1417 truncate = false;
1418 }
1419 return details::padding_info{std::min<size_t>(width, max_width), side, truncate};
1420 }
1421
1423 {
1424 auto end = pattern.end();
1425 std::unique_ptr<details::aggregate_formatter> user_chars;
1426 formatters_.clear();
1427 for (auto it = pattern.begin(); it != end; ++it)
1428 {
1429 if (*it == '%')
1430 {
1431 if (user_chars) // append user chars found so far
1432 {
1433 formatters_.push_back(std::move(user_chars));
1434 }
1435
1436 auto padding = handle_padspec_(++it, end);
1437
1438 if (it != end)
1439 {
1440 if (padding.enabled())
1441 {
1442 handle_flag_<details::scoped_padder>(*it, padding);
1443 }
1444 else
1445 {
1446 handle_flag_<details::null_scoped_padder>(*it, padding);
1447 }
1448 }
1449 else
1450 {
1451 break;
1452 }
1453 }
1454 else // chars not following the % sign should be displayed as is
1455 {
1456 if (!user_chars)
1457 {
1458 user_chars = details::make_unique<details::aggregate_formatter>();
1459 }
1460 user_chars->add_ch(*it);
1461 }
1462 }
1463 if (user_chars) // append raw chars found so far
1464 {
1465 formatters_.push_back(std::move(user_chars));
1466 }
1467 }
1468} // namespace spdlog
Definition pattern_formatter-inl.h:200
A_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:202
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:207
Definition pattern_formatter-inl.h:241
B_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:243
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:248
Definition pattern_formatter-inl.h:292
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:299
C_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:294
Definition pattern_formatter-inl.h:310
D_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:312
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:317
Definition pattern_formatter-inl.h:517
E_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:519
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:524
Definition pattern_formatter-inl.h:498
F_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:500
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:505
Definition pattern_formatter-inl.h:387
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:394
H_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:389
Definition pattern_formatter-inl.h:405
I_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:407
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:412
Definition pattern_formatter-inl.h:423
M_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:425
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:430
Definition pattern_formatter-inl.h:580
R_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:582
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:587
Definition pattern_formatter-inl.h:441
S_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:443
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:448
Definition pattern_formatter-inl.h:601
T_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:603
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:608
Definition pattern_formatter-inl.h:333
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:340
Y_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:335
Definition pattern_formatter-inl.h:180
a_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:182
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:187
Definition pattern_formatter-inl.h:745
std::string str_
Definition pattern_formatter-inl.h:759
void add_ch(char ch)
Definition pattern_formatter-inl.h:749
void format(const details::log_msg &, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:753
Definition pattern_formatter-inl.h:220
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:227
b_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:222
Definition pattern_formatter-inl.h:259
c_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:261
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:266
Definition pattern_formatter-inl.h:727
ch_formatter(char ch)
Definition pattern_formatter-inl.h:729
void format(const details::log_msg &, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:734
char ch_
Definition pattern_formatter-inl.h:740
Definition pattern_formatter-inl.h:764
color_start_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:766
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:771
Definition pattern_formatter-inl.h:778
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:785
color_stop_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:780
Definition pattern_formatter-inl.h:369
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:376
d_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:371
Definition pattern_formatter-inl.h:459
e_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:461
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:466
Definition pattern_formatter-inl.h:948
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:957
log_clock::time_point last_message_time_
Definition pattern_formatter-inl.h:969
Units DurationUnits
Definition pattern_formatter-inl.h:950
elapsed_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:952
Definition pattern_formatter-inl.h:478
f_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:480
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:485
Definition pattern_formatter.h:51
padding_info padinfo_
Definition pattern_formatter.h:62
Definition pattern_formatter-inl.h:975
std::chrono::seconds cache_timestamp_
Definition pattern_formatter-inl.h:1057
memory_buf_t cached_datetime_
Definition pattern_formatter-inl.h:1058
void format(const details::log_msg &msg, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:982
full_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:977
Definition pattern_formatter-inl.h:128
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:135
level_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:130
Definition pattern_formatter-inl.h:351
m_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:353
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:358
Definition pattern_formatter-inl.h:111
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:118
name_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:113
Definition pattern_formatter-inl.h:537
p_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:539
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:544
Definition pattern_formatter-inl.h:694
void format(const details::log_msg &, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:701
pid_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:696
Definition pattern_formatter-inl.h:555
void format(const details::log_msg &, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:562
r_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:557
Definition pattern_formatter-inl.h:40
scoped_padder(size_t wrapped_size, const padding_info &padinfo, memory_buf_t &dest)
Definition pattern_formatter-inl.h:42
static unsigned int count_digits(T n)
Definition pattern_formatter-inl.h:66
string_view_t spaces_
Definition pattern_formatter-inl.h:93
void pad_it(long count)
Definition pattern_formatter-inl.h:85
~scoped_padder()
Definition pattern_formatter-inl.h:71
const padding_info & padinfo_
Definition pattern_formatter-inl.h:90
memory_buf_t & dest_
Definition pattern_formatter-inl.h:91
long remaining_pad_
Definition pattern_formatter-inl.h:92
Definition pattern_formatter-inl.h:852
short_filename_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:854
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:885
static const char * basename(const char *filename)
Definition pattern_formatter-inl.h:863
Definition pattern_formatter-inl.h:146
short_level_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:148
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:153
Definition pattern_formatter-inl.h:830
source_filename_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:832
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:837
Definition pattern_formatter-inl.h:925
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:932
source_funcname_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:927
Definition pattern_formatter-inl.h:901
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:908
source_linenum_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:903
Definition pattern_formatter-inl.h:794
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:801
source_location_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:796
Definition pattern_formatter-inl.h:676
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:683
t_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:678
Definition pattern_formatter-inl.h:712
void format(const details::log_msg &msg, const std::tm &, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:719
v_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:714
Definition pattern_formatter-inl.h:624
z_formatter & operator=(const z_formatter &)=delete
z_formatter(padding_info padinfo)
Definition pattern_formatter-inl.h:626
z_formatter(const z_formatter &)=delete
int get_cached_offset(const log_msg &msg, const std::tm &tm_time)
Definition pattern_formatter-inl.h:661
void format(const details::log_msg &msg, const std::tm &tm_time, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:635
log_clock::time_point last_update_
Definition pattern_formatter-inl.h:658
int offset_minutes_
Definition pattern_formatter-inl.h:659
void compile_pattern_(const std::string &pattern)
Definition pattern_formatter-inl.h:1422
void need_localtime(bool need=true)
Definition pattern_formatter-inl.h:1122
custom_flags custom_handlers_
Definition pattern_formatter.h:111
static details::padding_info handle_padspec_(std::string::const_iterator &it, std::string::const_iterator end)
Definition pattern_formatter-inl.h:1370
std::string eol_
Definition pattern_formatter.h:105
void set_pattern(std::string pattern)
Definition pattern_formatter-inl.h:1115
pattern_time_type pattern_time_type_
Definition pattern_formatter.h:106
std::vector< std::unique_ptr< details::flag_formatter > > formatters_
Definition pattern_formatter.h:110
bool need_localtime_
Definition pattern_formatter.h:107
std::chrono::seconds last_log_secs_
Definition pattern_formatter.h:109
pattern_formatter(std::string pattern, pattern_time_type time_type=pattern_time_type::local, std::string eol=spdlog::details::os::default_eol, custom_flags custom_user_flags=custom_flags())
Definition pattern_formatter-inl.h:1063
std::tm cached_tm_
Definition pattern_formatter.h:108
std::tm get_time_(const details::log_msg &msg)
Definition pattern_formatter-inl.h:1127
std::string pattern_
Definition pattern_formatter.h:104
std::unordered_map< char, std::unique_ptr< custom_flag_formatter > > custom_flags
Definition pattern_formatter.h:81
std::unique_ptr< formatter > clone() const override
Definition pattern_formatter-inl.h:1079
void handle_flag_(char flag, details::padding_info padding)
void format(const details::log_msg &msg, memory_buf_t &dest) override
Definition pattern_formatter-inl.h:1095
#define SPDLOG_INLINE
Definition common.h:47
constexpr auto count() -> size_t
Definition core.h:1538
constexpr auto is_negative(T value) -> bool
Definition format.h:1184
void pad6(T n, memory_buf_t &dest)
Definition fmt_helper.h:141
unsigned int count_digits(T n)
Definition fmt_helper.h:81
void pad3(T n, memory_buf_t &dest)
Definition fmt_helper.h:124
void append_string_view(spdlog::string_view_t view, memory_buf_t &dest)
Definition fmt_helper.h:24
void pad9(T n, memory_buf_t &dest)
Definition fmt_helper.h:147
void pad2(int n, memory_buf_t &dest)
Definition fmt_helper.h:99
void append_int(T n, memory_buf_t &dest)
Definition fmt_helper.h:50
SPDLOG_INLINE int utc_minutes_offset(const std::tm &tm)
Definition os-inl.h:268
SPDLOG_INLINE std::tm localtime() SPDLOG_NOEXCEPT
Definition os-inl.h:102
SPDLOG_INLINE int pid() SPDLOG_NOEXCEPT
Definition os-inl.h:405
SPDLOG_INLINE std::tm gmtime() SPDLOG_NOEXCEPT
Definition os-inl.h:121
std::unique_ptr< T > make_unique(Args &&... args)
Definition common.h:392
SPDLOG_INLINE const string_view_t & to_string_view(spdlog::level::level_enum l) SPDLOG_NOEXCEPT
Definition common-inl.h:25
SPDLOG_INLINE const char * to_short_c_str(spdlog::level::level_enum l) SPDLOG_NOEXCEPT
Definition common-inl.h:30
Definition async.h:26
std::chrono::system_clock log_clock
Definition common.h:135
fmt::basic_string_view< char > string_view_t
Definition common.h:172
pattern_time_type
Definition common.h:289
fmt::basic_memory_buffer< char, 250 > memory_buf_t
Definition common.h:173
Definition uuid.h:926
Definition log_msg.h:14
size_t color_range_end
Definition log_msg.h:29
log_clock::time_point time
Definition log_msg.h:24
string_view_t payload
Definition log_msg.h:32
level::level_enum level
Definition log_msg.h:23
source_loc source
Definition log_msg.h:31
size_t color_range_start
Definition log_msg.h:28
string_view_t logger_name
Definition log_msg.h:22
size_t thread_id
Definition log_msg.h:25
Definition pattern_formatter-inl.h:97
null_scoped_padder(size_t, const padding_info &, memory_buf_t &)
Definition pattern_formatter-inl.h:98
static unsigned int count_digits(T)
Definition pattern_formatter-inl.h:103
Definition pattern_formatter.h:26
bool enabled() const
Definition pattern_formatter.h:40
pad_side side_
Definition pattern_formatter.h:45
bool truncate_
Definition pattern_formatter.h:46
size_t width_
Definition pattern_formatter.h:44
int line
Definition common.h:324
const char * funcname
Definition common.h:325
SPDLOG_CONSTEXPR bool empty() const SPDLOG_NOEXCEPT
Definition common.h:319
const char * filename
Definition common.h:323
annotation details
Definition tag_strings.h:125
p
Definition tag_strings.h:29