OLD | NEW |
---|---|
1 // Copyright 2014 The Chromium Authors. All rights reserved. | 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 | 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 "sync/internal_api/public/attachments/attachment_uploader_impl.h" | 5 #include "sync/internal_api/public/attachments/attachment_uploader_impl.h" |
6 | 6 |
7 #include "base/base64.h" | 7 #include "base/base64.h" |
8 #include "base/bind.h" | 8 #include "base/bind.h" |
9 #include "base/macros.h" | 9 #include "base/macros.h" |
10 #include "base/memory/weak_ptr.h" | 10 #include "base/memory/weak_ptr.h" |
11 #include "base/message_loop/message_loop.h" | 11 #include "base/message_loop/message_loop.h" |
12 #include "base/strings/string_piece.h" | 12 #include "base/strings/string_piece.h" |
13 #include "base/strings/stringprintf.h" | 13 #include "base/strings/stringprintf.h" |
14 #include "base/sys_byteorder.h" | 14 #include "base/sys_byteorder.h" |
15 #include "base/threading/non_thread_safe.h" | 15 #include "base/threading/non_thread_safe.h" |
16 #include "google_apis/gaia/gaia_constants.h" | 16 #include "google_apis/gaia/gaia_constants.h" |
17 #include "net/base/load_flags.h" | 17 #include "net/base/load_flags.h" |
18 #include "net/http/http_status_code.h" | 18 #include "net/http/http_status_code.h" |
19 #include "net/url_request/url_fetcher.h" | 19 #include "net/url_request/url_fetcher.h" |
20 #include "net/url_request/url_fetcher_delegate.h" | 20 #include "net/url_request/url_fetcher_delegate.h" |
21 #include "sync/api/attachments/attachment.h" | 21 #include "sync/api/attachments/attachment.h" |
22 #include "sync/protocol/sync.pb.h" | 22 #include "sync/protocol/sync.pb.h" |
23 #include "third_party/leveldatabase/src/util/crc32c.h" | |
24 | 23 |
25 namespace { | 24 namespace { |
26 | 25 |
27 const char kContentType[] = "application/octet-stream"; | 26 const char kContentType[] = "application/octet-stream"; |
28 const char kAttachments[] = "attachments/"; | 27 const char kAttachments[] = "attachments/"; |
29 | 28 |
30 } // namespace | 29 } // namespace |
31 | 30 |
32 namespace syncer { | 31 namespace syncer { |
33 | 32 |
(...skipping 166 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
200 fetcher_->SetRequestContext(url_request_context_getter_.get()); | 199 fetcher_->SetRequestContext(url_request_context_getter_.get()); |
201 // TODO(maniscalco): Is there a better way? Copying the attachment data into | 200 // TODO(maniscalco): Is there a better way? Copying the attachment data into |
202 // a string feels wrong given how large attachments may be (several MBs). If | 201 // a string feels wrong given how large attachments may be (several MBs). If |
203 // we may end up switching from URLFetcher to URLRequest, this copy won't be | 202 // we may end up switching from URLFetcher to URLRequest, this copy won't be |
204 // necessary. | 203 // necessary. |
205 scoped_refptr<base::RefCountedMemory> memory = attachment_.GetData(); | 204 scoped_refptr<base::RefCountedMemory> memory = attachment_.GetData(); |
206 const std::string upload_content(memory->front_as<char>(), memory->size()); | 205 const std::string upload_content(memory->front_as<char>(), memory->size()); |
207 fetcher_->SetUploadData(kContentType, upload_content); | 206 fetcher_->SetUploadData(kContentType, upload_content); |
208 const std::string auth_header("Authorization: Bearer " + access_token_); | 207 const std::string auth_header("Authorization: Bearer " + access_token_); |
209 fetcher_->AddExtraRequestHeader(auth_header); | 208 fetcher_->AddExtraRequestHeader(auth_header); |
210 // TODO(maniscalco): Consider computing the hash once and storing the value as | 209 uint32_t crc = attachment_.GetCrc32c(); |
maniscalco
2014/11/11 00:44:54
Can be made const. Also, how about renaming to cr
pavely
2014/11/11 22:27:15
Done.
| |
211 // a new field in the Attachment object to avoid recomputing when an upload | |
212 // fails and is retried (bug 417794). | |
213 fetcher_->AddExtraRequestHeader(base::StringPrintf( | 210 fetcher_->AddExtraRequestHeader(base::StringPrintf( |
214 "X-Goog-Hash: crc32c=%s", | 211 "X-Goog-Hash: crc32c=%s", FormatCrc32cHash(crc).c_str())); |
215 ComputeCrc32cHash(memory->front_as<char>(), memory->size()).c_str())); | |
216 fetcher_->SetLoadFlags(net::LOAD_DO_NOT_SAVE_COOKIES | | 212 fetcher_->SetLoadFlags(net::LOAD_DO_NOT_SAVE_COOKIES | |
217 net::LOAD_DO_NOT_SEND_COOKIES | | 213 net::LOAD_DO_NOT_SEND_COOKIES | |
218 net::LOAD_DISABLE_CACHE); | 214 net::LOAD_DISABLE_CACHE); |
219 // TODO(maniscalco): Set appropriate headers (e.g. User-Agent) on the request | 215 // TODO(maniscalco): Set appropriate headers (e.g. User-Agent) on the request |
220 // and include the "sync birthday" (bug 371521). | 216 // and include the "sync birthday" (bug 371521). |
221 fetcher_->Start(); | 217 fetcher_->Start(); |
222 } | 218 } |
223 | 219 |
224 void AttachmentUploaderImpl::UploadState::OnGetTokenFailure( | 220 void AttachmentUploaderImpl::UploadState::OnGetTokenFailure( |
225 const OAuth2TokenService::Request* request, | 221 const OAuth2TokenService::Request* request, |
(...skipping 112 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
338 StateMap::iterator iter = state_map_.find(unique_id); | 334 StateMap::iterator iter = state_map_.find(unique_id); |
339 // Only erase if stopped. Because this method is called asynchronously, it's | 335 // Only erase if stopped. Because this method is called asynchronously, it's |
340 // possible that a new request for this same id arrived after the UploadState | 336 // possible that a new request for this same id arrived after the UploadState |
341 // stopped, but before this method was invoked. In that case the UploadState | 337 // stopped, but before this method was invoked. In that case the UploadState |
342 // in the map might be a new one. | 338 // in the map might be a new one. |
343 if (iter != state_map_.end() && iter->second->IsStopped()) { | 339 if (iter != state_map_.end() && iter->second->IsStopped()) { |
344 state_map_.erase(iter); | 340 state_map_.erase(iter); |
345 } | 341 } |
346 } | 342 } |
347 | 343 |
348 std::string AttachmentUploaderImpl::ComputeCrc32cHash(const char* data, | 344 std::string AttachmentUploaderImpl::FormatCrc32cHash(uint32_t crc) { |
maniscalco
2014/11/11 00:44:54
crc -> crc32c?
pavely
2014/11/11 22:27:15
Done.
| |
349 size_t size) { | 345 const uint32_t crc32c_big_endian = base::HostToNet32(crc); |
350 const uint32_t crc32c_big_endian = | |
351 base::HostToNet32(leveldb::crc32c::Value(data, size)); | |
352 const base::StringPiece raw(reinterpret_cast<const char*>(&crc32c_big_endian), | 346 const base::StringPiece raw(reinterpret_cast<const char*>(&crc32c_big_endian), |
353 sizeof(crc32c_big_endian)); | 347 sizeof(crc32c_big_endian)); |
354 std::string encoded; | 348 std::string encoded; |
355 base::Base64Encode(raw, &encoded); | 349 base::Base64Encode(raw, &encoded); |
356 return encoded; | 350 return encoded; |
357 } | 351 } |
358 | 352 |
359 } // namespace syncer | 353 } // namespace syncer |
OLD | NEW |