Bitcoin ABC 0.30.5
P2P Digital Currency
univalue_write.cpp
Go to the documentation of this file.
1// Copyright 2014 BitPay Inc.
2// Distributed under the MIT software license, see the accompanying
3// file COPYING or https://opensource.org/licenses/mit-license.php.
4
5#include <univalue.h>
6#include <univalue_escapes.h>
7
8#include <cstddef>
9#include <string>
10#include <utility>
11
12namespace {
13struct UniValueStreamWriter {
14 std::string str;
15
16 UniValueStreamWriter() { str.reserve(1024); }
17
18 std::string getString() {
19#if __cplusplus >= 201103L
20 return std::move(str);
21#else
22 std::string ret;
23 std::swap(ret, str);
24 return ret;
25#endif
26 }
27
28 void put(char c) { str.push_back(c); }
29 void put(char c, size_t nFill) { str.append(nFill, c); }
30 void write(const char *s) { str.append(s); }
31 void write(const std::string &s) { str.append(s); }
32
33 void indentStr(unsigned int prettyIndent, unsigned int indentLevel) {
34 put(' ', prettyIndent * indentLevel);
35 }
36
37 void escapeJson(const std::string &inS);
38 void writeAny(unsigned int prettyIndent, unsigned int indentLevel,
39 const UniValue &obj);
40 void writeArray(unsigned int prettyIndent, unsigned int indentLevel,
41 const UniValue &obj);
42 void writeObject(unsigned int prettyIndent, unsigned int indentLevel,
43 const UniValue &obj);
44};
45
46void UniValueStreamWriter::escapeJson(const std::string &inS) {
47 size_t len = inS.length();
48 for (size_t i = 0; i < len; i++) {
49 const char ch = inS[i];
50 const char *const escStr = escapes[uint8_t(ch)];
51
52 if (escStr) {
53 write(escStr);
54 } else {
55 put(ch);
56 }
57 }
58}
59
60void UniValueStreamWriter::writeAny(unsigned int prettyIndent,
61 unsigned int indentLevel,
62 const UniValue &obj) {
63 unsigned int modIndent = indentLevel;
64 if (modIndent == 0) {
65 modIndent = 1;
66 }
67
68 switch (obj.typ) {
69 case UniValue::VNULL:
70 write("null");
71 break;
72 case UniValue::VOBJ:
73 writeObject(prettyIndent, modIndent, obj);
74 break;
75 case UniValue::VARR:
76 writeArray(prettyIndent, modIndent, obj);
77 break;
78 case UniValue::VSTR:
79 put('"');
80 escapeJson(obj.val);
81 put('"');
82 break;
83 case UniValue::VNUM:
84 write(obj.val);
85 break;
86 case UniValue::VBOOL:
87 write(obj.val == "1" ? "true" : "false");
88 break;
89 }
90}
91
92void UniValueStreamWriter::writeArray(unsigned int prettyIndent,
93 unsigned int indentLevel,
94 const UniValue &obj) {
95 put('[');
96 if (prettyIndent) {
97 put('\n');
98 }
99
100 const size_t nValues = obj.values.size();
101 for (size_t i = 0; i < nValues; ++i) {
102 if (prettyIndent) {
103 indentStr(prettyIndent, indentLevel);
104 }
105 writeAny(prettyIndent, indentLevel + 1, obj.values[i]);
106 if (i != nValues - 1) {
107 put(',');
108 }
109 if (prettyIndent) {
110 put('\n');
111 }
112 }
113
114 if (prettyIndent) {
115 indentStr(prettyIndent, indentLevel - 1);
116 }
117 put(']');
118}
119
120void UniValueStreamWriter::writeObject(unsigned int prettyIndent,
121 unsigned int indentLevel,
122 const UniValue &obj) {
123 put('{');
124 if (prettyIndent) {
125 put('\n');
126 }
127
128 // Note: if typ == VOBJ, then keys.size() == values.size() always, so we can
129 // use the non-bounds-checking operator[]() for both keys and values here
130 // safely.
131 const size_t nItems = obj.keys.size();
132 for (size_t i = 0; i < nItems; ++i) {
133 if (prettyIndent) {
134 indentStr(prettyIndent, indentLevel);
135 }
136 put('"');
137 escapeJson(obj.keys[i]);
138 write("\":");
139
140 if (prettyIndent) {
141 put(' ');
142 }
143 writeAny(prettyIndent, indentLevel + 1, obj.values[i]);
144 if (i != nItems - 1) {
145 put(',');
146 }
147 if (prettyIndent) {
148 put('\n');
149 }
150 }
151
152 if (prettyIndent) {
153 indentStr(prettyIndent, indentLevel - 1);
154 }
155 put('}');
156}
157} // namespace
158
159std::string UniValue::write(unsigned int prettyIndent,
160 unsigned int indentLevel) const {
161 UniValueStreamWriter ss;
162 ss.writeAny(prettyIndent, indentLevel, *this);
163 return ss.getString();
164}
UniValue::VType typ
Definition: univalue.h:127
@ VNULL
Definition: univalue.h:30
@ VOBJ
Definition: univalue.h:31
@ VSTR
Definition: univalue.h:33
@ VARR
Definition: univalue.h:32
@ VNUM
Definition: univalue.h:34
@ VBOOL
Definition: univalue.h:35
std::string write(unsigned int prettyIndent=0, unsigned int indentLevel=0) const
std::vector< UniValue > values
Definition: univalue.h:130
std::vector< std::string > keys
Definition: univalue.h:129
std::string val
Definition: univalue.h:128
static const char * escapes[256]