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 <stdint.h>
6 #include <map>
7 #include <string>
8 #include <utility>
9 #include <vector>
10 
11 #include "base/bind.h"
12 #include "base/strings/string_number_conversions.h"
13 #include "base/strings/string_tokenizer.h"
14 #include "base/threading/thread_task_runner_handle.h"
15 #include "google_apis/gcm/engine/gcm_registration_request_handler.h"
16 #include "google_apis/gcm/engine/gcm_request_test_base.h"
17 #include "google_apis/gcm/engine/instance_id_get_token_request_handler.h"
18 #include "google_apis/gcm/monitoring/fake_gcm_stats_recorder.h"
19 #include "net/base/escape.h"
20 #include "net/base/load_flags.h"
21 #include "net/base/net_errors.h"
22 #include "services/network/public/cpp/shared_url_loader_factory.h"
23 
24 namespace gcm {
25 
26 namespace {
27 const uint64_t kAndroidId = 42UL;
28 const char kAppId[] = "TestAppId";
29 const char kProductCategoryForSubtypes[] = "com.chrome.macosx";
30 const char kDeveloperId[] = "Project1";
31 const char kLoginHeader[] = "AidLogin";
32 const char kRegistrationURL[] = "http://foo.bar/register";
33 const uint64_t kSecurityToken = 77UL;
34 const int kGCMVersion = 40;
35 const char kInstanceId[] = "IID1";
36 const char kScope[] = "GCM";
37 
38 }  // namespace
39 
40 class RegistrationRequestTest : public GCMRequestTestBase {
41  public:
42   RegistrationRequestTest();
43   ~RegistrationRequestTest() override;
44 
45   void RegistrationCallback(RegistrationRequest::Status status,
46                             const std::string& registration_id);
47 
48   void OnAboutToCompleteFetch() override;
49 
set_max_retry_count(int max_retry_count)50   void set_max_retry_count(int max_retry_count) {
51     max_retry_count_ = max_retry_count;
52   }
53 
54  protected:
55   int max_retry_count_;
56   RegistrationRequest::Status status_;
57   std::string registration_id_;
58   bool callback_called_;
59   std::map<std::string, std::string> extras_;
60   std::unique_ptr<RegistrationRequest> request_;
61   FakeGCMStatsRecorder recorder_;
62 };
63 
RegistrationRequestTest()64 RegistrationRequestTest::RegistrationRequestTest()
65     : max_retry_count_(2),
66       status_(RegistrationRequest::SUCCESS),
67       callback_called_(false) {}
68 
~RegistrationRequestTest()69 RegistrationRequestTest::~RegistrationRequestTest() {}
70 
RegistrationCallback(RegistrationRequest::Status status,const std::string & registration_id)71 void RegistrationRequestTest::RegistrationCallback(
72     RegistrationRequest::Status status,
73     const std::string& registration_id) {
74   status_ = status;
75   registration_id_ = registration_id;
76   callback_called_ = true;
77 }
78 
OnAboutToCompleteFetch()79 void RegistrationRequestTest::OnAboutToCompleteFetch() {
80   registration_id_.clear();
81   status_ = RegistrationRequest::SUCCESS;
82   callback_called_ = false;
83 }
84 
85 class GCMRegistrationRequestTest : public RegistrationRequestTest {
86  public:
87   GCMRegistrationRequestTest();
88   ~GCMRegistrationRequestTest() override;
89 
90   void CreateRequest(const std::string& sender_ids);
91 };
92 
GCMRegistrationRequestTest()93 GCMRegistrationRequestTest::GCMRegistrationRequestTest() {
94 }
95 
~GCMRegistrationRequestTest()96 GCMRegistrationRequestTest::~GCMRegistrationRequestTest() {
97 }
98 
CreateRequest(const std::string & sender_ids)99 void GCMRegistrationRequestTest::CreateRequest(const std::string& sender_ids) {
100   RegistrationRequest::RequestInfo request_info(kAndroidId, kSecurityToken,
101                                                 kAppId /* category */,
102                                                 std::string() /* subtype */);
103   std::unique_ptr<GCMRegistrationRequestHandler> request_handler(
104       new GCMRegistrationRequestHandler(sender_ids));
105   request_.reset(new RegistrationRequest(
106       GURL(kRegistrationURL), request_info, std::move(request_handler),
107       GetBackoffPolicy(),
108       base::BindOnce(&RegistrationRequestTest::RegistrationCallback,
109                      base::Unretained(this)),
110       max_retry_count_, url_loader_factory(),
111       base::ThreadTaskRunnerHandle::Get(), &recorder_, sender_ids));
112 }
113 
TEST_F(GCMRegistrationRequestTest,RequestSuccessful)114 TEST_F(GCMRegistrationRequestTest, RequestSuccessful) {
115   set_max_retry_count(0);
116   CreateRequest("sender1,sender2");
117   request_->Start();
118 
119   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK, "token=2501");
120   EXPECT_TRUE(callback_called_);
121   EXPECT_EQ(RegistrationRequest::SUCCESS, status_);
122   EXPECT_EQ("2501", registration_id_);
123 }
124 
TEST_F(GCMRegistrationRequestTest,RequestDataAndURL)125 TEST_F(GCMRegistrationRequestTest, RequestDataAndURL) {
126   CreateRequest(kDeveloperId);
127   request_->Start();
128 
129   // Get data sent by request and verify that authorization header was put
130   // together properly.
131   const net::HttpRequestHeaders* headers =
132       GetExtraHeadersForURL(kRegistrationURL);
133   ASSERT_TRUE(headers != nullptr);
134   std::string auth_header;
135   headers->GetHeader(net::HttpRequestHeaders::kAuthorization, &auth_header);
136   base::StringTokenizer auth_tokenizer(auth_header, " :");
137   ASSERT_TRUE(auth_tokenizer.GetNext());
138   EXPECT_EQ(kLoginHeader, auth_tokenizer.token());
139   ASSERT_TRUE(auth_tokenizer.GetNext());
140   EXPECT_EQ(base::NumberToString(kAndroidId), auth_tokenizer.token());
141   ASSERT_TRUE(auth_tokenizer.GetNext());
142   EXPECT_EQ(base::NumberToString(kSecurityToken), auth_tokenizer.token());
143 
144   std::map<std::string, std::string> expected_pairs;
145   expected_pairs["app"] = kAppId;
146   expected_pairs["sender"] = kDeveloperId;
147   expected_pairs["device"] = base::NumberToString(kAndroidId);
148 
149   ASSERT_NO_FATAL_FAILURE(
150       VerifyFetcherUploadDataForURL(kRegistrationURL, &expected_pairs));
151 }
152 
TEST_F(GCMRegistrationRequestTest,RequestRegistrationWithMultipleSenderIds)153 TEST_F(GCMRegistrationRequestTest, RequestRegistrationWithMultipleSenderIds) {
154   CreateRequest("sender1,sender2@gmail.com");
155   request_->Start();
156 
157 
158   // Verify data was formatted properly.
159   std::string upload_data;
160   ASSERT_TRUE(GetUploadDataForURL(kRegistrationURL, &upload_data));
161   base::StringTokenizer data_tokenizer(upload_data, "&=");
162 
163   // Skip all tokens until you hit entry for senders.
164   while (data_tokenizer.GetNext() && data_tokenizer.token() != "sender")
165     continue;
166 
167   ASSERT_TRUE(data_tokenizer.GetNext());
168   std::string senders(net::UnescapeBinaryURLComponent(data_tokenizer.token()));
169   base::StringTokenizer sender_tokenizer(senders, ",");
170   ASSERT_TRUE(sender_tokenizer.GetNext());
171   EXPECT_EQ("sender1", sender_tokenizer.token());
172   ASSERT_TRUE(sender_tokenizer.GetNext());
173   EXPECT_EQ("sender2@gmail.com", sender_tokenizer.token());
174 }
175 
TEST_F(GCMRegistrationRequestTest,ResponseParsing)176 TEST_F(GCMRegistrationRequestTest, ResponseParsing) {
177   CreateRequest("sender1,sender2");
178   request_->Start();
179 
180   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK, "token=2501");
181   EXPECT_TRUE(callback_called_);
182   EXPECT_EQ(RegistrationRequest::SUCCESS, status_);
183   EXPECT_EQ("2501", registration_id_);
184 }
185 
TEST_F(GCMRegistrationRequestTest,ResponseParsingFailed)186 TEST_F(GCMRegistrationRequestTest, ResponseParsingFailed) {
187   CreateRequest("sender1,sender2");
188   request_->Start();
189 
190   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK,
191                                "tok");  // Simulate truncated message.
192   EXPECT_FALSE(callback_called_);
193 
194   // Ensuring a retry happened and succeeds.
195   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK, "token=2501");
196   EXPECT_TRUE(callback_called_);
197   EXPECT_EQ(RegistrationRequest::SUCCESS, status_);
198   EXPECT_EQ("2501", registration_id_);
199 }
200 
TEST_F(GCMRegistrationRequestTest,ResponseHttpStatusNotOK)201 TEST_F(GCMRegistrationRequestTest, ResponseHttpStatusNotOK) {
202   CreateRequest("sender1,sender2");
203   request_->Start();
204 
205   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_UNAUTHORIZED,
206                                "token=2501");
207   EXPECT_FALSE(callback_called_);
208 
209   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK, "token=2501");
210   EXPECT_TRUE(callback_called_);
211   EXPECT_EQ(RegistrationRequest::SUCCESS, status_);
212   EXPECT_EQ("2501", registration_id_);
213 }
214 
TEST_F(GCMRegistrationRequestTest,ResponseMissingRegistrationId)215 TEST_F(GCMRegistrationRequestTest, ResponseMissingRegistrationId) {
216   CreateRequest("sender1,sender2");
217   request_->Start();
218 
219   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK, "");
220   EXPECT_FALSE(callback_called_);
221 
222   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK,
223                                "some error in response");
224   EXPECT_FALSE(callback_called_);
225 
226   // Ensuring a retry happened and succeeds.
227   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK, "token=2501");
228   EXPECT_TRUE(callback_called_);
229   EXPECT_EQ(RegistrationRequest::SUCCESS, status_);
230   EXPECT_EQ("2501", registration_id_);
231 }
232 
TEST_F(GCMRegistrationRequestTest,ResponseDeviceRegistrationError)233 TEST_F(GCMRegistrationRequestTest, ResponseDeviceRegistrationError) {
234   CreateRequest("sender1,sender2");
235   request_->Start();
236 
237   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK,
238                                "Error=PHONE_REGISTRATION_ERROR");
239   EXPECT_FALSE(callback_called_);
240 
241   // Ensuring a retry happened and succeeds.
242   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK, "token=2501");
243   EXPECT_TRUE(callback_called_);
244   EXPECT_EQ(RegistrationRequest::SUCCESS, status_);
245   EXPECT_EQ("2501", registration_id_);
246 }
247 
TEST_F(GCMRegistrationRequestTest,ResponseAuthenticationError)248 TEST_F(GCMRegistrationRequestTest, ResponseAuthenticationError) {
249   CreateRequest("sender1,sender2");
250   request_->Start();
251 
252   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_UNAUTHORIZED,
253                                "Error=AUTHENTICATION_FAILED");
254   EXPECT_FALSE(callback_called_);
255 
256   // Ensuring a retry happened and succeeds.
257   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK, "token=2501");
258   EXPECT_TRUE(callback_called_);
259   EXPECT_EQ(RegistrationRequest::SUCCESS, status_);
260   EXPECT_EQ("2501", registration_id_);
261 }
262 
TEST_F(GCMRegistrationRequestTest,ResponseInternalServerError)263 TEST_F(GCMRegistrationRequestTest, ResponseInternalServerError) {
264   CreateRequest("sender1,sender2");
265   request_->Start();
266 
267   SetResponseForURLAndComplete(kRegistrationURL,
268                                net::HTTP_INTERNAL_SERVER_ERROR,
269                                "Error=InternalServerError");
270   EXPECT_FALSE(callback_called_);
271 
272   // Ensuring a retry happened and succeeds.
273   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK, "token=2501");
274   EXPECT_TRUE(callback_called_);
275   EXPECT_EQ(RegistrationRequest::SUCCESS, status_);
276   EXPECT_EQ("2501", registration_id_);
277 }
278 
TEST_F(GCMRegistrationRequestTest,ResponseInvalidParameters)279 TEST_F(GCMRegistrationRequestTest, ResponseInvalidParameters) {
280   CreateRequest("sender1,sender2");
281   request_->Start();
282 
283   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK,
284                                "Error=INVALID_PARAMETERS");
285   EXPECT_TRUE(callback_called_);
286   EXPECT_EQ(RegistrationRequest::INVALID_PARAMETERS, status_);
287   EXPECT_EQ(std::string(), registration_id_);
288 }
289 
TEST_F(GCMRegistrationRequestTest,ResponseInvalidSender)290 TEST_F(GCMRegistrationRequestTest, ResponseInvalidSender) {
291   CreateRequest("sender1,sender2");
292   request_->Start();
293 
294   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK,
295                                "Error=INVALID_SENDER");
296   EXPECT_TRUE(callback_called_);
297   EXPECT_EQ(RegistrationRequest::INVALID_SENDER, status_);
298   EXPECT_EQ(std::string(), registration_id_);
299 }
300 
TEST_F(GCMRegistrationRequestTest,ResponseInvalidSenderBadRequest)301 TEST_F(GCMRegistrationRequestTest, ResponseInvalidSenderBadRequest) {
302   CreateRequest("sender1");
303   request_->Start();
304 
305   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_BAD_REQUEST,
306                                "Error=INVALID_SENDER");
307   EXPECT_TRUE(callback_called_);
308   EXPECT_EQ(RegistrationRequest::INVALID_SENDER, status_);
309   EXPECT_EQ(std::string(), registration_id_);
310 }
311 
TEST_F(GCMRegistrationRequestTest,ResponseQuotaExceeded)312 TEST_F(GCMRegistrationRequestTest, ResponseQuotaExceeded) {
313   CreateRequest("sender1");
314   request_->Start();
315 
316   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_SERVICE_UNAVAILABLE,
317                                "Error=QUOTA_EXCEEDED");
318   EXPECT_TRUE(callback_called_);
319   EXPECT_EQ(RegistrationRequest::QUOTA_EXCEEDED, status_);
320   EXPECT_EQ(std::string(), registration_id_);
321 }
322 
TEST_F(GCMRegistrationRequestTest,ResponseTooManyRegistrations)323 TEST_F(GCMRegistrationRequestTest, ResponseTooManyRegistrations) {
324   CreateRequest("sender1");
325   request_->Start();
326 
327   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK,
328                                "Error=TOO_MANY_REGISTRATIONS");
329   EXPECT_TRUE(callback_called_);
330   EXPECT_EQ(RegistrationRequest::TOO_MANY_REGISTRATIONS, status_);
331   EXPECT_EQ(std::string(), registration_id_);
332 }
333 
TEST_F(GCMRegistrationRequestTest,RequestNotSuccessful)334 TEST_F(GCMRegistrationRequestTest, RequestNotSuccessful) {
335   CreateRequest("sender1,sender2");
336   request_->Start();
337 
338   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK, "token=2501",
339                                net::ERR_FAILED);
340   EXPECT_FALSE(callback_called_);
341 
342   // Ensuring a retry happened and succeeded.
343   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK, "token=2501");
344 
345   EXPECT_TRUE(callback_called_);
346   EXPECT_EQ(RegistrationRequest::SUCCESS, status_);
347   EXPECT_EQ("2501", registration_id_);
348 }
349 
TEST_F(GCMRegistrationRequestTest,ResponseHttpNotOk)350 TEST_F(GCMRegistrationRequestTest, ResponseHttpNotOk) {
351   CreateRequest("sender1,sender2");
352   request_->Start();
353 
354   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_GATEWAY_TIMEOUT,
355                                "token=2501");
356   EXPECT_FALSE(callback_called_);
357 
358   // Ensuring a retry happened and succeeded.
359   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK, "token=2501");
360 
361   EXPECT_TRUE(callback_called_);
362   EXPECT_EQ(RegistrationRequest::SUCCESS, status_);
363   EXPECT_EQ("2501", registration_id_);
364 }
365 
TEST_F(GCMRegistrationRequestTest,MaximumAttemptsReachedWithZeroRetries)366 TEST_F(GCMRegistrationRequestTest, MaximumAttemptsReachedWithZeroRetries) {
367   set_max_retry_count(0);
368   CreateRequest("sender1,sender2");
369   request_->Start();
370 
371   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_GATEWAY_TIMEOUT,
372                                "token=2501");
373 
374   EXPECT_TRUE(callback_called_);
375   EXPECT_EQ(RegistrationRequest::REACHED_MAX_RETRIES, status_);
376   EXPECT_EQ(std::string(), registration_id_);
377 }
378 
TEST_F(GCMRegistrationRequestTest,MaximumAttemptsReached)379 TEST_F(GCMRegistrationRequestTest, MaximumAttemptsReached) {
380   CreateRequest("sender1,sender2");
381   request_->Start();
382 
383   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_GATEWAY_TIMEOUT,
384                                "token=2501");
385   EXPECT_FALSE(callback_called_);
386 
387   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_GATEWAY_TIMEOUT,
388                                "token=2501");
389   EXPECT_FALSE(callback_called_);
390 
391   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_GATEWAY_TIMEOUT,
392                                "token=2501");
393   EXPECT_TRUE(callback_called_);
394   EXPECT_EQ(RegistrationRequest::REACHED_MAX_RETRIES, status_);
395   EXPECT_EQ(std::string(), registration_id_);
396 }
397 
398 class InstanceIDGetTokenRequestTest : public RegistrationRequestTest {
399  public:
400   InstanceIDGetTokenRequestTest();
401   ~InstanceIDGetTokenRequestTest() override;
402 
403   void CreateRequest(bool use_subtype,
404                      const std::string& instance_id,
405                      const std::string& authorized_entity,
406                      const std::string& scope,
407                      base::TimeDelta time_to_live,
408                      const std::map<std::string, std::string>& options);
409 };
410 
InstanceIDGetTokenRequestTest()411 InstanceIDGetTokenRequestTest::InstanceIDGetTokenRequestTest() {
412 }
413 
~InstanceIDGetTokenRequestTest()414 InstanceIDGetTokenRequestTest::~InstanceIDGetTokenRequestTest() {
415 }
416 
CreateRequest(bool use_subtype,const std::string & instance_id,const std::string & authorized_entity,const std::string & scope,base::TimeDelta time_to_live,const std::map<std::string,std::string> & options)417 void InstanceIDGetTokenRequestTest::CreateRequest(
418     bool use_subtype,
419     const std::string& instance_id,
420     const std::string& authorized_entity,
421     const std::string& scope,
422     base::TimeDelta time_to_live,
423     const std::map<std::string, std::string>& options) {
424   std::string category = use_subtype ? kProductCategoryForSubtypes : kAppId;
425   std::string subtype = use_subtype ? kAppId : std::string();
426   RegistrationRequest::RequestInfo request_info(kAndroidId, kSecurityToken,
427                                                 category, subtype);
428   std::unique_ptr<InstanceIDGetTokenRequestHandler> request_handler(
429       new InstanceIDGetTokenRequestHandler(instance_id, authorized_entity,
430                                            scope, kGCMVersion, time_to_live,
431                                            options));
432   request_.reset(new RegistrationRequest(
433       GURL(kRegistrationURL), request_info, std::move(request_handler),
434       GetBackoffPolicy(),
435       base::BindOnce(&RegistrationRequestTest::RegistrationCallback,
436                      base::Unretained(this)),
437       max_retry_count_, url_loader_factory(),
438       base::ThreadTaskRunnerHandle::Get(), &recorder_, authorized_entity));
439 }
440 
TEST_F(InstanceIDGetTokenRequestTest,RequestSuccessful)441 TEST_F(InstanceIDGetTokenRequestTest, RequestSuccessful) {
442   std::map<std::string, std::string> options;
443   options["Foo"] = "Bar";
444 
445   set_max_retry_count(0);
446   CreateRequest(false /* use_subtype */, kInstanceId, kDeveloperId, kScope,
447                 /*time_to_live=*/base::TimeDelta(), options);
448   request_->Start();
449 
450   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK, "token=2501");
451   EXPECT_TRUE(callback_called_);
452   EXPECT_EQ(RegistrationRequest::SUCCESS, status_);
453   EXPECT_EQ("2501", registration_id_);
454 }
455 
TEST_F(InstanceIDGetTokenRequestTest,RequestDataAndURL)456 TEST_F(InstanceIDGetTokenRequestTest, RequestDataAndURL) {
457   std::map<std::string, std::string> options;
458   options["Foo"] = "Bar";
459   CreateRequest(false /* use_subtype */, kInstanceId, kDeveloperId, kScope,
460                 /*time_to_live=*/base::TimeDelta(), options);
461   request_->Start();
462 
463   // Verify that the no-cookie flag is set.
464   const network::ResourceRequest* pending_request;
465   ASSERT_TRUE(
466       test_url_loader_factory()->IsPending(kRegistrationURL, &pending_request));
467   EXPECT_EQ(network::mojom::CredentialsMode::kOmit,
468             pending_request->credentials_mode);
469 
470   // Verify that authorization header was put together properly.
471   const net::HttpRequestHeaders* headers =
472       GetExtraHeadersForURL(kRegistrationURL);
473   ASSERT_TRUE(headers != nullptr);
474   std::string auth_header;
475   headers->GetHeader(net::HttpRequestHeaders::kAuthorization, &auth_header);
476   base::StringTokenizer auth_tokenizer(auth_header, " :");
477   ASSERT_TRUE(auth_tokenizer.GetNext());
478   EXPECT_EQ(kLoginHeader, auth_tokenizer.token());
479   ASSERT_TRUE(auth_tokenizer.GetNext());
480   EXPECT_EQ(base::NumberToString(kAndroidId), auth_tokenizer.token());
481   ASSERT_TRUE(auth_tokenizer.GetNext());
482   EXPECT_EQ(base::NumberToString(kSecurityToken), auth_tokenizer.token());
483 
484   std::map<std::string, std::string> expected_pairs;
485   expected_pairs["gmsv"] = base::NumberToString(kGCMVersion);
486   expected_pairs["app"] = kAppId;
487   expected_pairs["sender"] = kDeveloperId;
488   expected_pairs["device"] = base::NumberToString(kAndroidId);
489   expected_pairs["appid"] = kInstanceId;
490   expected_pairs["scope"] = kScope;
491   expected_pairs["X-scope"] = kScope;
492   expected_pairs["X-Foo"] = "Bar";
493 
494   ASSERT_NO_FATAL_FAILURE(
495       VerifyFetcherUploadDataForURL(kRegistrationURL, &expected_pairs));
496 }
497 
TEST_F(InstanceIDGetTokenRequestTest,RequestDataWithTTL)498 TEST_F(InstanceIDGetTokenRequestTest, RequestDataWithTTL) {
499   CreateRequest(false, kInstanceId, kDeveloperId, kScope,
500                 /*time_to_live=*/base::TimeDelta::FromSeconds(100),
501                 /*options=*/{});
502   request_->Start();
503 
504   // Same as RequestDataAndURL except "ttl" and "X-Foo".
505   std::map<std::string, std::string> expected_pairs;
506   expected_pairs["gmsv"] = base::NumberToString(kGCMVersion);
507   expected_pairs["app"] = kAppId;
508   expected_pairs["sender"] = kDeveloperId;
509   expected_pairs["device"] = base::NumberToString(kAndroidId);
510   expected_pairs["appid"] = kInstanceId;
511   expected_pairs["scope"] = kScope;
512   expected_pairs["ttl"] = "100";
513   expected_pairs["X-scope"] = kScope;
514 
515   ASSERT_NO_FATAL_FAILURE(
516       VerifyFetcherUploadDataForURL(kRegistrationURL, &expected_pairs));
517 }
518 
TEST_F(InstanceIDGetTokenRequestTest,RequestDataWithSubtype)519 TEST_F(InstanceIDGetTokenRequestTest, RequestDataWithSubtype) {
520   std::map<std::string, std::string> options;
521   options["Foo"] = "Bar";
522   CreateRequest(true /* use_subtype */, kInstanceId, kDeveloperId, kScope,
523                 /*time_to_live=*/base::TimeDelta(), options);
524   request_->Start();
525 
526   // Same as RequestDataAndURL except "app" and "X-subtype".
527   std::map<std::string, std::string> expected_pairs;
528   expected_pairs["gmsv"] = base::NumberToString(kGCMVersion);
529   expected_pairs["app"] = kProductCategoryForSubtypes;
530   expected_pairs["X-subtype"] = kAppId;
531   expected_pairs["sender"] = kDeveloperId;
532   expected_pairs["device"] = base::NumberToString(kAndroidId);
533   expected_pairs["appid"] = kInstanceId;
534   expected_pairs["scope"] = kScope;
535   expected_pairs["X-scope"] = kScope;
536   expected_pairs["X-Foo"] = "Bar";
537 
538   // Verify data was formatted properly.
539   std::string upload_data;
540   ASSERT_TRUE(GetUploadDataForURL(kRegistrationURL, &upload_data));
541   base::StringTokenizer data_tokenizer(upload_data, "&=");
542   while (data_tokenizer.GetNext()) {
543     auto iter = expected_pairs.find(data_tokenizer.token());
544     ASSERT_TRUE(iter != expected_pairs.end());
545     ASSERT_TRUE(data_tokenizer.GetNext());
546     EXPECT_EQ(iter->second, data_tokenizer.token());
547     // Ensure that none of the keys appears twice.
548     expected_pairs.erase(iter);
549   }
550 
551   EXPECT_EQ(0UL, expected_pairs.size());
552 }
553 
TEST_F(InstanceIDGetTokenRequestTest,ResponseHttpStatusNotOK)554 TEST_F(InstanceIDGetTokenRequestTest, ResponseHttpStatusNotOK) {
555   std::map<std::string, std::string> options;
556   CreateRequest(false /* use_subtype */, kInstanceId, kDeveloperId, kScope,
557                 /*time_to_live=*/base::TimeDelta(), options);
558   request_->Start();
559 
560   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_UNAUTHORIZED,
561                                "token=2501");
562   EXPECT_FALSE(callback_called_);
563 
564   SetResponseForURLAndComplete(kRegistrationURL, net::HTTP_OK, "token=2501");
565   EXPECT_TRUE(callback_called_);
566   EXPECT_EQ(RegistrationRequest::SUCCESS, status_);
567   EXPECT_EQ("2501", registration_id_);
568 }
569 
570 }  // namespace gcm
571