Skip to content

Commit 1dfdbc6

Browse files
committed
report: refactor JSON writer
- Support non-string entry types - Prefer single-character writes over string writes - Rename the state constants and adjust style to match more common Node.js style PR-URL: #25651 Reviewed-By: Colin Ihrig <cjihrig@gmail.com> Reviewed-By: Matheus Marchini <mat@mmarchini.me> Reviewed-By: Gireesh Punathil <gpunathi@in.ibm.com> Reviewed-By: Beth Griggs <Bethany.Griggs@uk.ibm.com> Reviewed-By: Richard Lau <riclau@uk.ibm.com> Reviewed-By: Michael Dawson <michael_dawson@ca.ibm.com>
1 parent 271126a commit 1dfdbc6

File tree

1 file changed

+59
-42
lines changed

1 file changed

+59
-42
lines changed

src/node_report.h

+59-42
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919
#include <iomanip>
2020
#include <iostream>
2121
#include <sstream>
22+
#include <limits>
2223

2324
#ifdef _WIN32
2425
#include <time.h>
@@ -67,93 +68,109 @@ extern double prog_start_time;
6768
// JSON compiler definitions.
6869
class JSONWriter {
6970
public:
70-
explicit JSONWriter(std::ostream& out)
71-
: out_(out), indent_(0), state_(JSONOBJECT) {}
71+
explicit JSONWriter(std::ostream& out) : out_(out) {}
7272

7373
inline void indent() { indent_ += 2; }
7474
inline void deindent() { indent_ -= 2; }
7575
inline void advance() {
76-
for (int i = 0; i < indent_; i++) out_ << " ";
76+
for (int i = 0; i < indent_; i++) out_ << ' ';
7777
}
7878

7979
inline void json_start() {
80-
if (state_ == JSONVALUE) out_ << ",";
81-
out_ << "\n";
80+
if (state_ == kAfterValue) out_ << ',';
81+
out_ << '\n';
8282
advance();
83-
out_ << "{";
83+
out_ << '{';
8484
indent();
85-
state_ = JSONOBJECT;
85+
state_ = kObjectStart;
8686
}
8787

8888
inline void json_end() {
89-
out_ << "\n";
89+
out_ << '\n';
9090
deindent();
9191
advance();
92-
out_ << "}";
93-
state_ = JSONVALUE;
92+
out_ << '}';
93+
state_ = kAfterValue;
9494
}
9595
template <typename T>
9696
inline void json_objectstart(T key) {
97-
if (state_ == JSONVALUE) out_ << ",";
98-
out_ << "\n";
97+
if (state_ == kAfterValue) out_ << ',';
98+
out_ << '\n';
9999
advance();
100-
out_ << "\"" << key << "\""
101-
<< ": {";
100+
write_string(key);
101+
out_ << ": {";
102102
indent();
103-
state_ = JSONOBJECT;
103+
state_ = kObjectStart;
104104
}
105105

106106
template <typename T>
107107
inline void json_arraystart(T key) {
108-
if (state_ == JSONVALUE) out_ << ",";
109-
out_ << "\n";
108+
if (state_ == kAfterValue) out_ << ',';
109+
out_ << '\n';
110110
advance();
111-
out_ << "\"" << key << "\""
112-
<< ": [";
111+
write_string(key);
112+
out_ << ": [";
113113
indent();
114-
state_ = JSONOBJECT;
114+
state_ = kObjectStart;
115115
}
116116
inline void json_objectend() {
117-
out_ << "\n";
117+
out_ << '\n';
118118
deindent();
119119
advance();
120-
out_ << "}";
121-
state_ = JSONVALUE;
120+
out_ << '}';
121+
state_ = kAfterValue;
122122
}
123123

124124
inline void json_arrayend() {
125-
out_ << "\n";
125+
out_ << '\n';
126126
deindent();
127127
advance();
128-
out_ << "]";
129-
state_ = JSONVALUE;
128+
out_ << ']';
129+
state_ = kAfterValue;
130130
}
131131
template <typename T, typename U>
132-
inline void json_keyvalue(T key, U value) {
133-
if (state_ == JSONVALUE) out_ << ",";
134-
out_ << "\n";
132+
inline void json_keyvalue(const T& key, const U& value) {
133+
if (state_ == kAfterValue) out_ << ',';
134+
out_ << '\n';
135135
advance();
136-
out_ << "\"" << key << "\""
137-
<< ": "
138-
<< "\"";
139-
out_ << EscapeJsonChars(value) << "\"";
140-
state_ = JSONVALUE;
136+
write_string(key);
137+
out_ << ": ";
138+
write_value(value);
139+
state_ = kAfterValue;
141140
}
142141

143142
template <typename U>
144-
inline void json_element(U value) {
145-
if (state_ == JSONVALUE) out_ << ",";
146-
out_ << "\n";
143+
inline void json_element(const U& value) {
144+
if (state_ == kAfterValue) out_ << ',';
145+
out_ << '\n';
147146
advance();
148-
out_ << "\"" << EscapeJsonChars(value) << "\"";
149-
state_ = JSONVALUE;
147+
write_value(value);
148+
state_ = kAfterValue;
150149
}
151150

152151
private:
153-
enum JSONState { JSONOBJECT, JSONVALUE };
152+
template <typename T,
153+
typename test_for_number = typename std::
154+
enable_if<std::numeric_limits<T>::is_specialized, bool>::type>
155+
inline void write_value(T number) {
156+
if (std::is_same<T, bool>::value)
157+
out_ << (number ? "true" : "false");
158+
else
159+
out_ << number;
160+
}
161+
162+
inline void write_value(const char* str) { write_string(str); }
163+
inline void write_value(const std::string& str) { write_string(str); }
164+
165+
inline void write_string(const std::string& str) {
166+
out_ << '"' << EscapeJsonChars(str) << '"';
167+
}
168+
inline void write_string(const char* str) { write_string(std::string(str)); }
169+
170+
enum JSONState { kObjectStart, kAfterValue };
154171
std::ostream& out_;
155-
int indent_;
156-
int state_;
172+
int indent_ = 0;
173+
int state_ = kObjectStart;
157174
};
158175

159176
} // namespace report

0 commit comments

Comments
 (0)