blob: 509a9cee1cd88e85bf3ed7389852afe342c3f673 [file] [log] [blame]
// Copyright 2016 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chromeos/components/tether/tether_host_fetcher_impl.h"
#include <memory>
#include <vector>
#include "base/bind.h"
#include "components/cryptauth/fake_remote_device_provider.h"
#include "components/cryptauth/remote_device_test_util.h"
#include "testing/gtest/include/gtest/gtest.h"
namespace chromeos {
namespace tether {
namespace {
const size_t kNumTestDevices = 5;
cryptauth::RemoteDeviceList CreateTestDevices() {
cryptauth::RemoteDeviceList list =
cryptauth::GenerateTestRemoteDevices(kNumTestDevices);
for (auto& remote_device : list)
remote_device.supports_mobile_hotspot = true;
return list;
}
class TestObserver : public TetherHostFetcher::Observer {
public:
TestObserver() = default;
virtual ~TestObserver() = default;
size_t num_updates() { return num_updates_; }
// TetherHostFetcher::Observer:
void OnTetherHostsUpdated() override { ++num_updates_; }
private:
size_t num_updates_ = 0;
};
} // namespace
class TetherHostFetcherImplTest : public testing::Test {
public:
TetherHostFetcherImplTest() : test_devices_(CreateTestDevices()) {}
void SetUp() override {
last_fetched_list_.clear();
last_fetched_single_host_.reset();
fake_remote_device_provider_ =
std::make_unique<cryptauth::FakeRemoteDeviceProvider>();
fake_remote_device_provider_->set_synced_remote_devices(test_devices_);
tether_host_fetcher_ = std::make_unique<TetherHostFetcherImpl>(
fake_remote_device_provider_.get());
test_observer_ = std::make_unique<TestObserver>();
tether_host_fetcher_->AddObserver(test_observer_.get());
}
void OnTetherHostListFetched(const cryptauth::RemoteDeviceList& device_list) {
last_fetched_list_ = device_list;
}
void OnSingleTetherHostFetched(
std::unique_ptr<cryptauth::RemoteDevice> device) {
last_fetched_single_host_ = std::move(device);
}
void VerifyAllTetherHosts(const cryptauth::RemoteDeviceList expected_list) {
tether_host_fetcher_->FetchAllTetherHosts(
base::Bind(&TetherHostFetcherImplTest::OnTetherHostListFetched,
base::Unretained(this)));
EXPECT_EQ(expected_list, last_fetched_list_);
}
void VerifySingleTetherHost(const std::string& device_id,
const cryptauth::RemoteDevice* expected_device) {
tether_host_fetcher_->FetchTetherHost(
device_id,
base::Bind(&TetherHostFetcherImplTest::OnSingleTetherHostFetched,
base::Unretained(this)));
if (expected_device)
EXPECT_EQ(*expected_device, *last_fetched_single_host_);
else
EXPECT_EQ(nullptr, last_fetched_single_host_);
}
const cryptauth::RemoteDeviceList test_devices_;
cryptauth::RemoteDeviceList last_fetched_list_;
std::unique_ptr<cryptauth::RemoteDevice> last_fetched_single_host_;
std::unique_ptr<TestObserver> test_observer_;
std::unique_ptr<cryptauth::FakeRemoteDeviceProvider>
fake_remote_device_provider_;
std::unique_ptr<TetherHostFetcherImpl> tether_host_fetcher_;
private:
DISALLOW_COPY_AND_ASSIGN(TetherHostFetcherImplTest);
};
TEST_F(TetherHostFetcherImplTest, TestHasSyncedTetherHosts) {
EXPECT_TRUE(tether_host_fetcher_->HasSyncedTetherHosts());
EXPECT_EQ(0u, test_observer_->num_updates());
// Update the list of devices to be empty.
fake_remote_device_provider_->set_synced_remote_devices(
cryptauth::RemoteDeviceList());
fake_remote_device_provider_->NotifyObserversDeviceListChanged();
EXPECT_FALSE(tether_host_fetcher_->HasSyncedTetherHosts());
EXPECT_EQ(1u, test_observer_->num_updates());
// Notify that the list has changed, even though it hasn't. There should be no
// update.
fake_remote_device_provider_->NotifyObserversDeviceListChanged();
EXPECT_FALSE(tether_host_fetcher_->HasSyncedTetherHosts());
EXPECT_EQ(1u, test_observer_->num_updates());
// Update the list to include device 0 only.
cryptauth::RemoteDeviceList device_0_list = {test_devices_[0]};
fake_remote_device_provider_->set_synced_remote_devices(device_0_list);
fake_remote_device_provider_->NotifyObserversDeviceListChanged();
EXPECT_TRUE(tether_host_fetcher_->HasSyncedTetherHosts());
EXPECT_EQ(2u, test_observer_->num_updates());
// Notify that the list has changed, even though it hasn't. There should be no
// update.
fake_remote_device_provider_->NotifyObserversDeviceListChanged();
EXPECT_TRUE(tether_host_fetcher_->HasSyncedTetherHosts());
EXPECT_EQ(2u, test_observer_->num_updates());
}
TEST_F(TetherHostFetcherImplTest, TestFetchAllTetherHosts) {
VerifyAllTetherHosts(test_devices_);
// Since none of these devices support mobile data, the list should be empty.
cryptauth::RemoteDeviceList list_without_mobile_support = test_devices_;
for (auto& remote_device : list_without_mobile_support)
remote_device.supports_mobile_hotspot = false;
fake_remote_device_provider_->set_synced_remote_devices(
list_without_mobile_support);
fake_remote_device_provider_->NotifyObserversDeviceListChanged();
VerifyAllTetherHosts(cryptauth::RemoteDeviceList());
// The list contains devices 0, 1, and 2, all of which support mobile data.
cryptauth::RemoteDeviceList smaller_list = {
test_devices_[0], test_devices_[1], test_devices_[2]};
fake_remote_device_provider_->set_synced_remote_devices(smaller_list);
fake_remote_device_provider_->NotifyObserversDeviceListChanged();
VerifyAllTetherHosts(smaller_list);
}
TEST_F(TetherHostFetcherImplTest, TestSingleTetherHost) {
VerifySingleTetherHost(test_devices_[0].GetDeviceId(), &test_devices_[0]);
// Now, set device 0 as the only device. It should still be returned when
// requested.
cryptauth::RemoteDevice device_0 = test_devices_[0];
fake_remote_device_provider_->set_synced_remote_devices(
cryptauth::RemoteDeviceList{device_0});
fake_remote_device_provider_->NotifyObserversDeviceListChanged();
VerifySingleTetherHost(test_devices_[0].GetDeviceId(), &device_0);
// Now, set device 0 as the only device, but remove its mobile data support.
// It should not be returned.
device_0.supports_mobile_hotspot = false;
fake_remote_device_provider_->set_synced_remote_devices(
cryptauth::RemoteDeviceList{device_0});
fake_remote_device_provider_->NotifyObserversDeviceListChanged();
VerifySingleTetherHost(test_devices_[0].GetDeviceId(), nullptr);
// Update the list; now, there are no more devices.
fake_remote_device_provider_->set_synced_remote_devices(
cryptauth::RemoteDeviceList());
fake_remote_device_provider_->NotifyObserversDeviceListChanged();
VerifySingleTetherHost(test_devices_[0].GetDeviceId(), nullptr);
}
TEST_F(TetherHostFetcherImplTest,
TestSingleTetherHost_IdDoesNotCorrespondToDevice) {
VerifySingleTetherHost("nonexistentId", nullptr);
}
} // namespace tether
} // namespace chromeos