Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(281)

Side by Side Diff: base/json/json_writer.cc

Issue 8505033: Allow JSONWriter and JSONValueSerializer to omit binary values when instructed to do so. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Address lint warning. Created 9 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2010 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "base/json/json_writer.h" 5 #include "base/json/json_writer.h"
6 6
7 #include "base/json/string_escape.h" 7 #include "base/json/string_escape.h"
8 #include "base/logging.h" 8 #include "base/logging.h"
9 #include "base/stringprintf.h" 9 #include "base/stringprintf.h"
10 #include "base/string_number_conversions.h" 10 #include "base/string_number_conversions.h"
11 #include "base/values.h" 11 #include "base/values.h"
12 #include "base/utf_string_conversions.h" 12 #include "base/utf_string_conversions.h"
13 13
14 namespace base { 14 namespace base {
15 15
16 #if defined(OS_WIN) 16 #if defined(OS_WIN)
17 static const char kPrettyPrintLineEnding[] = "\r\n"; 17 static const char kPrettyPrintLineEnding[] = "\r\n";
18 #else 18 #else
19 static const char kPrettyPrintLineEnding[] = "\n"; 19 static const char kPrettyPrintLineEnding[] = "\n";
20 #endif 20 #endif
21 21
22 /* static */ 22 /* static */
23 const char* JSONWriter::kEmptyArray = "[]"; 23 const char* JSONWriter::kEmptyArray = "[]";
24 24
25 /* static */ 25 /* static */
26 void JSONWriter::Write(const Value* const node, 26 void JSONWriter::Write(const Value* const node,
27 bool pretty_print, 27 bool pretty_print,
28 std::string* json) { 28 std::string* json) {
29 WriteWithOptionalEscape(node, pretty_print, true, json); 29 Write(node, pretty_print, 0, json);
30 } 30 }
31 31
32 /* static */ 32 /* static */
33 void JSONWriter::WriteWithOptionalEscape(const Value* const node, 33 void JSONWriter::Write(const Value* const node,
34 bool pretty_print, 34 bool pretty_print,
35 bool escape, 35 int options,
36 std::string* json) { 36 std::string* json) {
37 json->clear(); 37 json->clear();
38 // Is there a better way to estimate the size of the output? 38 // Is there a better way to estimate the size of the output?
39 json->reserve(1024); 39 json->reserve(1024);
40 JSONWriter writer(pretty_print, json); 40 JSONWriter writer(pretty_print, json);
41 writer.BuildJSONString(node, 0, escape); 41 bool escape = !(options & OPTIONS_DO_NOT_ESCAPE);
42 bool ignore_binary_values = !!(options & OPTIONS_IGNORE_BINARY_VALUES);
43 writer.BuildJSONString(node, 0, escape, ignore_binary_values);
42 if (pretty_print) 44 if (pretty_print)
43 json->append(kPrettyPrintLineEnding); 45 json->append(kPrettyPrintLineEnding);
44 } 46 }
45 47
46 JSONWriter::JSONWriter(bool pretty_print, std::string* json) 48 JSONWriter::JSONWriter(bool pretty_print, std::string* json)
47 : json_string_(json), 49 : json_string_(json),
48 pretty_print_(pretty_print) { 50 pretty_print_(pretty_print) {
49 DCHECK(json); 51 DCHECK(json);
50 } 52 }
51 53
52 void JSONWriter::BuildJSONString(const Value* const node, 54 void JSONWriter::BuildJSONString(const Value* const node,
53 int depth, 55 int depth,
54 bool escape) { 56 bool escape,
57 bool ignore_binary_values) {
55 switch (node->GetType()) { 58 switch (node->GetType()) {
56 case Value::TYPE_NULL: 59 case Value::TYPE_NULL:
57 json_string_->append("null"); 60 json_string_->append("null");
58 break; 61 break;
59 62
60 case Value::TYPE_BOOLEAN: 63 case Value::TYPE_BOOLEAN:
61 { 64 {
62 bool value; 65 bool value;
63 bool result = node->GetAsBoolean(&value); 66 bool result = node->GetAsBoolean(&value);
64 DCHECK(result); 67 DCHECK(result);
(...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after
115 } 118 }
116 119
117 case Value::TYPE_LIST: 120 case Value::TYPE_LIST:
118 { 121 {
119 json_string_->append("["); 122 json_string_->append("[");
120 if (pretty_print_) 123 if (pretty_print_)
121 json_string_->append(" "); 124 json_string_->append(" ");
122 125
123 const ListValue* list = static_cast<const ListValue*>(node); 126 const ListValue* list = static_cast<const ListValue*>(node);
124 for (size_t i = 0; i < list->GetSize(); ++i) { 127 for (size_t i = 0; i < list->GetSize(); ++i) {
128 Value* value = NULL;
129 bool result = list->Get(i, &value);
130 DCHECK(result);
131
132 if (ignore_binary_values && value->GetType() == Value::TYPE_BINARY) {
133 continue;
134 }
135
125 if (i != 0) { 136 if (i != 0) {
126 json_string_->append(","); 137 json_string_->append(",");
127 if (pretty_print_) 138 if (pretty_print_)
128 json_string_->append(" "); 139 json_string_->append(" ");
129 } 140 }
130 141
131 Value* value = NULL; 142 BuildJSONString(value, depth, escape, ignore_binary_values);
132 bool result = list->Get(i, &value);
133 DCHECK(result);
134 BuildJSONString(value, depth, escape);
135 } 143 }
136 144
137 if (pretty_print_) 145 if (pretty_print_)
138 json_string_->append(" "); 146 json_string_->append(" ");
139 json_string_->append("]"); 147 json_string_->append("]");
140 break; 148 break;
141 } 149 }
142 150
143 case Value::TYPE_DICTIONARY: 151 case Value::TYPE_DICTIONARY:
144 { 152 {
145 json_string_->append("{"); 153 json_string_->append("{");
146 if (pretty_print_) 154 if (pretty_print_)
147 json_string_->append(kPrettyPrintLineEnding); 155 json_string_->append(kPrettyPrintLineEnding);
148 156
149 const DictionaryValue* dict = 157 const DictionaryValue* dict =
150 static_cast<const DictionaryValue*>(node); 158 static_cast<const DictionaryValue*>(node);
151 for (DictionaryValue::key_iterator key_itr = dict->begin_keys(); 159 for (DictionaryValue::key_iterator key_itr = dict->begin_keys();
152 key_itr != dict->end_keys(); 160 key_itr != dict->end_keys();
153 ++key_itr) { 161 ++key_itr) {
162 Value* value = NULL;
163 bool result = dict->GetWithoutPathExpansion(*key_itr, &value);
164 DCHECK(result);
165
166 if (ignore_binary_values && value->GetType() == Value::TYPE_BINARY) {
167 continue;
168 }
169
154 if (key_itr != dict->begin_keys()) { 170 if (key_itr != dict->begin_keys()) {
155 json_string_->append(","); 171 json_string_->append(",");
156 if (pretty_print_) 172 if (pretty_print_)
157 json_string_->append(kPrettyPrintLineEnding); 173 json_string_->append(kPrettyPrintLineEnding);
158 } 174 }
159 175
160 Value* value = NULL;
161 bool result = dict->GetWithoutPathExpansion(*key_itr, &value);
162 DCHECK(result);
163
164 if (pretty_print_) 176 if (pretty_print_)
165 IndentLine(depth + 1); 177 IndentLine(depth + 1);
166 AppendQuotedString(*key_itr); 178 AppendQuotedString(*key_itr);
167 if (pretty_print_) { 179 if (pretty_print_) {
168 json_string_->append(": "); 180 json_string_->append(": ");
169 } else { 181 } else {
170 json_string_->append(":"); 182 json_string_->append(":");
171 } 183 }
172 BuildJSONString(value, depth + 1, escape); 184 BuildJSONString(value, depth + 1, escape, ignore_binary_values);
173 } 185 }
174 186
175 if (pretty_print_) { 187 if (pretty_print_) {
176 json_string_->append(kPrettyPrintLineEnding); 188 json_string_->append(kPrettyPrintLineEnding);
177 IndentLine(depth); 189 IndentLine(depth);
178 json_string_->append("}"); 190 json_string_->append("}");
179 } else { 191 } else {
180 json_string_->append("}"); 192 json_string_->append("}");
181 } 193 }
182 break; 194 break;
183 } 195 }
184 196
197 case Value::TYPE_BINARY:
198 {
199 if (!ignore_binary_values) {
200 NOTREACHED() << "Cannot serialize binary value.";
201 }
202 break;
203 }
204
185 default: 205 default:
186 // TODO(jhughes): handle TYPE_BINARY
187 NOTREACHED() << "unknown json type"; 206 NOTREACHED() << "unknown json type";
188 } 207 }
189 } 208 }
190 209
191 void JSONWriter::AppendQuotedString(const std::string& str) { 210 void JSONWriter::AppendQuotedString(const std::string& str) {
192 // TODO(viettrungluu): |str| is UTF-8, not ASCII, so to properly escape it we 211 // TODO(viettrungluu): |str| is UTF-8, not ASCII, so to properly escape it we
193 // have to convert it to UTF-16. This round-trip is suboptimal. 212 // have to convert it to UTF-16. This round-trip is suboptimal.
194 JsonDoubleQuote(UTF8ToUTF16(str), true, json_string_); 213 JsonDoubleQuote(UTF8ToUTF16(str), true, json_string_);
195 } 214 }
196 215
197 void JSONWriter::IndentLine(int depth) { 216 void JSONWriter::IndentLine(int depth) {
198 // It may be faster to keep an indent string so we don't have to keep 217 // It may be faster to keep an indent string so we don't have to keep
199 // reallocating. 218 // reallocating.
200 json_string_->append(std::string(depth * 3, ' ')); 219 json_string_->append(std::string(depth * 3, ' '));
201 } 220 }
202 221
203 } // namespace base 222 } // namespace base
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698