OLD | NEW |
1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "chrome/browser/policy/device_token_fetcher.h" | 5 #include "chrome/browser/policy/device_token_fetcher.h" |
6 | 6 |
7 #include "base/file_util.h" | 7 #include "base/file_util.h" |
8 #include "base/path_service.h" | 8 #include "base/path_service.h" |
9 #include "base/singleton.h" | 9 #include "base/singleton.h" |
10 #include "chrome/browser/guid.h" | 10 #include "chrome/browser/guid.h" |
11 #include "chrome/browser/net/gaia/token_service.h" | 11 #include "chrome/browser/net/gaia/token_service.h" |
| 12 #include "chrome/browser/policy/proto/device_management_local.pb.h" |
12 #include "chrome/common/chrome_paths.h" | 13 #include "chrome/common/chrome_paths.h" |
13 #include "chrome/common/net/gaia/gaia_constants.h" | 14 #include "chrome/common/net/gaia/gaia_constants.h" |
14 #include "chrome/common/notification_details.h" | 15 #include "chrome/common/notification_details.h" |
15 #include "chrome/common/notification_service.h" | 16 #include "chrome/common/notification_service.h" |
16 #include "chrome/common/notification_source.h" | 17 #include "chrome/common/notification_source.h" |
17 #include "chrome/common/notification_type.h" | 18 #include "chrome/common/notification_type.h" |
18 | 19 |
19 namespace policy { | 20 namespace policy { |
20 | 21 |
| 22 namespace em = enterprise_management; |
| 23 |
21 DeviceTokenFetcher::DeviceTokenFetcher( | 24 DeviceTokenFetcher::DeviceTokenFetcher( |
22 DeviceManagementBackend* backend, | 25 DeviceManagementBackend* backend, |
23 const FilePath& token_path) | 26 const FilePath& token_path) |
24 : token_path_(token_path), | 27 : token_path_(token_path), |
25 backend_(backend), | 28 backend_(backend), |
26 state_(kStateNotStarted), | 29 state_(kStateNotStarted), |
27 device_token_load_complete_event_(true, false) { | 30 device_token_load_complete_event_(true, false) { |
28 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 31 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
29 // The token fetcher gets initialized AuthTokens for the device management | 32 // The token fetcher gets initialized AuthTokens for the device management |
30 // server are available. Install a notification observer to ensure that the | 33 // server are available. Install a notification observer to ensure that the |
(...skipping 26 matching lines...) Expand all Loading... |
57 const em::DeviceRegisterResponse& response) { | 60 const em::DeviceRegisterResponse& response) { |
58 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 61 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
59 DCHECK_EQ(kStateRequestingDeviceTokenFromServer, state_); | 62 DCHECK_EQ(kStateRequestingDeviceTokenFromServer, state_); |
60 if (response.has_device_management_token()) { | 63 if (response.has_device_management_token()) { |
61 device_token_ = response.device_management_token(); | 64 device_token_ = response.device_management_token(); |
62 BrowserThread::PostTask( | 65 BrowserThread::PostTask( |
63 BrowserThread::FILE, | 66 BrowserThread::FILE, |
64 FROM_HERE, | 67 FROM_HERE, |
65 NewRunnableFunction(&WriteDeviceTokenToDisk, | 68 NewRunnableFunction(&WriteDeviceTokenToDisk, |
66 token_path_, | 69 token_path_, |
67 device_token_)); | 70 device_token_, |
| 71 device_id_)); |
68 SetState(kStateHasDeviceToken); | 72 SetState(kStateHasDeviceToken); |
69 } else { | 73 } else { |
70 NOTREACHED(); | 74 NOTREACHED(); |
71 SetState(kStateFailure); | 75 SetState(kStateFailure); |
72 } | 76 } |
73 } | 77 } |
74 | 78 |
75 void DeviceTokenFetcher::OnError(DeviceManagementBackend::ErrorCode code) { | 79 void DeviceTokenFetcher::OnError(DeviceManagementBackend::ErrorCode code) { |
76 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 80 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
77 SetState(kStateFailure); | 81 SetState(kStateFailure); |
78 } | 82 } |
79 | 83 |
80 void DeviceTokenFetcher::StartFetching() { | 84 void DeviceTokenFetcher::StartFetching() { |
81 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 85 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
82 if (state_ == kStateNotStarted) { | 86 if (state_ == kStateNotStarted) { |
83 SetState(kStateLoadDeviceTokenFromDisk); | 87 SetState(kStateLoadDeviceTokenFromDisk); |
84 // The file calls for loading the persisted token must be deferred to the | 88 // The file calls for loading the persisted token must be deferred to the |
85 // FILE thread. | 89 // FILE thread. |
86 BrowserThread::PostTask( | 90 BrowserThread::PostTask( |
87 BrowserThread::FILE, | 91 BrowserThread::FILE, |
88 FROM_HERE, | 92 FROM_HERE, |
89 NewRunnableMethod(this, | 93 NewRunnableMethod(this, |
90 &DeviceTokenFetcher::AttemptTokenLoadFromDisk)); | 94 &DeviceTokenFetcher::AttemptTokenLoadFromDisk)); |
91 } | 95 } |
92 } | 96 } |
93 | 97 |
94 void DeviceTokenFetcher::AttemptTokenLoadFromDisk() { | 98 void DeviceTokenFetcher::AttemptTokenLoadFromDisk() { |
95 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::FILE)); | 99 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::FILE)); |
96 FetcherState new_state = kStateFailure; | |
97 if (file_util::PathExists(token_path_)) { | 100 if (file_util::PathExists(token_path_)) { |
98 std::string device_token; | 101 std::string data; |
99 if (file_util::ReadFileToString(token_path_, &device_token_)) { | 102 em::DeviceCredentials device_credentials; |
100 new_state = kStateHasDeviceToken; | 103 if (file_util::ReadFileToString(token_path_, &data) && |
| 104 device_credentials.ParseFromArray(data.c_str(), data.size())) { |
| 105 device_token_ = device_credentials.device_token(); |
| 106 device_id_ = device_credentials.device_id(); |
| 107 if (!device_token_.empty() && !device_id_.empty()) { |
| 108 BrowserThread::PostTask( |
| 109 BrowserThread::UI, |
| 110 FROM_HERE, |
| 111 NewRunnableMethod(this, |
| 112 &DeviceTokenFetcher::SetState, |
| 113 kStateHasDeviceToken)); |
| 114 return; |
| 115 } |
101 } | 116 } |
102 BrowserThread::PostTask( | |
103 BrowserThread::UI, | |
104 FROM_HERE, | |
105 NewRunnableMethod(this, | |
106 &DeviceTokenFetcher::SetState, | |
107 new_state)); | |
108 return; | |
109 } | 117 } |
110 | 118 |
111 BrowserThread::PostTask( | 119 BrowserThread::PostTask( |
112 BrowserThread::UI, | 120 BrowserThread::UI, |
113 FROM_HERE, | 121 FROM_HERE, |
114 NewRunnableMethod(this, | 122 NewRunnableMethod(this, |
115 &DeviceTokenFetcher::MakeReadyToRequestDeviceToken)); | 123 &DeviceTokenFetcher::MakeReadyToRequestDeviceToken)); |
116 } | 124 } |
117 | 125 |
118 void DeviceTokenFetcher::MakeReadyToRequestDeviceToken() { | 126 void DeviceTokenFetcher::MakeReadyToRequestDeviceToken() { |
119 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 127 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
120 SetState(kStateReadyToRequestDeviceTokenFromServer); | 128 SetState(kStateReadyToRequestDeviceTokenFromServer); |
121 SendServerRequestIfPossible(); | 129 SendServerRequestIfPossible(); |
122 } | 130 } |
123 | 131 |
124 void DeviceTokenFetcher::SendServerRequestIfPossible() { | 132 void DeviceTokenFetcher::SendServerRequestIfPossible() { |
125 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 133 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
126 if (state_ == kStateReadyToRequestDeviceTokenFromServer | 134 if (state_ == kStateReadyToRequestDeviceTokenFromServer |
127 && HasAuthToken()) { | 135 && HasAuthToken()) { |
128 em::DeviceRegisterRequest register_request; | 136 em::DeviceRegisterRequest register_request; |
129 SetState(kStateRequestingDeviceTokenFromServer); | 137 SetState(kStateRequestingDeviceTokenFromServer); |
130 backend_->ProcessRegisterRequest(auth_token_, | 138 backend_->ProcessRegisterRequest(auth_token_, |
131 GenerateNewDeviceID(), | 139 GetDeviceID(), |
132 register_request, | 140 register_request, |
133 this); | 141 this); |
134 } | 142 } |
135 } | 143 } |
136 | 144 |
137 bool DeviceTokenFetcher::IsTokenPending() { | 145 bool DeviceTokenFetcher::IsTokenPending() { |
138 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 146 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
139 return !device_token_load_complete_event_.IsSignaled(); | 147 return !device_token_load_complete_event_.IsSignaled(); |
140 } | 148 } |
141 | 149 |
142 std::string DeviceTokenFetcher::GetDeviceToken() { | 150 std::string DeviceTokenFetcher::GetDeviceToken() { |
143 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 151 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
144 device_token_load_complete_event_.Wait(); | 152 device_token_load_complete_event_.Wait(); |
145 return device_token_; | 153 return device_token_; |
146 } | 154 } |
147 | 155 |
| 156 std::string DeviceTokenFetcher::GetDeviceID() { |
| 157 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| 158 // As long as access to this is only allowed from the UI thread, no explicit |
| 159 // locking is necessary to prevent the ID from being generated twice. |
| 160 if (device_id_.empty()) |
| 161 device_id_ = GenerateNewDeviceID(); |
| 162 return device_id_; |
| 163 } |
| 164 |
148 void DeviceTokenFetcher::SetState(FetcherState state) { | 165 void DeviceTokenFetcher::SetState(FetcherState state) { |
149 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 166 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
150 if (state_ == state) | 167 if (state_ == state) |
151 return; | 168 return; |
152 state_ = state; | 169 state_ = state; |
153 if (state == kStateFailure) { | 170 if (state == kStateFailure) { |
154 device_token_load_complete_event_.Signal(); | 171 device_token_load_complete_event_.Signal(); |
155 } else if (state == kStateHasDeviceToken) { | 172 } else if (state == kStateHasDeviceToken) { |
156 device_token_load_complete_event_.Signal(); | 173 device_token_load_complete_event_.Signal(); |
157 NotificationService::current()->Notify( | 174 NotificationService::current()->Notify( |
158 NotificationType::DEVICE_TOKEN_AVAILABLE, | 175 NotificationType::DEVICE_TOKEN_AVAILABLE, |
159 Source<DeviceTokenFetcher>(this), | 176 Source<DeviceTokenFetcher>(this), |
160 NotificationService::NoDetails()); | 177 NotificationService::NoDetails()); |
161 } | 178 } |
162 } | 179 } |
163 | 180 |
164 void DeviceTokenFetcher::GetDeviceTokenPath(FilePath* token_path) const { | 181 void DeviceTokenFetcher::GetDeviceTokenPath(FilePath* token_path) const { |
165 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 182 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
166 *token_path = token_path_; | 183 *token_path = token_path_; |
167 } | 184 } |
168 | 185 |
169 bool DeviceTokenFetcher::IsTokenValid() const { | 186 bool DeviceTokenFetcher::IsTokenValid() const { |
170 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 187 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
171 return state_ == kStateHasDeviceToken; | 188 return state_ == kStateHasDeviceToken; |
172 } | 189 } |
173 | 190 |
174 // static | 191 // static |
175 void DeviceTokenFetcher::WriteDeviceTokenToDisk( | 192 void DeviceTokenFetcher::WriteDeviceTokenToDisk( |
176 const FilePath& path, | 193 const FilePath& path, |
177 const std::string& device_token) { | 194 const std::string& device_token, |
178 file_util::WriteFile(path, | 195 const std::string& device_id) { |
179 device_token.c_str(), | 196 em::DeviceCredentials device_credentials; |
180 device_token.length()); | 197 device_credentials.set_device_token(device_token); |
| 198 device_credentials.set_device_id(device_id); |
| 199 std::string data; |
| 200 bool no_error = device_credentials.SerializeToString(&data); |
| 201 DCHECK(no_error); |
| 202 file_util::WriteFile(path, data.c_str(), data.length()); |
181 } | 203 } |
182 | 204 |
183 // static | 205 // static |
184 std::string DeviceTokenFetcher::GenerateNewDeviceID() { | 206 std::string DeviceTokenFetcher::GenerateNewDeviceID() { |
185 return guid::GenerateGUID(); | 207 return guid::GenerateGUID(); |
186 } | 208 } |
187 | 209 |
188 } | 210 } |
OLD | NEW |