0.6.0
C++ to UML diagram generator based on Clang
Loading...
Searching...
No Matches
progress_indicator.cc
Go to the documentation of this file.
1/**
2 * @file src/common/generators/progress_indicator.cc
3 *
4 * Copyright (c) 2021-2025 Bartek Kryza <bkryza@gmail.com>
5 *
6 * Licensed under the Apache License, Version 2.0 (the "License");
7 * you may not use this file except in compliance with the License.
8 * You may obtain a copy of the License at
9 *
10 * http://www.apache.org/licenses/LICENSE-2.0
11 *
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
17 */
18
19#include "progress_indicator.h"
20#include "inja/inja.hpp"
21
22#include <util/util.h>
23
25
27 : progress_indicator(std::cout)
28{
29}
30
32 : ostream_(ostream)
33{
34 progress_bars_.set_option(indicators::option::HideBarWhenComplete{false});
35}
36
38 const std::string &name, size_t max, indicators::Color /*color*/)
39{
40 inja::json j;
41 j["diagram_name"] = name;
42 j["max"] = max;
43 j["progress"] = 0;
44 j["status"] = "started";
45
47
48 progress_bar_index_.emplace(name, progress_state{0, 0, max});
49
50 progress_bars_mutex_.unlock();
51
52 spdlog::get("json-progress-logger")
53 ->log(spdlog::level::info, "{}", j.dump());
54}
55
57 const std::string &name, size_t max, indicators::Color color)
58{
59 auto postfix_text = max > 0 ? fmt::format("{}/{}", 0, max) : std::string{};
60
61 const auto kBarWidth = 35U;
62 const auto kPrefixTextWidth = 25U;
63
64 auto bar = std::make_shared<indicators::ProgressBar>(
65 indicators::option::Stream{ostream_},
66 indicators::option::BarWidth{kBarWidth},
67 indicators::option::ForegroundColor{color},
68 indicators::option::ShowElapsedTime{true},
69#if _MSC_VER
70 indicators::option::Fill{"="}, indicators::option::Lead{">"},
71#else
72 indicators::option::Fill{"█"}, indicators::option::Lead{"█"},
73#endif
74 indicators::option::Remainder{"-"},
75 indicators::option::PrefixText{
76 fmt::format("{:<25}", util::abbreviate(name, kPrefixTextWidth))},
77 indicators::option::PostfixText{postfix_text});
78
80
81 progress_bars_.push_back(*bar);
82 bars_.push_back(bar);
83 auto bar_index = bars_.size() - 1;
84 progress_bar_index_.emplace(name, progress_state{bar_index, 0, max});
85
86 progress_bars_mutex_.unlock();
87}
88
89void json_logger_progress_indicator::increment(const std::string &name)
90{
91 inja::json j;
92 j["diagram_name"] = name;
93
95
96 if (progress_bar_index_.count(name) == 0) {
97 progress_bars_mutex_.unlock();
98 return;
99 }
100
101 auto &p = progress_bar_index_.at(name);
102
103 j["progress"] = p.progress;
104 j["max"] = p.max;
105 j["status"] = "ongoing";
106
107 p.progress++;
108
109 progress_bars_mutex_.unlock();
110
111 spdlog::get("json-progress-logger")
112 ->log(spdlog::level::info, "{}", j.dump());
113}
114
115void progress_indicator::increment(const std::string &name)
116{
117 const auto kASTTraverseProgressPercent = 95U;
118
120
121 if (progress_bar_index_.count(name) == 0) {
122 progress_bars_mutex_.unlock();
123 return;
124 }
125
126 auto &p = progress_bar_index_.at(name);
127 auto &bar = progress_bars_[p.index];
128
129 p.progress++;
130
131 bar.set_progress((p.progress * kASTTraverseProgressPercent) / p.max);
132 bar.set_option(indicators::option::PostfixText{
133 fmt::format("{}/{}", p.progress, p.max)});
134
135 progress_bars_mutex_.unlock();
136}
137
139{
141
142 for (auto &[name, p] : progress_bar_index_) {
143 progress_bars_[p.index].mark_as_completed();
144 }
145
146 progress_bars_mutex_.unlock();
147}
148
149void json_logger_progress_indicator::complete(const std::string &name)
150{
151 inja::json j;
152 j["diagram_name"] = name;
153
155
156 if (progress_bar_index_.count(name) == 0) {
157 progress_bars_mutex_.unlock();
158 return;
159 }
160
161 auto &p = progress_bar_index_.at(name);
162
163 p.progress = p.max;
164
165 j["progress"] = p.progress;
166 j["max"] = p.max;
167 j["status"] = "completed";
168
169 progress_bars_mutex_.unlock();
170
171 spdlog::get("json-progress-logger")
172 ->log(spdlog::level::info, "{}", j.dump());
173}
174
175void progress_indicator::complete(const std::string &name)
176{
177 const auto kCompleteProgressPercent = 100U;
178
180
181 if (progress_bar_index_.count(name) == 0) {
182 progress_bars_mutex_.unlock();
183 return;
184 }
185
186 auto &p = progress_bar_index_.at(name);
187 auto &bar = progress_bars_[p.index];
188
189 p.progress = p.max;
190
191 bar.set_progress(kCompleteProgressPercent);
192
193#if _MSC_VER
194 const auto postfix_text = fmt::format("{}/{} OK", p.progress, p.max);
195#else
196 const auto postfix_text = fmt::format("{}/{} ✔", p.progress, p.max);
197#endif
198 bar.set_option(indicators::option::PostfixText{postfix_text});
199 bar.set_option(
200 indicators::option::ForegroundColor{indicators::Color::green});
201 bar.mark_as_completed();
202
203 progress_bars_mutex_.unlock();
204}
205
206void json_logger_progress_indicator::fail(const std::string &name)
207{
208 inja::json j;
209 j["diagram_name"] = name;
210
212
213 if (progress_bar_index_.count(name) == 0) {
214 progress_bars_mutex_.unlock();
215 return;
216 }
217 auto &p = progress_bar_index_.at(name);
218
219 j["progress"] = p.progress;
220 j["max"] = p.max;
221 j["status"] = "failed";
222
223 progress_bars_mutex_.unlock();
224
225 spdlog::get("json-progress-logger")
226 ->log(spdlog::level::err, "{}", j.dump());
227}
228
229void progress_indicator::fail(const std::string &name)
230{
232
233 if (progress_bar_index_.count(name) == 0) {
234 progress_bars_mutex_.unlock();
235 return;
236 }
237
238 auto &p = progress_bar_index_.at(name);
239 auto &bar = progress_bars_[p.index];
240
241#if _MSC_VER
242 const auto postfix_text = fmt::format("{}/{} FAILED", p.progress, p.max);
243#else
244 const auto postfix_text = fmt::format("{}/{} ✗", p.progress, p.max);
245#endif
246 bar.set_option(indicators::option::ForegroundColor{indicators::Color::red});
247 bar.set_option(indicators::option::PostfixText{postfix_text});
248 bar.mark_as_completed();
249
250 progress_bars_mutex_.unlock();
251}
252
253} // namespace clanguml::common::generators