Home | History | Annotate | Download | only in dbus
      1 // Copyright (c) 2012 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 
      5 #include "chrome/browser/chromeos/dbus/service_provider_test_helper.h"
      6 
      7 #include "base/bind.h"
      8 #include "dbus/message.h"
      9 #include "dbus/mock_bus.h"
     10 #include "testing/gmock/include/gmock/gmock.h"
     11 #include "testing/gtest/include/gtest/gtest.h"
     12 #include "third_party/cros_system_api/dbus/service_constants.h"
     13 
     14 using ::testing::_;
     15 using ::testing::AllOf;
     16 using ::testing::Invoke;
     17 using ::testing::ResultOf;
     18 using ::testing::Return;
     19 using ::testing::Unused;
     20 
     21 namespace chromeos {
     22 
     23 ServiceProviderTestHelper::ServiceProviderTestHelper()
     24     : response_received_(false) {
     25 }
     26 
     27 ServiceProviderTestHelper::~ServiceProviderTestHelper() {
     28 }
     29 
     30 void ServiceProviderTestHelper::SetUp(
     31     const std::string& exported_method_name,
     32     CrosDBusService::ServiceProviderInterface* service_provider) {
     33   // Create a mock bus.
     34   dbus::Bus::Options options;
     35   options.bus_type = dbus::Bus::SYSTEM;
     36   mock_bus_ = new dbus::MockBus(options);
     37 
     38   // ShutdownAndBlock() will be called in TearDown().
     39   EXPECT_CALL(*mock_bus_.get(), ShutdownAndBlock()).WillOnce(Return());
     40 
     41   // Create a mock exported object that behaves as
     42   // org.chromium.CrosDBusService.
     43   mock_exported_object_ =
     44       new dbus::MockExportedObject(mock_bus_.get(),
     45                                    dbus::ObjectPath(kLibCrosServicePath));
     46 
     47   // |mock_exported_object_|'s ExportMethod() will use
     48   // |MockExportedObject().
     49   EXPECT_CALL(
     50       *mock_exported_object_.get(),
     51       ExportMethod(kLibCrosServiceInterface, exported_method_name, _, _))
     52       .WillOnce(Invoke(this, &ServiceProviderTestHelper::MockExportMethod));
     53 
     54   // Create a mock object proxy, with which we call a method of
     55   // |mock_exported_object_|.
     56   mock_object_proxy_ =
     57       new dbus::MockObjectProxy(mock_bus_.get(),
     58                                 kLibCrosServiceName,
     59                                 dbus::ObjectPath(kLibCrosServicePath));
     60   // |mock_object_proxy_|'s MockCallMethodAndBlock() will use
     61   // MockCallMethodAndBlock() to return responses.
     62   EXPECT_CALL(*mock_object_proxy_.get(),
     63               MockCallMethodAndBlock(
     64                   AllOf(ResultOf(std::mem_fun(&dbus::MethodCall::GetInterface),
     65                                  kLibCrosServiceInterface),
     66                         ResultOf(std::mem_fun(&dbus::MethodCall::GetMember),
     67                                  exported_method_name)),
     68                   _))
     69       .WillOnce(
     70            Invoke(this, &ServiceProviderTestHelper::MockCallMethodAndBlock));
     71 
     72   service_provider->Start(mock_exported_object_.get());
     73 }
     74 
     75 void ServiceProviderTestHelper::TearDown() {
     76   mock_bus_->ShutdownAndBlock();
     77   mock_exported_object_ = NULL;
     78   mock_object_proxy_ = NULL;
     79   mock_bus_ = NULL;
     80 }
     81 
     82 void ServiceProviderTestHelper::SetUpReturnSignal(
     83     const std::string& interface_name,
     84     const std::string& signal_name,
     85     dbus::ObjectProxy::SignalCallback signal_callback,
     86     dbus::ObjectProxy::OnConnectedCallback on_connected_callback) {
     87   // |mock_exported_object_|'s SendSignal() will use
     88   // MockSendSignal().
     89   EXPECT_CALL(*mock_exported_object_.get(), SendSignal(_))
     90       .WillOnce(Invoke(this, &ServiceProviderTestHelper::MockSendSignal));
     91 
     92   // |mock_object_proxy_|'s ConnectToSignal will use
     93   // MockConnectToSignal().
     94   EXPECT_CALL(*mock_object_proxy_.get(),
     95               ConnectToSignal(interface_name, signal_name, _, _))
     96       .WillOnce(Invoke(this, &ServiceProviderTestHelper::MockConnectToSignal));
     97 
     98   mock_object_proxy_->ConnectToSignal(interface_name, signal_name,
     99                                       signal_callback, on_connected_callback);
    100 }
    101 
    102 scoped_ptr<dbus::Response> ServiceProviderTestHelper::CallMethod(
    103     dbus::MethodCall* method_call) {
    104   return mock_object_proxy_->CallMethodAndBlock(
    105       method_call,
    106       dbus::ObjectProxy::TIMEOUT_USE_DEFAULT);
    107 }
    108 
    109 void ServiceProviderTestHelper::MockExportMethod(
    110     const std::string& interface_name,
    111     const std::string& method_name,
    112     dbus::ExportedObject::MethodCallCallback method_callback,
    113     dbus::ExportedObject::OnExportedCallback on_exported_callback) {
    114   // Tell the call back that the method is exported successfully.
    115   on_exported_callback.Run(interface_name, method_name, true);
    116   // Capture the callback, so we can run this at a later time.
    117   method_callback_ = method_callback;
    118 }
    119 
    120 dbus::Response* ServiceProviderTestHelper::MockCallMethodAndBlock(
    121     dbus::MethodCall* method_call,
    122     Unused) {
    123   // Set the serial number to non-zero, so
    124   // dbus_message_new_method_return() won't emit a warning.
    125   method_call->SetSerial(1);
    126   // Run the callback captured in MockExportMethod(). In addition to returning
    127   // a response that the caller will ignore, this will send a signal, which
    128   // will be received by |on_signal_callback_|.
    129   method_callback_.Run(method_call,
    130                        base::Bind(&ServiceProviderTestHelper::OnResponse,
    131                                   base::Unretained(this)));
    132   // Check for a response.
    133   if (!response_received_)
    134     message_loop_.Run();
    135   // Return response.
    136   return response_.release();
    137 }
    138 
    139 void ServiceProviderTestHelper::MockConnectToSignal(
    140     const std::string& interface_name,
    141     const std::string& signal_name,
    142     dbus::ObjectProxy::SignalCallback signal_callback,
    143     dbus::ObjectProxy::OnConnectedCallback connected_callback) {
    144   // Tell the callback that the object proxy is connected to the signal.
    145   connected_callback.Run(interface_name, signal_name, true);
    146   // Capture the callback, so we can run this at a later time.
    147   on_signal_callback_ = signal_callback;
    148 }
    149 
    150 void ServiceProviderTestHelper::MockSendSignal(dbus::Signal* signal) {
    151   // Run the callback captured in MockConnectToSignal(). This will call
    152   // OnSignalReceived().
    153   on_signal_callback_.Run(signal);
    154 }
    155 
    156 void ServiceProviderTestHelper::OnResponse(
    157     scoped_ptr<dbus::Response> response) {
    158   response_ = response.Pass();
    159   response_received_ = true;
    160   if (message_loop_.is_running())
    161     message_loop_.Quit();
    162 }
    163 
    164 }  // namespace chromeos
    165