OLD | NEW |
| (Empty) |
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 "chrome/browser/extensions/api/copresence/copresence_api.h" | |
6 | |
7 #include <utility> | |
8 | |
9 #include "base/json/json_writer.h" | |
10 #include "base/memory/ptr_util.h" | |
11 #include "base/values.h" | |
12 #include "chrome/browser/extensions/extension_api_unittest.h" | |
13 #include "chrome/browser/extensions/extension_function_test_utils.h" | |
14 #include "components/copresence/proto/data.pb.h" | |
15 #include "components/copresence/proto/rpcs.pb.h" | |
16 #include "components/copresence/public/copresence_manager.h" | |
17 | |
18 using base::ListValue; | |
19 using copresence::AUDIO_CONFIGURATION_AUDIBLE; | |
20 using copresence::AUDIO_CONFIGURATION_UNKNOWN; | |
21 using copresence::BROADCAST_ONLY; | |
22 using copresence::CopresenceDelegate; | |
23 using copresence::CopresenceManager; | |
24 using copresence::FAIL; | |
25 using copresence::PublishedMessage; | |
26 using copresence::ReportRequest; | |
27 using copresence::SCAN_ONLY; | |
28 using copresence::Subscription; | |
29 using google::protobuf::RepeatedPtrField; | |
30 | |
31 namespace test_utils = extension_function_test_utils; | |
32 | |
33 namespace extensions { | |
34 | |
35 using api::copresence::Message; | |
36 using api::copresence::Operation; | |
37 using api::copresence::PublishOperation; | |
38 using api::copresence::Strategy; | |
39 using api::copresence::SubscribeOperation; | |
40 using api::copresence::UnpublishOperation; | |
41 using api::copresence::UnsubscribeOperation; | |
42 | |
43 | |
44 PublishOperation* CreatePublish(const std::string& id) { | |
45 PublishOperation* publish = new PublishOperation; | |
46 | |
47 publish->id = id; | |
48 publish->time_to_live_millis.reset(new int(1000)); | |
49 publish->message.type = "joke"; | |
50 std::string payload("Knock Knock!"); | |
51 publish->message.payload.assign(payload.begin(), payload.end()); | |
52 | |
53 return publish; | |
54 } | |
55 | |
56 SubscribeOperation* CreateSubscribe(const std::string& id) { | |
57 SubscribeOperation* subscribe = new SubscribeOperation; | |
58 | |
59 subscribe->id = id; | |
60 subscribe->time_to_live_millis.reset(new int(1000)); | |
61 subscribe->filter.type = "joke"; | |
62 | |
63 return subscribe; | |
64 } | |
65 | |
66 template <typename T> | |
67 bool GetOnly(const RepeatedPtrField<T>& things, T* out) { | |
68 if (things.size() != 1) | |
69 return false; | |
70 | |
71 *out = things.Get(0); | |
72 return true; | |
73 } | |
74 | |
75 class FakeCopresenceManager : public CopresenceManager { | |
76 public: | |
77 explicit FakeCopresenceManager(CopresenceDelegate* delegate) | |
78 : delegate_(delegate) {} | |
79 ~FakeCopresenceManager() override {} | |
80 | |
81 // CopresenceManager overrides. | |
82 copresence::CopresenceState* state() override { | |
83 NOTREACHED(); | |
84 return nullptr; | |
85 } | |
86 void ExecuteReportRequest( | |
87 const ReportRequest& request, | |
88 const std::string& app_id, | |
89 const std::string& /* auth_token */, | |
90 const copresence::StatusCallback& status_callback) override { | |
91 request_ = request; | |
92 app_id_ = app_id; | |
93 status_callback.Run(copresence::SUCCESS); | |
94 } | |
95 | |
96 CopresenceDelegate* delegate_; | |
97 | |
98 ReportRequest request_; | |
99 std::string app_id_; | |
100 }; | |
101 | |
102 class CopresenceApiUnittest : public ExtensionApiUnittest { | |
103 public: | |
104 CopresenceApiUnittest() {} | |
105 ~CopresenceApiUnittest() override {} | |
106 | |
107 void SetUp() override { | |
108 ExtensionApiUnittest::SetUp(); | |
109 | |
110 CopresenceService* service = | |
111 CopresenceService::GetFactoryInstance()->Get(profile()); | |
112 copresence_manager_ = new FakeCopresenceManager(service); | |
113 service->set_manager_for_testing( | |
114 base::WrapUnique<CopresenceManager>(copresence_manager_)); | |
115 } | |
116 | |
117 // Takes ownership of the operation_list. | |
118 bool ExecuteOperations(ListValue* operation_list) { | |
119 std::unique_ptr<ListValue> args_list(new ListValue); | |
120 args_list->Append(operation_list); | |
121 | |
122 scoped_refptr<UIThreadExtensionFunction> function = | |
123 new CopresenceExecuteFunction; | |
124 function->set_extension(extension()); | |
125 function->set_browser_context(profile()); | |
126 function->set_has_callback(true); | |
127 test_utils::RunFunction(function.get(), std::move(args_list), browser(), | |
128 test_utils::NONE); | |
129 return function->GetResultList(); | |
130 } | |
131 | |
132 bool ExecuteOperation(std::unique_ptr<Operation> operation) { | |
133 ListValue* operation_list = new ListValue; | |
134 operation_list->Append(operation->ToValue()); | |
135 return ExecuteOperations(operation_list); | |
136 } | |
137 | |
138 const ReportRequest& request_sent() const { | |
139 return copresence_manager_->request_; | |
140 } | |
141 | |
142 const std::string& app_id_sent() const { | |
143 return copresence_manager_->app_id_; | |
144 } | |
145 | |
146 void clear_app_id() { | |
147 copresence_manager_->app_id_.clear(); | |
148 } | |
149 | |
150 CopresenceDelegate* delegate() { | |
151 return copresence_manager_->delegate_; | |
152 } | |
153 | |
154 protected: | |
155 FakeCopresenceManager* copresence_manager_; | |
156 }; | |
157 | |
158 TEST_F(CopresenceApiUnittest, Publish) { | |
159 std::unique_ptr<PublishOperation> publish(CreatePublish("pub")); | |
160 publish->strategies.reset(new Strategy); | |
161 publish->strategies->only_broadcast.reset(new bool(true)); // Default | |
162 | |
163 std::unique_ptr<Operation> operation(new Operation); | |
164 operation->publish = std::move(publish); | |
165 | |
166 clear_app_id(); | |
167 EXPECT_TRUE(ExecuteOperation(std::move(operation))); | |
168 EXPECT_EQ(extension()->id(), app_id_sent()); | |
169 | |
170 PublishedMessage message; | |
171 ASSERT_TRUE(GetOnly( | |
172 request_sent().manage_messages_request().message_to_publish(), &message)); | |
173 EXPECT_EQ("pub", message.id()); | |
174 EXPECT_EQ(1000, message.access_policy().ttl_millis()); | |
175 EXPECT_EQ(copresence::NO_ACL_CHECK, message.access_policy().acl().acl_type()); | |
176 EXPECT_EQ("joke", message.message().type().type()); | |
177 EXPECT_EQ("Knock Knock!", message.message().payload()); | |
178 EXPECT_EQ(BROADCAST_ONLY, | |
179 message.token_exchange_strategy().broadcast_scan_configuration()); | |
180 EXPECT_EQ(AUDIO_CONFIGURATION_UNKNOWN, | |
181 message.token_exchange_strategy().audio_configuration()); | |
182 } | |
183 | |
184 TEST_F(CopresenceApiUnittest, Subscribe) { | |
185 std::unique_ptr<SubscribeOperation> subscribe(CreateSubscribe("sub")); | |
186 subscribe->strategies.reset(new Strategy); | |
187 subscribe->strategies->only_broadcast.reset(new bool(true)); // Not default | |
188 subscribe->strategies->audible.reset(new bool(true)); // Not default | |
189 | |
190 std::unique_ptr<Operation> operation(new Operation); | |
191 operation->subscribe = std::move(subscribe); | |
192 | |
193 clear_app_id(); | |
194 EXPECT_TRUE(ExecuteOperation(std::move(operation))); | |
195 EXPECT_EQ(extension()->id(), app_id_sent()); | |
196 | |
197 Subscription subscription; | |
198 ASSERT_TRUE(GetOnly( | |
199 request_sent().manage_subscriptions_request().subscription(), | |
200 &subscription)); | |
201 EXPECT_EQ("sub", subscription.id()); | |
202 EXPECT_EQ(1000, subscription.ttl_millis()); | |
203 EXPECT_EQ("joke", subscription.message_type().type()); | |
204 copresence::BroadcastScanConfiguration broadcast_scan = | |
205 subscription.token_exchange_strategy().broadcast_scan_configuration(); | |
206 EXPECT_EQ(BROADCAST_ONLY, broadcast_scan); | |
207 EXPECT_EQ(AUDIO_CONFIGURATION_AUDIBLE, | |
208 subscription.token_exchange_strategy().audio_configuration()); | |
209 } | |
210 | |
211 TEST_F(CopresenceApiUnittest, DefaultStrategies) { | |
212 std::unique_ptr<Operation> publish_operation(new Operation); | |
213 publish_operation->publish.reset(CreatePublish("pub")); | |
214 | |
215 std::unique_ptr<Operation> subscribe_operation(new Operation); | |
216 subscribe_operation->subscribe.reset(CreateSubscribe("sub")); | |
217 | |
218 ListValue* operation_list = new ListValue; | |
219 operation_list->Append(publish_operation->ToValue()); | |
220 operation_list->Append(subscribe_operation->ToValue()); | |
221 EXPECT_TRUE(ExecuteOperations(operation_list)); | |
222 | |
223 EXPECT_EQ(BROADCAST_ONLY, | |
224 request_sent().manage_messages_request().message_to_publish(0) | |
225 .token_exchange_strategy().broadcast_scan_configuration()); | |
226 EXPECT_EQ(SCAN_ONLY, | |
227 request_sent().manage_subscriptions_request().subscription(0) | |
228 .token_exchange_strategy().broadcast_scan_configuration()); | |
229 } | |
230 | |
231 TEST_F(CopresenceApiUnittest, LowPowerStrategy) { | |
232 std::unique_ptr<Operation> subscribe_operation(new Operation); | |
233 subscribe_operation->subscribe.reset(CreateSubscribe("sub")); | |
234 subscribe_operation->subscribe->strategies.reset(new Strategy); | |
235 subscribe_operation->subscribe->strategies->low_power.reset(new bool(true)); | |
236 | |
237 ListValue* operation_list = new ListValue; | |
238 operation_list->Append(subscribe_operation->ToValue()); | |
239 EXPECT_TRUE(ExecuteOperations(operation_list)); | |
240 | |
241 EXPECT_EQ(copresence::BROADCAST_SCAN_CONFIGURATION_UNKNOWN, | |
242 request_sent().manage_subscriptions_request().subscription(0) | |
243 .token_exchange_strategy().broadcast_scan_configuration()); | |
244 } | |
245 | |
246 TEST_F(CopresenceApiUnittest, UnPubSub) { | |
247 // First we need to create a publish and a subscribe to cancel. | |
248 std::unique_ptr<Operation> publish_operation(new Operation); | |
249 std::unique_ptr<Operation> subscribe_operation(new Operation); | |
250 publish_operation->publish.reset(CreatePublish("pub")); | |
251 subscribe_operation->subscribe.reset(CreateSubscribe("sub")); | |
252 ListValue* operation_list = new ListValue; | |
253 operation_list->Append(publish_operation->ToValue()); | |
254 operation_list->Append(subscribe_operation->ToValue()); | |
255 EXPECT_TRUE(ExecuteOperations(operation_list)); | |
256 | |
257 std::unique_ptr<Operation> unpublish_operation(new Operation); | |
258 unpublish_operation->unpublish.reset(new UnpublishOperation); | |
259 unpublish_operation->unpublish->unpublish_id = "pub"; | |
260 | |
261 std::unique_ptr<Operation> unsubscribe_operation(new Operation); | |
262 unsubscribe_operation->unsubscribe.reset(new UnsubscribeOperation); | |
263 unsubscribe_operation->unsubscribe->unsubscribe_id = "sub"; | |
264 | |
265 operation_list = new ListValue; | |
266 operation_list->Append(unpublish_operation->ToValue()); | |
267 operation_list->Append(unsubscribe_operation->ToValue()); | |
268 EXPECT_TRUE(ExecuteOperations(operation_list)); | |
269 | |
270 std::string unpublish_id; | |
271 ASSERT_TRUE(GetOnly( | |
272 request_sent().manage_messages_request().id_to_unpublish(), | |
273 &unpublish_id)); | |
274 EXPECT_EQ("pub", unpublish_id); | |
275 | |
276 std::string unsubscribe_id; | |
277 ASSERT_TRUE(GetOnly( | |
278 request_sent().manage_subscriptions_request().id_to_unsubscribe(), | |
279 &unsubscribe_id)); | |
280 EXPECT_EQ("sub", unsubscribe_id); | |
281 } | |
282 | |
283 TEST_F(CopresenceApiUnittest, BadId) { | |
284 std::unique_ptr<Operation> unsubscribe_operation(new Operation); | |
285 unsubscribe_operation->unsubscribe.reset(new UnsubscribeOperation); | |
286 unsubscribe_operation->unsubscribe->unsubscribe_id = "invalid id"; | |
287 | |
288 EXPECT_FALSE(ExecuteOperation(std::move(unsubscribe_operation))); | |
289 } | |
290 | |
291 TEST_F(CopresenceApiUnittest, MultipleOperations) { | |
292 std::unique_ptr<Operation> multi_operation(new Operation); | |
293 multi_operation->publish.reset(CreatePublish("pub")); | |
294 multi_operation->subscribe.reset(CreateSubscribe("sub")); | |
295 | |
296 EXPECT_FALSE(ExecuteOperation(std::move(multi_operation))); | |
297 } | |
298 | |
299 } // namespace extensions | |
300 | |
301 // TODO(ckehoe): add tests for auth tokens and api key functionality | |
OLD | NEW |