10d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// Copyright (c) 2012 The Chromium Authors. All rights reserved. 20d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// Use of this source code is governed by a BSD-style license that can be 30d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// found in the LICENSE file. 40d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 50d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#ifndef BASE_JSON_JSON_VALUE_CONVERTER_H_ 60d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#define BASE_JSON_JSON_VALUE_CONVERTER_H_ 70d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 80d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#include <stddef.h> 90d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1094ffa55491333f3dcc701befd0d2652922916d99Luis Hector Chavez#include <memory> 110d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#include <string> 120d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#include <vector> 130d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 140d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#include "base/base_export.h" 150d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#include "base/logging.h" 160d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#include "base/macros.h" 170d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#include "base/memory/scoped_vector.h" 180d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#include "base/stl_util.h" 190d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#include "base/strings/string16.h" 200d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#include "base/strings/string_piece.h" 210d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#include "base/values.h" 220d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 230d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// JSONValueConverter converts a JSON value into a C++ struct in a 240d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// lightweight way. 250d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// 260d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// Usage: 270d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// For real examples, you may want to refer to _unittest.cc file. 280d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// 290d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// Assume that you have a struct like this: 300d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// struct Message { 310d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// int foo; 320d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// std::string bar; 330d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// static void RegisterJSONConverter( 340d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// JSONValueConverter<Message>* converter); 350d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// }; 360d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// 370d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// And you want to parse a json data into this struct. First, you 380d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// need to declare RegisterJSONConverter() method in your struct. 390d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// // static 400d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// void Message::RegisterJSONConverter( 410d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// JSONValueConverter<Message>* converter) { 420d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// converter->RegisterIntField("foo", &Message::foo); 430d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// converter->RegisterStringField("bar", &Message::bar); 440d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// } 450d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// 460d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// Then, you just instantiate your JSONValueConverter of your type and call 470d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// Convert() method. 480d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// Message message; 490d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// JSONValueConverter<Message> converter; 500d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// converter.Convert(json, &message); 510d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// 520d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// Convert() returns false when it fails. Here "fail" means that the value is 530d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// structurally different from expected, such like a string value appears 540d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// for an int field. Do not report failures for missing fields. 550d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// Also note that Convert() will modify the passed |message| even when it 560d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// fails for performance reason. 570d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// 580d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// For nested field, the internal message also has to implement the registration 590d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// method. Then, just use RegisterNestedField() from the containing struct's 600d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// RegisterJSONConverter method. 610d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// struct Nested { 620d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// Message foo; 630d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// static void RegisterJSONConverter(...) { 640d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// ... 650d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// converter->RegisterNestedField("foo", &Nested::foo); 660d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// } 670d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// }; 680d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// 690d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// For repeated field, we just assume ScopedVector for its container 700d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// and you can put RegisterRepeatedInt or some other types. Use 710d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// RegisterRepeatedMessage for nested repeated fields. 720d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// 730d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// Sometimes JSON format uses string representations for other types such 740d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// like enum, timestamp, or URL. You can use RegisterCustomField method 750d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// and specify a function to convert a StringPiece to your type. 760d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// bool ConvertFunc(const StringPiece& s, YourEnum* result) { 770d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// // do something and return true if succeed... 780d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// } 790d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// struct Message { 800d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// YourEnum ye; 810d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// ... 820d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// static void RegisterJSONConverter(...) { 830d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// ... 840d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// converter->RegsiterCustomField<YourEnum>( 850d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// "your_enum", &Message::ye, &ConvertFunc); 860d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// } 870d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko// }; 880d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 890d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkonamespace base { 900d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 910d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <typename StructType> 920d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass JSONValueConverter; 930d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 940d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkonamespace internal { 950d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 960d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate<typename StructType> 970d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass FieldConverterBase { 980d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 990d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko explicit FieldConverterBase(const std::string& path) : field_path_(path) {} 1000d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko virtual ~FieldConverterBase() {} 1010d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko virtual bool ConvertField(const base::Value& value, StructType* obj) 1020d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const = 0; 1030d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const std::string& field_path() const { return field_path_; } 1040d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1050d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko private: 1060d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko std::string field_path_; 1070d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DISALLOW_COPY_AND_ASSIGN(FieldConverterBase); 1080d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 1090d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1100d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <typename FieldType> 1110d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass ValueConverter { 1120d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 1130d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko virtual ~ValueConverter() {} 1140d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko virtual bool Convert(const base::Value& value, FieldType* field) const = 0; 1150d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 1160d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1170d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <typename StructType, typename FieldType> 1180d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass FieldConverter : public FieldConverterBase<StructType> { 1190d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 1200d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko explicit FieldConverter(const std::string& path, 1210d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko FieldType StructType::* field, 1220d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ValueConverter<FieldType>* converter) 1230d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko : FieldConverterBase<StructType>(path), 1240d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_pointer_(field), 1250d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko value_converter_(converter) { 1260d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 1270d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1280d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool ConvertField(const base::Value& value, StructType* dst) const override { 1290d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return value_converter_->Convert(value, &(dst->*field_pointer_)); 1300d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 1310d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1320d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko private: 1330d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko FieldType StructType::* field_pointer_; 13494ffa55491333f3dcc701befd0d2652922916d99Luis Hector Chavez std::unique_ptr<ValueConverter<FieldType>> value_converter_; 1350d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DISALLOW_COPY_AND_ASSIGN(FieldConverter); 1360d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 1370d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1380d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <typename FieldType> 1390d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass BasicValueConverter; 1400d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1410d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <> 1420d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass BASE_EXPORT BasicValueConverter<int> : public ValueConverter<int> { 1430d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 1440d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko BasicValueConverter() {} 1450d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1460d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool Convert(const base::Value& value, int* field) const override; 1470d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1480d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko private: 1490d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DISALLOW_COPY_AND_ASSIGN(BasicValueConverter); 1500d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 1510d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1520d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <> 1530d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass BASE_EXPORT BasicValueConverter<std::string> 1540d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko : public ValueConverter<std::string> { 1550d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 1560d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko BasicValueConverter() {} 1570d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1580d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool Convert(const base::Value& value, std::string* field) const override; 1590d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1600d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko private: 1610d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DISALLOW_COPY_AND_ASSIGN(BasicValueConverter); 1620d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 1630d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1640d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <> 1650d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass BASE_EXPORT BasicValueConverter<string16> 1660d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko : public ValueConverter<string16> { 1670d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 1680d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko BasicValueConverter() {} 1690d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1700d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool Convert(const base::Value& value, string16* field) const override; 1710d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1720d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko private: 1730d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DISALLOW_COPY_AND_ASSIGN(BasicValueConverter); 1740d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 1750d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1760d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <> 1770d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass BASE_EXPORT BasicValueConverter<double> : public ValueConverter<double> { 1780d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 1790d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko BasicValueConverter() {} 1800d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1810d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool Convert(const base::Value& value, double* field) const override; 1820d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1830d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko private: 1840d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DISALLOW_COPY_AND_ASSIGN(BasicValueConverter); 1850d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 1860d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1870d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <> 1880d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass BASE_EXPORT BasicValueConverter<bool> : public ValueConverter<bool> { 1890d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 1900d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko BasicValueConverter() {} 1910d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1920d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool Convert(const base::Value& value, bool* field) const override; 1930d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1940d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko private: 1950d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DISALLOW_COPY_AND_ASSIGN(BasicValueConverter); 1960d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 1970d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 1980d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <typename FieldType> 1990d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass ValueFieldConverter : public ValueConverter<FieldType> { 2000d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 2010d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko typedef bool(*ConvertFunc)(const base::Value* value, FieldType* field); 2020d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2030d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ValueFieldConverter(ConvertFunc convert_func) 2040d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko : convert_func_(convert_func) {} 2050d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2060d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool Convert(const base::Value& value, FieldType* field) const override { 2070d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return convert_func_(&value, field); 2080d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 2090d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2100d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko private: 2110d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ConvertFunc convert_func_; 2120d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2130d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DISALLOW_COPY_AND_ASSIGN(ValueFieldConverter); 2140d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 2150d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2160d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <typename FieldType> 2170d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass CustomFieldConverter : public ValueConverter<FieldType> { 2180d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 2190d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko typedef bool(*ConvertFunc)(const StringPiece& value, FieldType* field); 2200d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2210d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko CustomFieldConverter(ConvertFunc convert_func) 2220d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko : convert_func_(convert_func) {} 2230d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2240d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool Convert(const base::Value& value, FieldType* field) const override { 2250d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko std::string string_value; 2260d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return value.GetAsString(&string_value) && 2270d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko convert_func_(string_value, field); 2280d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 2290d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2300d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko private: 2310d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ConvertFunc convert_func_; 2320d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2330d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DISALLOW_COPY_AND_ASSIGN(CustomFieldConverter); 2340d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 2350d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2360d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <typename NestedType> 2370d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass NestedValueConverter : public ValueConverter<NestedType> { 2380d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 2390d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko NestedValueConverter() {} 2400d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2410d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool Convert(const base::Value& value, NestedType* field) const override { 2420d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return converter_.Convert(value, field); 2430d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 2440d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2450d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko private: 2460d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko JSONValueConverter<NestedType> converter_; 2470d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DISALLOW_COPY_AND_ASSIGN(NestedValueConverter); 2480d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 2490d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2500d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <typename Element> 2510d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass RepeatedValueConverter : public ValueConverter<ScopedVector<Element> > { 2520d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 2530d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko RepeatedValueConverter() {} 2540d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2550d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool Convert(const base::Value& value, 2560d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ScopedVector<Element>* field) const override { 2570d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const base::ListValue* list = NULL; 2580d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko if (!value.GetAsList(&list)) { 2590d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko // The field is not a list. 2600d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return false; 2610d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 2620d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2630d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field->reserve(list->GetSize()); 2640d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko for (size_t i = 0; i < list->GetSize(); ++i) { 2650d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const base::Value* element = NULL; 2660d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko if (!list->Get(i, &element)) 2670d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko continue; 2680d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 26994ffa55491333f3dcc701befd0d2652922916d99Luis Hector Chavez std::unique_ptr<Element> e(new Element); 2700d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko if (basic_converter_.Convert(*element, e.get())) { 2710d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field->push_back(e.release()); 2720d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } else { 2730d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DVLOG(1) << "failure at " << i << "-th element"; 2740d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return false; 2750d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 2760d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 2770d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return true; 2780d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 2790d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2800d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko private: 2810d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko BasicValueConverter<Element> basic_converter_; 2820d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DISALLOW_COPY_AND_ASSIGN(RepeatedValueConverter); 2830d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 2840d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2850d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <typename NestedType> 2860d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass RepeatedMessageConverter 2870d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko : public ValueConverter<ScopedVector<NestedType> > { 2880d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 2890d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko RepeatedMessageConverter() {} 2900d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2910d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool Convert(const base::Value& value, 2920d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ScopedVector<NestedType>* field) const override { 2930d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const base::ListValue* list = NULL; 2940d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko if (!value.GetAsList(&list)) 2950d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return false; 2960d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 2970d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field->reserve(list->GetSize()); 2980d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko for (size_t i = 0; i < list->GetSize(); ++i) { 2990d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const base::Value* element = NULL; 3000d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko if (!list->Get(i, &element)) 3010d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko continue; 3020d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 30394ffa55491333f3dcc701befd0d2652922916d99Luis Hector Chavez std::unique_ptr<NestedType> nested(new NestedType); 3040d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko if (converter_.Convert(*element, nested.get())) { 3050d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field->push_back(nested.release()); 3060d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } else { 3070d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DVLOG(1) << "failure at " << i << "-th element"; 3080d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return false; 3090d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 3100d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 3110d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return true; 3120d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 3130d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3140d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko private: 3150d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko JSONValueConverter<NestedType> converter_; 3160d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DISALLOW_COPY_AND_ASSIGN(RepeatedMessageConverter); 3170d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 3180d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3190d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <typename NestedType> 3200d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass RepeatedCustomValueConverter 3210d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko : public ValueConverter<ScopedVector<NestedType> > { 3220d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 3230d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko typedef bool(*ConvertFunc)(const base::Value* value, NestedType* field); 3240d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3250d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko RepeatedCustomValueConverter(ConvertFunc convert_func) 3260d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko : convert_func_(convert_func) {} 3270d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3280d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool Convert(const base::Value& value, 3290d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ScopedVector<NestedType>* field) const override { 3300d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const base::ListValue* list = NULL; 3310d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko if (!value.GetAsList(&list)) 3320d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return false; 3330d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3340d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field->reserve(list->GetSize()); 3350d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko for (size_t i = 0; i < list->GetSize(); ++i) { 3360d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const base::Value* element = NULL; 3370d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko if (!list->Get(i, &element)) 3380d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko continue; 3390d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 34094ffa55491333f3dcc701befd0d2652922916d99Luis Hector Chavez std::unique_ptr<NestedType> nested(new NestedType); 3410d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko if ((*convert_func_)(element, nested.get())) { 3420d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field->push_back(nested.release()); 3430d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } else { 3440d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DVLOG(1) << "failure at " << i << "-th element"; 3450d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return false; 3460d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 3470d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 3480d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return true; 3490d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 3500d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3510d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko private: 3520d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ConvertFunc convert_func_; 3530d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DISALLOW_COPY_AND_ASSIGN(RepeatedCustomValueConverter); 3540d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 3550d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3560d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3570d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko} // namespace internal 3580d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3590d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkotemplate <class StructType> 3600d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenkoclass JSONValueConverter { 3610d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko public: 3620d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko JSONValueConverter() { 3630d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko StructType::RegisterJSONConverter(this); 3640d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 3650d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3660d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterIntField(const std::string& field_name, 3670d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko int StructType::* field) { 3680d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back(new internal::FieldConverter<StructType, int>( 3690d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, field, new internal::BasicValueConverter<int>)); 3700d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 3710d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3720d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterStringField(const std::string& field_name, 3730d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko std::string StructType::* field) { 3740d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back(new internal::FieldConverter<StructType, std::string>( 3750d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, field, new internal::BasicValueConverter<std::string>)); 3760d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 3770d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3780d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterStringField(const std::string& field_name, 3790d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko string16 StructType::* field) { 3800d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back(new internal::FieldConverter<StructType, string16>( 3810d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, field, new internal::BasicValueConverter<string16>)); 3820d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 3830d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3840d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterBoolField(const std::string& field_name, 3850d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool StructType::* field) { 3860d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back(new internal::FieldConverter<StructType, bool>( 3870d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, field, new internal::BasicValueConverter<bool>)); 3880d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 3890d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3900d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterDoubleField(const std::string& field_name, 3910d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko double StructType::* field) { 3920d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back(new internal::FieldConverter<StructType, double>( 3930d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, field, new internal::BasicValueConverter<double>)); 3940d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 3950d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 3960d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko template <class NestedType> 3970d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterNestedField( 3980d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const std::string& field_name, NestedType StructType::* field) { 3990d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back(new internal::FieldConverter<StructType, NestedType>( 4000d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, 4010d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field, 4020d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko new internal::NestedValueConverter<NestedType>)); 4030d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 4040d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 4050d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko template <typename FieldType> 4060d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterCustomField( 4070d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const std::string& field_name, 4080d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko FieldType StructType::* field, 4090d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool (*convert_func)(const StringPiece&, FieldType*)) { 4100d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back(new internal::FieldConverter<StructType, FieldType>( 4110d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, 4120d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field, 4130d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko new internal::CustomFieldConverter<FieldType>(convert_func))); 4140d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 4150d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 4160d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko template <typename FieldType> 4170d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterCustomValueField( 4180d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const std::string& field_name, 4190d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko FieldType StructType::* field, 4200d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool (*convert_func)(const base::Value*, FieldType*)) { 4210d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back(new internal::FieldConverter<StructType, FieldType>( 4220d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, 4230d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field, 4240d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko new internal::ValueFieldConverter<FieldType>(convert_func))); 4250d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 4260d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 4270d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterRepeatedInt(const std::string& field_name, 4280d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ScopedVector<int> StructType::* field) { 4290d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back( 4300d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko new internal::FieldConverter<StructType, ScopedVector<int> >( 4310d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, field, new internal::RepeatedValueConverter<int>)); 4320d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 4330d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 4340d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterRepeatedString(const std::string& field_name, 4350d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ScopedVector<std::string> StructType::* field) { 4360d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back( 4370d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko new internal::FieldConverter<StructType, ScopedVector<std::string> >( 4380d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, 4390d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field, 4400d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko new internal::RepeatedValueConverter<std::string>)); 4410d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 4420d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 4430d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterRepeatedString(const std::string& field_name, 4440d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ScopedVector<string16> StructType::* field) { 4450d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back( 4460d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko new internal::FieldConverter<StructType, ScopedVector<string16> >( 4470d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, 4480d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field, 4490d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko new internal::RepeatedValueConverter<string16>)); 4500d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 4510d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 4520d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterRepeatedDouble(const std::string& field_name, 4530d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ScopedVector<double> StructType::* field) { 4540d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back( 4550d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko new internal::FieldConverter<StructType, ScopedVector<double> >( 4560d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, field, new internal::RepeatedValueConverter<double>)); 4570d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 4580d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 4590d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterRepeatedBool(const std::string& field_name, 4600d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ScopedVector<bool> StructType::* field) { 4610d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back( 4620d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko new internal::FieldConverter<StructType, ScopedVector<bool> >( 4630d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, field, new internal::RepeatedValueConverter<bool>)); 4640d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 4650d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 4660d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko template <class NestedType> 4670d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterRepeatedCustomValue( 4680d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const std::string& field_name, 4690d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ScopedVector<NestedType> StructType::* field, 4700d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool (*convert_func)(const base::Value*, NestedType*)) { 4710d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back( 4720d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko new internal::FieldConverter<StructType, ScopedVector<NestedType> >( 4730d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, 4740d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field, 4750d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko new internal::RepeatedCustomValueConverter<NestedType>( 4760d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko convert_func))); 4770d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 4780d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 4790d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko template <class NestedType> 4800d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko void RegisterRepeatedMessage(const std::string& field_name, 4810d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ScopedVector<NestedType> StructType::* field) { 4820d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_.push_back( 4830d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko new internal::FieldConverter<StructType, ScopedVector<NestedType> >( 4840d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field_name, 4850d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko field, 4860d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko new internal::RepeatedMessageConverter<NestedType>)); 4870d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 4880d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 4890d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko bool Convert(const base::Value& value, StructType* output) const { 4900d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const DictionaryValue* dictionary_value = NULL; 4910d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko if (!value.GetAsDictionary(&dictionary_value)) 4920d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return false; 4930d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 4940d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko for(size_t i = 0; i < fields_.size(); ++i) { 4950d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const internal::FieldConverterBase<StructType>* field_converter = 4960d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko fields_[i]; 4970d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko const base::Value* field = NULL; 4980d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko if (dictionary_value->Get(field_converter->field_path(), &field)) { 4990d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko if (!field_converter->ConvertField(*field, output)) { 5000d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DVLOG(1) << "failure at field " << field_converter->field_path(); 5010d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return false; 5020d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 5030d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 5040d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 5050d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko return true; 5060d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko } 5070d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 5080d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko private: 5090d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko ScopedVector<internal::FieldConverterBase<StructType> > fields_; 5100d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 5110d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko DISALLOW_COPY_AND_ASSIGN(JSONValueConverter); 5120d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko}; 5130d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 5140d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko} // namespace base 5150d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko 5160d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#endif // BASE_JSON_JSON_VALUE_CONVERTER_H_ 517