value_builder.h 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113
  1. // Copyright 2013 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. // This file provides a builders for DictionaryValue and ListValue. These
  5. // aren't specific to extensions and could move up to base/ if there's interest
  6. // from other sub-projects.
  7. //
  8. // The pattern is to write:
  9. //
  10. // std::unique_ptr<BuiltType> result(FooBuilder()
  11. // .Set(args)
  12. // .Set(args)
  13. // .Build());
  14. //
  15. // The Build() method invalidates its builder, and returns ownership of the
  16. // built value.
  17. //
  18. // These objects are intended to be used as temporaries rather than stored
  19. // anywhere, so the use of non-const reference parameters is likely to cause
  20. // less confusion than usual.
  21. #ifndef EXTENSIONS_COMMON_VALUE_BUILDER_H_
  22. #define EXTENSIONS_COMMON_VALUE_BUILDER_H_
  23. #include <memory>
  24. #include <string>
  25. #include <utility>
  26. #include "base/strings/string_piece_forward.h"
  27. #include "base/values.h"
  28. namespace extensions {
  29. class DictionaryBuilder {
  30. public:
  31. DictionaryBuilder();
  32. explicit DictionaryBuilder(const base::DictionaryValue& init);
  33. DictionaryBuilder(const DictionaryBuilder&) = delete;
  34. DictionaryBuilder& operator=(const DictionaryBuilder&) = delete;
  35. ~DictionaryBuilder();
  36. // Can only be called once, after which it's invalid to use the builder.
  37. std::unique_ptr<base::DictionaryValue> Build() { return std::move(dict_); }
  38. // Immediately serializes the current state to JSON. Can be called as many
  39. // times as you like.
  40. std::string ToJSON() const;
  41. template <typename T>
  42. DictionaryBuilder& Set(base::StringPiece key, T in_value) {
  43. dict_->SetKey(key, base::Value(in_value));
  44. return *this;
  45. }
  46. // NOTE(devlin): This overload is really just for passing
  47. // std::unique_ptr<base::[SomeTypeOf]Value>, but the argument resolution
  48. // would require us to define a template specialization for each of the value
  49. // types. Just define this; it will fail to compile if <T> is anything but
  50. // a base::Value (or one of its subclasses).
  51. template <typename T>
  52. DictionaryBuilder& Set(base::StringPiece key, std::unique_ptr<T> in_value) {
  53. dict_->SetKey(key, std::move(*in_value));
  54. return *this;
  55. }
  56. private:
  57. std::unique_ptr<base::DictionaryValue> dict_;
  58. };
  59. class ListBuilder {
  60. public:
  61. ListBuilder();
  62. ListBuilder(const ListBuilder&) = delete;
  63. ListBuilder& operator=(const ListBuilder&) = delete;
  64. ~ListBuilder();
  65. // Can only be called once, after which it's invalid to use the builder.
  66. std::unique_ptr<base::ListValue> Build() { return std::move(list_); }
  67. template <typename T>
  68. ListBuilder& Append(T in_value) {
  69. list_->Append(in_value);
  70. return *this;
  71. }
  72. // Utility for appending a collection. Is this templating simplistic? Yes.
  73. // But if it's good enough for the STL, it's good enough for this class.
  74. template <typename InputIt>
  75. ListBuilder& Append(InputIt first, InputIt last) {
  76. for (; first != last; ++first)
  77. list_->Append(*first);
  78. return *this;
  79. }
  80. // See note on DictionaryBuilder::Set().
  81. template <typename T>
  82. ListBuilder& Append(std::unique_ptr<T> in_value) {
  83. list_->Append(std::move(*in_value));
  84. return *this;
  85. }
  86. private:
  87. std::unique_ptr<base::ListValue> list_;
  88. };
  89. } // namespace extensions
  90. #endif // EXTENSIONS_COMMON_VALUE_BUILDER_H_