1a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley// Copyright 2014 The Chromium OS Authors. All rights reserved.
2a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley// Use of this source code is governed by a BSD-style license that can be
3a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley// found in the LICENSE file.
4a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
59ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko#include <brillo/dbus/exported_property_set.h>
6a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
7a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley#include <string>
8a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley#include <vector>
9a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
10a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley#include <base/bind.h>
11f2418e562d358917b02b53290d5f4b3690d6f5d3Alex Vakulenko#include <base/macros.h>
129ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko#include <brillo/dbus/dbus_object.h>
139ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko#include <brillo/dbus/dbus_object_test_helpers.h>
149ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko#include <brillo/errors/error_codes.h>
15a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley#include <dbus/message.h>
16a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley#include <dbus/property.h>
17a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley#include <dbus/object_path.h>
18a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley#include <dbus/mock_bus.h>
19a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley#include <dbus/mock_exported_object.h>
20a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley#include <gmock/gmock.h>
21a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley#include <gtest/gtest.h>
22a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
23a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyusing ::testing::AnyNumber;
24a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyusing ::testing::Return;
25a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyusing ::testing::Invoke;
26a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyusing ::testing::_;
278667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiuusing ::testing::Unused;
28a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
299ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenkonamespace brillo {
30a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
31a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileynamespace dbus_utils {
32a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
33a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileynamespace {
34a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
35a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kBoolPropName[] = "BoolProp";
36a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kUint8PropName[] = "Uint8Prop";
37a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kInt16PropName[] = "Int16Prop";
38a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kUint16PropName[] = "Uint16Prop";
39a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kInt32PropName[] = "Int32Prop";
40a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kUint32PropName[] = "Uint32Prop";
41a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kInt64PropName[] = "Int64Prop";
42a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kUint64PropName[] = "Uint64Prop";
43a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kDoublePropName[] = "DoubleProp";
44a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kStringPropName[] = "StringProp";
45a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kPathPropName[] = "PathProp";
46a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kStringListPropName[] = "StringListProp";
47a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kPathListPropName[] = "PathListProp";
48a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kUint8ListPropName[] = "Uint8ListProp";
49a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
50a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kTestInterface1[] = "org.chromium.TestInterface1";
51a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kTestInterface2[] = "org.chromium.TestInterface2";
52a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst char kTestInterface3[] = "org.chromium.TestInterface3";
53a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
54a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst std::string kTestString("lies");
55a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst dbus::ObjectPath kMethodsExportedOnPath(std::string("/export"));
56a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst dbus::ObjectPath kTestObjectPathInit(std::string("/path_init"));
57a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyconst dbus::ObjectPath kTestObjectPathUpdate(std::string("/path_update"));
58a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
59a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}  // namespace
60a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
61a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyclass ExportedPropertySetTest : public ::testing::Test {
62a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley public:
63520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko  struct Properties {
64a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley   public:
65a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ExportedProperty<bool> bool_prop_;
66f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan    ExportedProperty<uint8_t> uint8_prop_;
67f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan    ExportedProperty<int16_t> int16_prop_;
68f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan    ExportedProperty<uint16_t> uint16_prop_;
69f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan    ExportedProperty<int32_t> int32_prop_;
70f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan    ExportedProperty<uint32_t> uint32_prop_;
71f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan    ExportedProperty<int64_t> int64_prop_;
72f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan    ExportedProperty<uint64_t> uint64_prop_;
73a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ExportedProperty<double> double_prop_;
74a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ExportedProperty<std::string> string_prop_;
75a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ExportedProperty<dbus::ObjectPath> path_prop_;
76a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ExportedProperty<std::vector<std::string>> stringlist_prop_;
77a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ExportedProperty<std::vector<dbus::ObjectPath>> pathlist_prop_;
78f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan    ExportedProperty<std::vector<uint8_t>> uint8list_prop_;
79a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
80520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko    Properties(scoped_refptr<dbus::Bus> bus, const dbus::ObjectPath& path)
81520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko        : dbus_object_(nullptr, bus, path) {
82a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley      // The empty string is not a valid value for an ObjectPath.
83a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley      path_prop_.SetValue(kTestObjectPathInit);
84520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      DBusInterface* itf1 = dbus_object_.AddOrGetInterface(kTestInterface1);
85520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      itf1->AddProperty(kBoolPropName, &bool_prop_);
86520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      itf1->AddProperty(kUint8PropName, &uint8_prop_);
87520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      itf1->AddProperty(kInt16PropName, &int16_prop_);
88a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley      // I chose this weird grouping because N=2 is about all the permutations
89a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley      // of GetAll that I want to anticipate.
90520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      DBusInterface* itf2 = dbus_object_.AddOrGetInterface(kTestInterface2);
91520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      itf2->AddProperty(kUint16PropName, &uint16_prop_);
92520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      itf2->AddProperty(kInt32PropName, &int32_prop_);
93520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      DBusInterface* itf3 = dbus_object_.AddOrGetInterface(kTestInterface3);
94520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      itf3->AddProperty(kUint32PropName, &uint32_prop_);
95520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      itf3->AddProperty(kInt64PropName, &int64_prop_);
96520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      itf3->AddProperty(kUint64PropName, &uint64_prop_);
97520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      itf3->AddProperty(kDoublePropName, &double_prop_);
98520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      itf3->AddProperty(kStringPropName, &string_prop_);
99520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      itf3->AddProperty(kPathPropName, &path_prop_);
100520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      itf3->AddProperty(kStringListPropName, &stringlist_prop_);
101520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      itf3->AddProperty(kPathListPropName, &pathlist_prop_);
102520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko      itf3->AddProperty(kUint8ListPropName, &uint8list_prop_);
10390e4ffc22f8eaeb8284b30e22474d77aa1ba1557Alex Vakulenko      dbus_object_.RegisterAsync(
10490e4ffc22f8eaeb8284b30e22474d77aa1ba1557Alex Vakulenko          AsyncEventSequencer::GetDefaultCompletionAction());
105a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    }
106a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    virtual ~Properties() {}
107a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
108520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko    DBusObject dbus_object_;
109a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  };
110a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
111520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko  void SetUp() override {
112a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    dbus::Bus::Options options;
113a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    options.bus_type = dbus::Bus::SYSTEM;
114a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    bus_ = new dbus::MockBus(options);
115a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    // By default, don't worry about threading assertions.
116a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    EXPECT_CALL(*bus_, AssertOnOriginThread()).Times(AnyNumber());
117a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    EXPECT_CALL(*bus_, AssertOnDBusThread()).Times(AnyNumber());
118a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    // Use a mock exported object.
11905d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko    mock_exported_object_ =
12005d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko        new dbus::MockExportedObject(bus_.get(), kMethodsExportedOnPath);
121a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    EXPECT_CALL(*bus_, GetExportedObject(kMethodsExportedOnPath))
122a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley        .Times(1).WillOnce(Return(mock_exported_object_.get()));
123a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
124520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko    EXPECT_CALL(*mock_exported_object_,
125520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko                ExportMethod(dbus::kPropertiesInterface, _, _, _)).Times(3);
126520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko    p_.reset(new Properties(bus_, kMethodsExportedOnPath));
127a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  }
128a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
129520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko  void TearDown() override {
130520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko    EXPECT_CALL(*mock_exported_object_, Unregister()).Times(1);
131a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  }
132a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
133520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko  void AssertMethodReturnsError(dbus::MethodCall* method_call) {
134a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    method_call->SetSerial(123);
135f437e3b367869af7cb5a53153284566164b48a7cAlex Vakulenko    auto response = testing::CallMethod(p_->dbus_object_, method_call);
1364d8501c1f9689c833d38c9087df28b971a6ebe42Alex Vakulenko    ASSERT_EQ(dbus::Message::MESSAGE_ERROR, response->GetMessageType());
137a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  }
138a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
1395e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  std::unique_ptr<dbus::Response> GetPropertyOnInterface(
14005d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko      const std::string& interface_name,
14105d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko      const std::string& property_name) {
142a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    dbus::MethodCall method_call(dbus::kPropertiesInterface,
143a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley                                 dbus::kPropertiesGet);
144a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    method_call.SetSerial(123);
145a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    dbus::MessageWriter writer(&method_call);
146a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    writer.AppendString(interface_name);
147a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    writer.AppendString(property_name);
148f437e3b367869af7cb5a53153284566164b48a7cAlex Vakulenko    return testing::CallMethod(p_->dbus_object_, &method_call);
149a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  }
150a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
1518667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  std::unique_ptr<dbus::Response> SetPropertyOnInterface(
1528667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu      const std::string& interface_name,
1538667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu      const std::string& property_name,
1549ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko      const brillo::Any& value) {
1558667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu    dbus::MethodCall method_call(dbus::kPropertiesInterface,
1568667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu                                 dbus::kPropertiesSet);
1578667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu    method_call.SetSerial(123);
1588667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu    dbus::MessageWriter writer(&method_call);
1598667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu    writer.AppendString(interface_name);
1608667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu    writer.AppendString(property_name);
1618667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu    dbus_utils::AppendValueToWriter(&writer, value);
1628667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu    return testing::CallMethod(p_->dbus_object_, &method_call);
1638667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  }
1648667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
165a4df79e294e678591cb94e09c73ab41a62086492Alex Vakulenko  std::unique_ptr<dbus::Response> last_response_;
166a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  scoped_refptr<dbus::MockBus> bus_;
167a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  scoped_refptr<dbus::MockExportedObject> mock_exported_object_;
168a4df79e294e678591cb94e09c73ab41a62086492Alex Vakulenko  std::unique_ptr<Properties> p_;
169a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley};
170a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
17105d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenkotemplate<typename T>
1728667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiuclass PropertyValidatorObserver {
1738667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu public:
1748667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  PropertyValidatorObserver()
1758667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu      : validate_property_callback_(
1768667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu            base::Bind(&PropertyValidatorObserver::ValidateProperty,
1778667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu                       base::Unretained(this))) {}
1788667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  virtual ~PropertyValidatorObserver() {}
1798667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
1808667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  MOCK_METHOD2_T(ValidateProperty,
1819ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko                 bool(brillo::ErrorPtr* error, const T& value));
1828667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
1839ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko  const base::Callback<bool(brillo::ErrorPtr*, const T&)>&
18405d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko  validate_property_callback() const {
1858667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu    return validate_property_callback_;
1868667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  }
1878667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
1888667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu private:
1899ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko  base::Callback<bool(brillo::ErrorPtr*, const T&)>
1908667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu      validate_property_callback_;
1918667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
1928667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  DISALLOW_COPY_AND_ASSIGN(PropertyValidatorObserver);
1938667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu};
1948667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
195a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, UpdateNotifications) {
196a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  EXPECT_CALL(*mock_exported_object_, SendSignal(_)).Times(14);
197a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->bool_prop_.SetValue(true);
198a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->uint8_prop_.SetValue(1);
199a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->int16_prop_.SetValue(1);
200a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->uint16_prop_.SetValue(1);
201a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->int32_prop_.SetValue(1);
202a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->uint32_prop_.SetValue(1);
203a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->int64_prop_.SetValue(1);
204a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->uint64_prop_.SetValue(1);
205a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->double_prop_.SetValue(1.0);
206a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->string_prop_.SetValue(kTestString);
207a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->path_prop_.SetValue(kTestObjectPathUpdate);
208a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->stringlist_prop_.SetValue({kTestString});
209a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->pathlist_prop_.SetValue({kTestObjectPathUpdate});
210a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->uint8list_prop_.SetValue({1});
211a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
212a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
213a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, UpdateToSameValue) {
214a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  EXPECT_CALL(*mock_exported_object_, SendSignal(_)).Times(1);
215a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->bool_prop_.SetValue(true);
216a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->bool_prop_.SetValue(true);
217a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
218a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
219a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetAllNoArgs) {
220a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MethodCall method_call(dbus::kPropertiesInterface,
221a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley                               dbus::kPropertiesGetAll);
222520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko  AssertMethodReturnsError(&method_call);
223a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
224a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
225a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetAllInvalidInterface) {
22605d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko  dbus::MethodCall method_call(dbus::kPropertiesInterface,
22705d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko                               dbus::kPropertiesGetAll);
228a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  method_call.SetSerial(123);
229a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageWriter writer(&method_call);
230a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  writer.AppendString("org.chromium.BadInterface");
231f437e3b367869af7cb5a53153284566164b48a7cAlex Vakulenko  auto response = testing::CallMethod(p_->dbus_object_, &method_call);
232520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko  dbus::MessageReader response_reader(response.get());
233a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader dict_reader(nullptr);
234a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(response_reader.PopArray(&dict_reader));
235a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  // The response should just be a an empty array, since there are no properties
236a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  // on this interface.  The spec doesn't say much about error conditions here,
237a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  // so I'm going to assume this is a valid implementation.
238a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(dict_reader.HasMoreData());
239a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(response_reader.HasMoreData());
240a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
241a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
242a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetAllExtraArgs) {
243a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MethodCall method_call(dbus::kPropertiesInterface,
244a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley                               dbus::kPropertiesGetAll);
245a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageWriter writer(&method_call);
246a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  writer.AppendString(kTestInterface1);
247a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  writer.AppendString(kTestInterface1);
248520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko  AssertMethodReturnsError(&method_call);
249a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
250a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
251a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetAllCorrectness) {
25205d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko  dbus::MethodCall method_call(dbus::kPropertiesInterface,
25305d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko                               dbus::kPropertiesGetAll);
254a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  method_call.SetSerial(123);
255a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageWriter writer(&method_call);
256a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  writer.AppendString(kTestInterface2);
257f437e3b367869af7cb5a53153284566164b48a7cAlex Vakulenko  auto response = testing::CallMethod(p_->dbus_object_, &method_call);
258520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko  dbus::MessageReader response_reader(response.get());
259a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader dict_reader(nullptr);
260a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader entry_reader(nullptr);
261a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(response_reader.PopArray(&dict_reader));
262a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(dict_reader.PopDictEntry(&entry_reader));
263a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  std::string property_name;
264a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(entry_reader.PopString(&property_name));
265f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan  uint16_t value16;
266f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan  int32_t value32;
267a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  if (property_name.compare(kUint16PropName) == 0) {
268a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ASSERT_TRUE(entry_reader.PopVariantOfUint16(&value16));
269a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ASSERT_FALSE(entry_reader.HasMoreData());
270a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ASSERT_TRUE(dict_reader.PopDictEntry(&entry_reader));
271a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ASSERT_TRUE(entry_reader.PopString(&property_name));
272a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ASSERT_EQ(property_name.compare(kInt32PropName), 0);
273a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ASSERT_TRUE(entry_reader.PopVariantOfInt32(&value32));
274a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  } else {
275a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ASSERT_EQ(property_name.compare(kInt32PropName), 0);
276a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ASSERT_TRUE(entry_reader.PopVariantOfInt32(&value32));
277a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ASSERT_FALSE(entry_reader.HasMoreData());
278a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ASSERT_TRUE(dict_reader.PopDictEntry(&entry_reader));
279a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ASSERT_TRUE(entry_reader.PopString(&property_name));
280a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ASSERT_EQ(property_name.compare(kUint16PropName), 0);
281a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley    ASSERT_TRUE(entry_reader.PopVariantOfUint16(&value16));
282a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  }
283a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(entry_reader.HasMoreData());
284a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(dict_reader.HasMoreData());
285a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(response_reader.HasMoreData());
286a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
287a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
288a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetNoArgs) {
289a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MethodCall method_call(dbus::kPropertiesInterface,
290a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley                               dbus::kPropertiesGet);
291520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko  AssertMethodReturnsError(&method_call);
292a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
293a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
294a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetInvalidInterface) {
295a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MethodCall method_call(dbus::kPropertiesInterface,
296a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley                               dbus::kPropertiesGet);
297a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageWriter writer(&method_call);
298a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  writer.AppendString("org.chromium.BadInterface");
299a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  writer.AppendString(kInt16PropName);
300520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko  AssertMethodReturnsError(&method_call);
301a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
302a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
303a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetBadPropertyName) {
304a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MethodCall method_call(dbus::kPropertiesInterface,
305a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley                               dbus::kPropertiesGet);
306a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageWriter writer(&method_call);
307a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  writer.AppendString(kTestInterface1);
308a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  writer.AppendString("IAmNotAProperty");
309520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko  AssertMethodReturnsError(&method_call);
310a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
311a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
312a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetPropIfMismatch) {
313a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MethodCall method_call(dbus::kPropertiesInterface,
314a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley                               dbus::kPropertiesGet);
315a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageWriter writer(&method_call);
316a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  writer.AppendString(kTestInterface1);
317a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  writer.AppendString(kStringPropName);
318520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko  AssertMethodReturnsError(&method_call);
319a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
320a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
321a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetNoPropertyName) {
322a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MethodCall method_call(dbus::kPropertiesInterface,
323a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley                               dbus::kPropertiesGet);
324a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageWriter writer(&method_call);
325a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  writer.AppendString(kTestInterface1);
326520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko  AssertMethodReturnsError(&method_call);
327a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
328a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
329a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetExtraArgs) {
330a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MethodCall method_call(dbus::kPropertiesInterface,
331a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley                               dbus::kPropertiesGet);
332a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageWriter writer(&method_call);
333a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  writer.AppendString(kTestInterface1);
334a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  writer.AppendString(kBoolPropName);
335a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  writer.AppendString("Extra param");
336520fc150672378db4927d50c7ec569df03a534aeAlex Vakulenko  AssertMethodReturnsError(&method_call);
337a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
338a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
339a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetWorksWithBool) {
3405e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  auto response = GetPropertyOnInterface(kTestInterface1, kBoolPropName);
341a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(response.get());
342a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  bool value;
343a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopVariantOfBool(&value));
344a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
345a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
346a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
347a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetWorksWithUint8) {
3485e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  auto response = GetPropertyOnInterface(kTestInterface1, kUint8PropName);
349a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(response.get());
350f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan  uint8_t value;
351a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopVariantOfByte(&value));
352a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
353a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
354a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
355a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetWorksWithInt16) {
3565e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  auto response = GetPropertyOnInterface(kTestInterface1, kInt16PropName);
357a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(response.get());
358f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan  int16_t value;
359a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopVariantOfInt16(&value));
360a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
361a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
362a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
363a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetWorksWithUint16) {
3645e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  auto response = GetPropertyOnInterface(kTestInterface2, kUint16PropName);
365a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(response.get());
366f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan  uint16_t value;
367a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopVariantOfUint16(&value));
368a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
369a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
370a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
371a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetWorksWithInt32) {
3725e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  auto response = GetPropertyOnInterface(kTestInterface2, kInt32PropName);
373a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(response.get());
374f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan  int32_t value;
375a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopVariantOfInt32(&value));
376a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
377a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
378a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
379a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetWorksWithUint32) {
3805e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  auto response = GetPropertyOnInterface(kTestInterface3, kUint32PropName);
381a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(response.get());
382f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan  uint32_t value;
383a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopVariantOfUint32(&value));
384a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
385a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
386a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
387a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetWorksWithInt64) {
3885e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  auto response = GetPropertyOnInterface(kTestInterface3, kInt64PropName);
389a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(response.get());
390f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan  int64_t value;
391a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopVariantOfInt64(&value));
392a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
393a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
394a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
395a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetWorksWithUint64) {
3965e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  auto response = GetPropertyOnInterface(kTestInterface3, kUint64PropName);
397a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(response.get());
398f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan  uint64_t value;
399a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopVariantOfUint64(&value));
400a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
401a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
402a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
403a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetWorksWithDouble) {
4045e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  auto response = GetPropertyOnInterface(kTestInterface3, kDoublePropName);
405a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(response.get());
406a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  double value;
407a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopVariantOfDouble(&value));
408a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
409a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
410a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
411a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetWorksWithString) {
4125e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  auto response = GetPropertyOnInterface(kTestInterface3, kStringPropName);
413a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(response.get());
414a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  std::string value;
415a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopVariantOfString(&value));
416a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
417a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
418a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
419a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetWorksWithPath) {
4205e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  auto response = GetPropertyOnInterface(kTestInterface3, kPathPropName);
421a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(response.get());
422a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::ObjectPath value;
423a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopVariantOfObjectPath(&value));
424a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
425a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
426a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
427a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetWorksWithStringList) {
4285e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  auto response = GetPropertyOnInterface(kTestInterface3, kStringListPropName);
429a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(response.get());
430a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader variant_reader(nullptr);
431a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  std::vector<std::string> value;
432a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopVariant(&variant_reader));
433a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(variant_reader.PopArrayOfStrings(&value));
434a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(variant_reader.HasMoreData());
435a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
436a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
437a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
438a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetWorksWithPathList) {
4395e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  auto response = GetPropertyOnInterface(kTestInterface3, kPathListPropName);
440a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(response.get());
441a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader variant_reader(nullptr);
442a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  std::vector<dbus::ObjectPath> value;
443a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopVariant(&variant_reader));
444a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(variant_reader.PopArrayOfObjectPaths(&value));
445a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(variant_reader.HasMoreData());
446a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
447a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
448a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
449a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, GetWorksWithUint8List) {
4505e87965baf35a9d219f066de82cc43c946c21b75Alex Vakulenko  auto response = GetPropertyOnInterface(kTestInterface3, kPathListPropName);
451a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(response.get());
452a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader variant_reader(nullptr);
453f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan  const uint8_t* buffer;
454a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  size_t buffer_len;
455a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopVariant(&variant_reader));
456a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  // |buffer| remains under the control of the MessageReader.
457a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(variant_reader.PopArrayOfBytes(&buffer, &buffer_len));
458a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(variant_reader.HasMoreData());
459a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
460a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
461a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
4628667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter QiuTEST_F(ExportedPropertySetTest, SetInvalidInterface) {
46305d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko  auto response = SetPropertyOnInterface(
4649ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko      "BadInterfaceName", kStringPropName, brillo::Any(kTestString));
4658667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_EQ(dbus::Message::MESSAGE_ERROR, response->GetMessageType());
4668667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_EQ(DBUS_ERROR_UNKNOWN_INTERFACE, response->GetErrorName());
4678667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu}
4688667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
4698667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter QiuTEST_F(ExportedPropertySetTest, SetBadPropertyName) {
47005d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko  auto response = SetPropertyOnInterface(
4719ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko      kTestInterface3, "IAmNotAProperty", brillo::Any(kTestString));
4728667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_EQ(dbus::Message::MESSAGE_ERROR, response->GetMessageType());
4738667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_EQ(DBUS_ERROR_UNKNOWN_PROPERTY, response->GetErrorName());
4748667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu}
4758667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
4768667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter QiuTEST_F(ExportedPropertySetTest, SetFailsWithReadOnlyProperty) {
47705d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko  auto response = SetPropertyOnInterface(
4789ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko      kTestInterface3, kStringPropName, brillo::Any(kTestString));
4798667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_EQ(dbus::Message::MESSAGE_ERROR, response->GetMessageType());
4808667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_EQ(DBUS_ERROR_PROPERTY_READ_ONLY, response->GetErrorName());
4818667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu}
4828667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
4838667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter QiuTEST_F(ExportedPropertySetTest, SetFailsWithMismatchedValueType) {
4848667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  p_->string_prop_.SetAccessMode(ExportedPropertyBase::Access::kReadWrite);
48505d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko  auto response = SetPropertyOnInterface(
4869ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko      kTestInterface3, kStringPropName, brillo::Any(true));
4878667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_EQ(dbus::Message::MESSAGE_ERROR, response->GetMessageType());
4888667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_EQ(DBUS_ERROR_INVALID_ARGS, response->GetErrorName());
4898667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu}
4908667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
4918667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiunamespace {
4928667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
4939ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenkobool SetInvalidProperty(brillo::ErrorPtr* error, Unused) {
4949ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko  brillo::Error::AddTo(error, FROM_HERE, errors::dbus::kDomain,
4959ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko                       DBUS_ERROR_INVALID_ARGS, "Invalid value");
49605d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko  return false;
4978667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu}
4988667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
4998667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu}  // namespace
5008667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
5018667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter QiuTEST_F(ExportedPropertySetTest, SetFailsWithValidator) {
5028667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  PropertyValidatorObserver<std::string> property_validator;
5038667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  p_->string_prop_.SetAccessMode(ExportedPropertyBase::Access::kReadWrite);
5048667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  p_->string_prop_.SetValidator(
5058667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu      property_validator.validate_property_callback());
5068667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
5079ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko  brillo::ErrorPtr error = brillo::Error::Create(
5088667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu      FROM_HERE, errors::dbus::kDomain, DBUS_ERROR_INVALID_ARGS, "");
5098667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  EXPECT_CALL(property_validator, ValidateProperty(_, kTestString))
5108667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu      .WillOnce(Invoke(SetInvalidProperty));
51105d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko  auto response = SetPropertyOnInterface(
5129ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko      kTestInterface3, kStringPropName, brillo::Any(kTestString));
5138667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_EQ(dbus::Message::MESSAGE_ERROR, response->GetMessageType());
5148667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_EQ(DBUS_ERROR_INVALID_ARGS, response->GetErrorName());
5158667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu}
5168667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
5178667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter QiuTEST_F(ExportedPropertySetTest, SetWorksWithValidator) {
5188667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  PropertyValidatorObserver<std::string> property_validator;
5198667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  p_->string_prop_.SetAccessMode(ExportedPropertyBase::Access::kReadWrite);
5208667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  p_->string_prop_.SetValidator(
5218667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu      property_validator.validate_property_callback());
5228667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
5238667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  EXPECT_CALL(property_validator, ValidateProperty(_, kTestString))
5248667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu      .WillOnce(Return(true));
52505d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko  auto response = SetPropertyOnInterface(
5269ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko      kTestInterface3, kStringPropName, brillo::Any(kTestString));
5278667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_NE(dbus::Message::MESSAGE_ERROR, response->GetMessageType());
5288667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_EQ(kTestString, p_->string_prop_.value());
5298667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu}
5308667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
5318667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter QiuTEST_F(ExportedPropertySetTest, SetWorksWithSameValue) {
5328667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  PropertyValidatorObserver<std::string> property_validator;
5338667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  p_->string_prop_.SetAccessMode(ExportedPropertyBase::Access::kReadWrite);
5348667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  p_->string_prop_.SetValidator(
5358667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu      property_validator.validate_property_callback());
536f5effe9e46e479e6fdc4f6928da545d48dcd3997Alex Vakulenko  EXPECT_CALL(*mock_exported_object_, SendSignal(_)).Times(1);
5378667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  p_->string_prop_.SetValue(kTestString);
5388667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
5398667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  // No need to validate the value if it is the same as the current one.
5408667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  EXPECT_CALL(property_validator, ValidateProperty(_, _)).Times(0);
54105d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko  auto response = SetPropertyOnInterface(
5429ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko      kTestInterface3, kStringPropName, brillo::Any(kTestString));
5438667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_NE(dbus::Message::MESSAGE_ERROR, response->GetMessageType());
5448667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_EQ(kTestString, p_->string_prop_.value());
5458667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu}
5468667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu
5478667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter QiuTEST_F(ExportedPropertySetTest, SetWorksWithoutValidator) {
5488667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  p_->string_prop_.SetAccessMode(ExportedPropertyBase::Access::kReadWrite);
54905d29044d14a60775ed6c51c75a414eb0cb50347Alex Vakulenko  auto response = SetPropertyOnInterface(
5509ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko      kTestInterface3, kStringPropName, brillo::Any(kTestString));
5518667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_NE(dbus::Message::MESSAGE_ERROR, response->GetMessageType());
5528667f32b1e4bb023a34ec55dbe7fe261ea39f04bPeter Qiu  ASSERT_EQ(kTestString, p_->string_prop_.value());
553a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
554a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
555a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileynamespace {
556a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
557a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wileyvoid VerifySignal(dbus::Signal* signal) {
558a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_NE(signal, nullptr);
559a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  std::string interface_name;
560a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  std::string property_name;
561f2275aedb34a81364c1d7122aebfb8d2b0f134cfBen Chan  uint8_t value;
562a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader reader(signal);
563a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader array_reader(signal);
564a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  dbus::MessageReader dict_reader(signal);
565a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopString(&interface_name));
566a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopArray(&array_reader));
567a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(array_reader.PopDictEntry(&dict_reader));
568a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(dict_reader.PopString(&property_name));
569a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(dict_reader.PopVariantOfByte(&value));
570a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(dict_reader.HasMoreData());
571a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(array_reader.HasMoreData());
572a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.HasMoreData());
573a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  // Read the (empty) list of invalidated property names.
574a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_TRUE(reader.PopArray(&array_reader));
575a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(array_reader.HasMoreData());
576a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_FALSE(reader.HasMoreData());
577a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_EQ(value, 57);
578a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_EQ(property_name, std::string(kUint8PropName));
579a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  ASSERT_EQ(interface_name, std::string(kTestInterface1));
580a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
581a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
582a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}  // namespace
583a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
584a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher WileyTEST_F(ExportedPropertySetTest, SignalsAreParsable) {
585a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  EXPECT_CALL(*mock_exported_object_, SendSignal(_))
586a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley      .Times(1).WillOnce(Invoke(&VerifySignal));
587a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley  p_->uint8_prop_.SetValue(57);
588a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}
589a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
590a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley}  // namespace dbus_utils
591a96e6db630ca976f4ed6e4c8f4d04b0a548c2cf4Christopher Wiley
5929ed0cab99f18acb3570a35e9408f24355f6b8324Alex Vakulenko}  // namespace brillo
593