blob: bcd111b625d69c85f574b8e3be78ee22eb9e18e3 [file] [log] [blame]
[email protected]e4097c82013-11-08 00:16:121// Copyright 2013 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#ifndef GOOGLE_APIS_GCM_GCM_CLIENT_IMPL_H_
6#define GOOGLE_APIS_GCM_GCM_CLIENT_IMPL_H_
7
[email protected]b83122a92014-01-22 21:29:298#include <map>
9#include <string>
[email protected]848b1b62014-01-30 23:51:0410#include <vector>
[email protected]b83122a92014-01-22 21:29:2911
[email protected]e4097c82013-11-08 00:16:1212#include "base/compiler_specific.h"
[email protected]79994f42014-01-16 16:05:3613#include "base/memory/ref_counted.h"
[email protected]955e0ff2014-01-31 20:42:1214#include "base/memory/weak_ptr.h"
[email protected]b83122a92014-01-22 21:29:2915#include "base/stl_util.h"
[email protected]b83122a92014-01-22 21:29:2916#include "google_apis/gcm/base/mcs_message.h"
17#include "google_apis/gcm/engine/gcm_store.h"
18#include "google_apis/gcm/engine/mcs_client.h"
[email protected]b4dd0232014-02-08 02:37:3119#include "google_apis/gcm/engine/registration_request.h"
[email protected]e4097c82013-11-08 00:16:1220#include "google_apis/gcm/gcm_client.h"
[email protected]b83122a92014-01-22 21:29:2921#include "google_apis/gcm/protocol/android_checkin.pb.h"
22#include "net/base/net_log.h"
23#include "net/url_request/url_request_context_getter.h"
[email protected]e4097c82013-11-08 00:16:1224
[email protected]79994f42014-01-16 16:05:3625namespace base {
[email protected]955e0ff2014-01-31 20:42:1226class Clock;
[email protected]79994f42014-01-16 16:05:3627} // namespace base
28
[email protected]b83122a92014-01-22 21:29:2929namespace net {
30class HttpNetworkSession;
[email protected]955e0ff2014-01-31 20:42:1231} // namespace net
[email protected]b83122a92014-01-22 21:29:2932
[email protected]e4097c82013-11-08 00:16:1233namespace gcm {
34
[email protected]b83122a92014-01-22 21:29:2935class CheckinRequest;
36class ConnectionFactory;
37class GCMClientImplTest;
[email protected]79994f42014-01-16 16:05:3638class UserList;
39
[email protected]b83122a92014-01-22 21:29:2940// Implements the GCM Client. It is used to coordinate MCS Client (communication
41// with MCS) and other pieces of GCM infrastructure like Registration and
42// Checkins. It also allows for registering user delegates that host
43// applications that send and receive messages.
[email protected]0db118222014-01-22 01:37:5944class GCM_EXPORT GCMClientImpl : public GCMClient {
[email protected]e4097c82013-11-08 00:16:1245 public:
46 GCMClientImpl();
47 virtual ~GCMClientImpl();
48
49 // Overridden from GCMClient:
[email protected]e2a4a8012014-02-07 22:32:5250 virtual void Initialize(
51 const checkin_proto::ChromeBuildProto& chrome_build_proto,
52 const base::FilePath& store_path,
53 const scoped_refptr<base::SequencedTaskRunner>& blocking_task_runner,
54 const scoped_refptr<net::URLRequestContextGetter>&
55 url_request_context_getter) OVERRIDE;
[email protected]1b1c3cd2013-12-17 18:40:0456 virtual void SetUserDelegate(const std::string& username,
57 Delegate* delegate) OVERRIDE;
58 virtual void CheckIn(const std::string& username) OVERRIDE;
[email protected]e4097c82013-11-08 00:16:1259 virtual void Register(const std::string& username,
60 const std::string& app_id,
61 const std::string& cert,
62 const std::vector<std::string>& sender_ids) OVERRIDE;
63 virtual void Unregister(const std::string& username,
64 const std::string& app_id) OVERRIDE;
65 virtual void Send(const std::string& username,
66 const std::string& app_id,
67 const std::string& receiver_id,
68 const OutgoingMessage& message) OVERRIDE;
[email protected]86625df2014-01-31 03:47:5869 virtual bool IsReady() const OVERRIDE;
[email protected]e4097c82013-11-08 00:16:1270
71 private:
[email protected]b83122a92014-01-22 21:29:2972 // State representation of the GCMClient.
73 enum State {
74 // Uninitialized.
75 UNINITIALIZED,
76 // GCM store loading is in progress.
77 LOADING,
78 // Initial device checkin is in progress.
79 INITIAL_DEVICE_CHECKIN,
80 // Ready to accept requests.
81 READY,
82 };
83
84 // Collection of pending checkin requests. Keys are serial numbers of the
85 // users as assigned by the user_list_. Values are pending checkin requests to
86 // obtain android IDs and security tokens for the users.
87 typedef std::map<int64, CheckinRequest*> PendingCheckins;
88
[email protected]848b1b62014-01-30 23:51:0489 // A pair of |username| and |app_id| identifying a pending
90 // RegistrationRequest.
91 struct PendingRegistrationKey {
92 PendingRegistrationKey(const std::string& username,
93 const std::string& app_id);
94 ~PendingRegistrationKey();
95 bool operator<(const PendingRegistrationKey& rhs) const;
96
97 std::string username;
98 std::string app_id;
99 };
100
101 // Collection of pending registration requests. Keys are pairs of |username|
102 // and |app_id|, while values are pending registration requests to obtain a
103 // registration ID for requesting application.
104 typedef std::map<PendingRegistrationKey, RegistrationRequest*>
105 PendingRegistrations;
106
[email protected]b83122a92014-01-22 21:29:29107 friend class GCMClientImplTest;
108
109 // Callbacks for the MCSClient.
110 // Receives messages and dispatches them to relevant user delegates.
111 void OnMessageReceivedFromMCS(const gcm::MCSMessage& message);
112 // Receives confirmation of sent messages or information about errors.
113 void OnMessageSentToMCS(int64 user_serial_number,
114 const std::string& app_id,
115 const std::string& message_id,
116 MCSClient::MessageSendStatus status);
117 // Receives information about mcs_client_ errors.
118 void OnMCSError();
119
120 // Runs after GCM Store load is done to trigger continuation of the
121 // initialization.
[email protected]2809af72014-01-25 09:23:57122 void OnLoadCompleted(scoped_ptr<GCMStore::LoadResult> result);
[email protected]b83122a92014-01-22 21:29:29123 // Initializes mcs_client_, which handles the connection to MCS.
[email protected]2809af72014-01-25 09:23:57124 void InitializeMCSClient(scoped_ptr<GCMStore::LoadResult> result);
[email protected]b83122a92014-01-22 21:29:29125 // Complets the first time device checkin.
126 void OnFirstTimeDeviceCheckinCompleted(const CheckinInfo& checkin_info);
127 // Starts a login on mcs_client_.
128 void StartMCSLogin();
129 // Resets state to before initialization.
130 void ResetState();
[email protected]86625df2014-01-31 03:47:58131 // Sets state to ready. This will initiate the MCS login and notify the
132 // delegates.
133 void OnReady();
[email protected]b83122a92014-01-22 21:29:29134
135 // Startes a checkin request for a user with specified |serial_number|.
136 // Checkin info can be invalid, in which case it is considered a first time
137 // checkin.
138 void StartCheckin(int64 user_serial_number,
139 const CheckinInfo& checkin_info);
140 // Completes the checkin request for the specified |serial_number|.
141 // |android_id| and |security_token| are expected to be non-zero or an error
142 // is triggered. Function also cleans up the pending checkin.
143 void OnCheckinCompleted(int64 user_serial_number,
144 uint64 android_id,
145 uint64 security_token);
146 // Completes the checkin request for a device (serial number of 0).
147 void OnDeviceCheckinCompleted(const CheckinInfo& checkin_info);
148
149 // Callback for persisting device credentials in the |gcm_store_|.
150 void SetDeviceCredentialsCallback(bool success);
151
[email protected]848b1b62014-01-30 23:51:04152 // Completes the registration request.
153 void OnRegisterCompleted(const PendingRegistrationKey& registration_key,
[email protected]b4dd0232014-02-08 02:37:31154 RegistrationRequest::Status status,
[email protected]848b1b62014-01-30 23:51:04155 const std::string& registration_id);
156
[email protected]b83122a92014-01-22 21:29:29157 // Callback for setting a delegate on a |user_list_|. Informs that the
158 // delegate with matching |username| was assigned a |user_serial_number|.
159 void SetDelegateCompleted(const std::string& username,
160 int64 user_serial_number);
161
162 // Handles incoming data message and dispatches it the a relevant user
163 // delegate.
164 void HandleIncomingMessage(const gcm::MCSMessage& message);
165
[email protected]848b1b62014-01-30 23:51:04166 // Fires OnMessageSendError event on |delegate|, with specified |app_id| and
167 // message ID obtained from |incoming_message| if one is available.
168 void NotifyDelegateOnMessageSendError(
169 GCMClient::Delegate* delegate,
170 const std::string& app_id,
171 const IncomingMessage& incoming_message);
172
173 // For testing purpose only.
174 // Sets an |mcs_client_| for testing. Takes the ownership of |mcs_client|.
175 // TODO(fgorski): Remove this method. Create GCMEngineFactory that will create
176 // components of the engine.
177 void SetMCSClientForTesting(scoped_ptr<MCSClient> mcs_client);
[email protected]b83122a92014-01-22 21:29:29178
179 // State of the GCM Client Implementation.
180 State state_;
181
182 // Device checkin info (android ID and security token used by device).
183 CheckinInfo device_checkin_info_;
184
[email protected]848b1b62014-01-30 23:51:04185 // Clock used for timing of retry logic. Passed in for testing. Owned by
186 // GCMClientImpl.
187 scoped_ptr<base::Clock> clock_;
[email protected]b83122a92014-01-22 21:29:29188
189 // Information about the chrome build.
190 // TODO(fgorski): Check if it can be passed in constructor and made const.
191 checkin_proto::ChromeBuildProto chrome_build_proto_;
192
193 // Persistent data store for keeping device credentials, messages and user to
194 // serial number mappings.
[email protected]79994f42014-01-16 16:05:36195 scoped_ptr<GCMStore> gcm_store_;
[email protected]b83122a92014-01-22 21:29:29196
197 // Keeps the mappings of user's serial numbers and assigns new serial numbers
198 // once a user delegate is added for the first time.
[email protected]79994f42014-01-16 16:05:36199 scoped_ptr<UserList> user_list_;
200
[email protected]b83122a92014-01-22 21:29:29201 scoped_refptr<net::HttpNetworkSession> network_session_;
202 net::BoundNetLog net_log_;
203 scoped_ptr<ConnectionFactory> connection_factory_;
204 scoped_refptr<net::URLRequestContextGetter> url_request_context_getter_;
205
206 // Controls receiving and sending of packets and reliable message queueing.
207 scoped_ptr<MCSClient> mcs_client_;
208
209 // Currently pending checkins. GCMClientImpl owns the CheckinRequests.
210 PendingCheckins pending_checkins_;
211 STLValueDeleter<PendingCheckins> pending_checkins_deleter_;
212
[email protected]848b1b62014-01-30 23:51:04213 // Currently pending registrations. GCMClientImpl owns the
214 // RegistrationRequests.
215 PendingRegistrations pending_registrations_;
216 STLValueDeleter<PendingRegistrations> pending_registrations_deleter_;
217
[email protected]955e0ff2014-01-31 20:42:12218 // Factory for creating references in callbacks.
219 base::WeakPtrFactory<GCMClientImpl> weak_ptr_factory_;
220
[email protected]e4097c82013-11-08 00:16:12221 DISALLOW_COPY_AND_ASSIGN(GCMClientImpl);
222};
223
224} // namespace gcm
225
226#endif // GOOGLE_APIS_GCM_GCM_CLIENT_IMPL_H_