1// 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#include "chrome/browser/upload_list.h" 6 7#include <algorithm> 8#include <iterator> 9 10#include "base/bind.h" 11#include "base/files/file_util.h" 12#include "base/strings/string_number_conversions.h" 13#include "base/strings/string_split.h" 14#include "content/public/browser/browser_thread.h" 15 16using content::BrowserThread; 17 18UploadList::UploadInfo::UploadInfo(const std::string& id, 19 const base::Time& t, 20 const std::string& local_id) 21 : id(id), time(t), local_id(local_id) {} 22 23UploadList::UploadInfo::UploadInfo(const std::string& id, const base::Time& t) 24 : id(id), time(t) {} 25 26UploadList::UploadInfo::~UploadInfo() {} 27 28UploadList::UploadList(Delegate* delegate, 29 const base::FilePath& upload_log_path) 30 : delegate_(delegate), 31 upload_log_path_(upload_log_path) {} 32 33UploadList::~UploadList() {} 34 35void UploadList::LoadUploadListAsynchronously() { 36 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 37 BrowserThread::PostBlockingPoolTask( 38 FROM_HERE, 39 base::Bind(&UploadList::LoadUploadListAndInformDelegateOfCompletion, 40 this)); 41} 42 43void UploadList::ClearDelegate() { 44 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 45 delegate_ = NULL; 46} 47 48void UploadList::LoadUploadListAndInformDelegateOfCompletion() { 49 LoadUploadList(); 50 BrowserThread::PostTask( 51 BrowserThread::UI, 52 FROM_HERE, 53 base::Bind(&UploadList::InformDelegateOfCompletion, this)); 54} 55 56void UploadList::LoadUploadList() { 57 if (base::PathExists(upload_log_path_)) { 58 std::string contents; 59 base::ReadFileToString(upload_log_path_, &contents); 60 std::vector<std::string> log_entries; 61 base::SplitStringAlongWhitespace(contents, &log_entries); 62 ClearUploads(); 63 ParseLogEntries(log_entries); 64 } 65} 66 67void UploadList::AppendUploadInfo(const UploadInfo& info) { 68 uploads_.push_back(info); 69} 70 71void UploadList::ClearUploads() { 72 uploads_.clear(); 73} 74 75void UploadList::ParseLogEntries( 76 const std::vector<std::string>& log_entries) { 77 std::vector<std::string>::const_reverse_iterator i; 78 for (i = log_entries.rbegin(); i != log_entries.rend(); ++i) { 79 std::vector<std::string> components; 80 base::SplitString(*i, ',', &components); 81 // Skip any blank (or corrupted) lines. 82 if (components.size() != 2 && components.size() != 3) 83 continue; 84 base::Time upload_time; 85 double seconds_since_epoch; 86 if (!components[0].empty()) { 87 if (!base::StringToDouble(components[0], &seconds_since_epoch)) 88 continue; 89 upload_time = base::Time::FromDoubleT(seconds_since_epoch); 90 } 91 UploadInfo info(components[1], upload_time); 92 if (components.size() == 3) 93 info.local_id = components[2]; 94 uploads_.push_back(info); 95 } 96} 97 98void UploadList::InformDelegateOfCompletion() { 99 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 100 if (delegate_) 101 delegate_->OnUploadListAvailable(); 102} 103 104void UploadList::GetUploads(unsigned int max_count, 105 std::vector<UploadInfo>* uploads) { 106 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 107 std::copy(uploads_.begin(), 108 uploads_.begin() + std::min<size_t>(uploads_.size(), max_count), 109 std::back_inserter(*uploads)); 110} 111