1 // Copyright 2014 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 "components/pairing/fake_host_pairing_controller.h"
6
7 #include <map>
8 #include <vector>
9
10 #include "base/bind.h"
11 #include "base/logging.h"
12 #include "base/message_loop/message_loop.h"
13 #include "base/rand_util.h"
14 #include "base/strings/string_number_conversions.h"
15 #include "base/strings/string_split.h"
16
17 namespace {
18
19 const int kDefaultAsyncDurationMs = 3000;
20 const size_t kCodeLength = 6;
21
22 } // namespace
23
24 namespace pairing_chromeos {
25
FakeHostPairingController(const std::string & config)26 FakeHostPairingController::FakeHostPairingController(const std::string& config)
27 : current_stage_(STAGE_NONE),
28 enrollment_should_fail_(false),
29 start_after_update_(false) {
30 ApplyConfig(config);
31 AddObserver(this);
32 }
33
~FakeHostPairingController()34 FakeHostPairingController::~FakeHostPairingController() {
35 RemoveObserver(this);
36 }
37
ApplyConfig(const std::string & config)38 void FakeHostPairingController::ApplyConfig(const std::string& config) {
39 typedef std::vector<std::string> Tokens;
40
41 base::StringPairs kv_pairs;
42 CHECK(base::SplitStringIntoKeyValuePairs(config, ':', ',', &kv_pairs))
43 << "Wrong config format.";
44 std::map<std::string, std::string> dict(kv_pairs.begin(), kv_pairs.end());
45
46 if (dict.count("async_duration")) {
47 int ms = 0;
48 CHECK(base::StringToInt(dict["async_duration"], &ms))
49 << "Wrong 'async_duration' format.";
50 async_duration_ = base::TimeDelta::FromMilliseconds(ms);
51 } else {
52 async_duration_ =
53 base::TimeDelta::FromMilliseconds(kDefaultAsyncDurationMs);
54 }
55
56 start_after_update_ = dict["start_after_update"] == "1";
57
58 enrollment_should_fail_ = dict["fail_enrollment"] == "1";
59
60 if (dict.count("code")) {
61 confirmation_code_ = dict["code"];
62 } else {
63 confirmation_code_.clear();
64 for (size_t i = 0; i < kCodeLength; ++i)
65 confirmation_code_.push_back(base::RandInt('0', '9'));
66 }
67 CHECK(confirmation_code_.length() == kCodeLength &&
68 confirmation_code_.find_first_not_of("0123456789") == std::string::npos)
69 << "Wrong 'code' format.";
70
71 device_name_ =
72 dict.count("device_name") ? dict["device_name"] : "Chromebox-01";
73
74 enrollment_domain_ = dict.count("domain") ? dict["domain"] : "example.com";
75 }
76
ChangeStage(Stage new_stage)77 void FakeHostPairingController::ChangeStage(Stage new_stage) {
78 if (current_stage_ == new_stage)
79 return;
80 current_stage_ = new_stage;
81 FOR_EACH_OBSERVER(Observer, observers_, PairingStageChanged(new_stage));
82 }
83
ChangeStageLater(Stage new_stage)84 void FakeHostPairingController::ChangeStageLater(Stage new_stage) {
85 base::MessageLoop::current()->PostDelayedTask(
86 FROM_HERE,
87 base::Bind(&FakeHostPairingController::ChangeStage,
88 base::Unretained(this),
89 new_stage),
90 async_duration_);
91 }
92
AddObserver(Observer * observer)93 void FakeHostPairingController::AddObserver(Observer* observer) {
94 observers_.AddObserver(observer);
95 }
96
RemoveObserver(Observer * observer)97 void FakeHostPairingController::RemoveObserver(Observer* observer) {
98 observers_.RemoveObserver(observer);
99 }
100
GetCurrentStage()101 HostPairingController::Stage FakeHostPairingController::GetCurrentStage() {
102 return current_stage_;
103 }
104
StartPairing()105 void FakeHostPairingController::StartPairing() {
106 CHECK(current_stage_ == STAGE_NONE);
107 if (start_after_update_) {
108 ChangeStage(STAGE_WAITING_FOR_CONTROLLER_AFTER_UPDATE);
109 } else {
110 ChangeStage(STAGE_WAITING_FOR_CONTROLLER);
111 }
112 }
113
GetDeviceName()114 std::string FakeHostPairingController::GetDeviceName() {
115 return device_name_;
116 }
117
GetConfirmationCode()118 std::string FakeHostPairingController::GetConfirmationCode() {
119 CHECK(current_stage_ == STAGE_WAITING_FOR_CODE_CONFIRMATION);
120 return confirmation_code_;
121 }
122
GetEnrollmentDomain()123 std::string FakeHostPairingController::GetEnrollmentDomain() {
124 return enrollment_domain_;
125 }
126
OnUpdateStatusChanged(UpdateStatus update_status)127 void FakeHostPairingController::OnUpdateStatusChanged(
128 UpdateStatus update_status) {
129 }
130
SetEnrollmentComplete(bool success)131 void FakeHostPairingController::SetEnrollmentComplete(bool success) {
132 }
133
PairingStageChanged(Stage new_stage)134 void FakeHostPairingController::PairingStageChanged(Stage new_stage) {
135 switch (new_stage) {
136 case STAGE_WAITING_FOR_CONTROLLER: {
137 ChangeStageLater(STAGE_WAITING_FOR_CODE_CONFIRMATION);
138 break;
139 }
140 case STAGE_WAITING_FOR_CODE_CONFIRMATION: {
141 ChangeStageLater(STAGE_UPDATING);
142 break;
143 }
144 case STAGE_UPDATING: {
145 ChangeStageLater(STAGE_WAITING_FOR_CONTROLLER_AFTER_UPDATE);
146 break;
147 }
148 case STAGE_WAITING_FOR_CONTROLLER_AFTER_UPDATE: {
149 ChangeStageLater(STAGE_WAITING_FOR_CREDENTIALS);
150 break;
151 }
152 case STAGE_WAITING_FOR_CREDENTIALS: {
153 ChangeStageLater(STAGE_ENROLLING);
154 break;
155 }
156 case STAGE_ENROLLING: {
157 if (enrollment_should_fail_) {
158 enrollment_should_fail_ = false;
159 ChangeStageLater(STAGE_ENROLLMENT_ERROR);
160 } else {
161 ChangeStageLater(STAGE_PAIRING_DONE);
162 }
163 break;
164 }
165 case STAGE_ENROLLMENT_ERROR: {
166 ChangeStageLater(STAGE_WAITING_FOR_CONTROLLER_AFTER_UPDATE);
167 break;
168 }
169 case STAGE_PAIRING_DONE: {
170 ChangeStageLater(STAGE_FINISHED);
171 break;
172 }
173 default: { break; }
174 }
175 }
176
ConfigureHost(bool accepted_eula,const std::string & lang,const std::string & timezone,bool send_reports,const std::string & keyboard_layout)177 void FakeHostPairingController::ConfigureHost(
178 bool accepted_eula,
179 const std::string& lang,
180 const std::string& timezone,
181 bool send_reports,
182 const std::string& keyboard_layout) {
183 }
184
EnrollHost(const std::string & auth_token)185 void FakeHostPairingController::EnrollHost(const std::string& auth_token) {
186 }
187
188 } // namespace pairing_chromeos
189