Home | History | Annotate | Download | only in history
      1 // Copyright (c) 2011 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/history/history_types.h"
      6 
      7 #include <limits>
      8 
      9 #include "base/logging.h"
     10 #include "base/stl_util-inl.h"
     11 
     12 namespace history {
     13 
     14 // URLRow ----------------------------------------------------------------------
     15 
     16 URLRow::URLRow() {
     17   Initialize();
     18 }
     19 
     20 URLRow::URLRow(const GURL& url) : url_(url) {
     21   // Initialize will not set the URL, so our initialization above will stay.
     22   Initialize();
     23 }
     24 
     25 URLRow::URLRow(const GURL& url, URLID id) : url_(url) {
     26   // Initialize will not set the URL, so our initialization above will stay.
     27   Initialize();
     28   // Initialize will zero the id_, so set it here.
     29   id_ = id;
     30 }
     31 
     32 URLRow::~URLRow() {
     33 }
     34 
     35 URLRow& URLRow::operator=(const URLRow& other) {
     36   id_ = other.id_;
     37   url_ = other.url_;
     38   title_ = other.title_;
     39   visit_count_ = other.visit_count_;
     40   typed_count_ = other.typed_count_;
     41   last_visit_ = other.last_visit_;
     42   hidden_ = other.hidden_;
     43   return *this;
     44 }
     45 
     46 void URLRow::Swap(URLRow* other) {
     47   std::swap(id_, other->id_);
     48   url_.Swap(&other->url_);
     49   title_.swap(other->title_);
     50   std::swap(visit_count_, other->visit_count_);
     51   std::swap(typed_count_, other->typed_count_);
     52   std::swap(last_visit_, other->last_visit_);
     53   std::swap(hidden_, other->hidden_);
     54 }
     55 
     56 void URLRow::Initialize() {
     57   id_ = 0;
     58   visit_count_ = 0;
     59   typed_count_ = 0;
     60   last_visit_ = base::Time();
     61   hidden_ = false;
     62 }
     63 
     64 // VisitRow --------------------------------------------------------------------
     65 
     66 VisitRow::VisitRow()
     67     : visit_id(0),
     68       url_id(0),
     69       referring_visit(0),
     70       transition(PageTransition::LINK),
     71       segment_id(0),
     72       is_indexed(false) {
     73 }
     74 
     75 VisitRow::VisitRow(URLID arg_url_id,
     76                    base::Time arg_visit_time,
     77                    VisitID arg_referring_visit,
     78                    PageTransition::Type arg_transition,
     79                    SegmentID arg_segment_id)
     80     : visit_id(0),
     81       url_id(arg_url_id),
     82       visit_time(arg_visit_time),
     83       referring_visit(arg_referring_visit),
     84       transition(arg_transition),
     85       segment_id(arg_segment_id),
     86       is_indexed(false) {
     87 }
     88 
     89 VisitRow::~VisitRow() {
     90 }
     91 
     92 // Favicons -------------------------------------------------------------------
     93 
     94 ImportedFaviconUsage::ImportedFaviconUsage() {
     95 }
     96 
     97 ImportedFaviconUsage::~ImportedFaviconUsage() {
     98 }
     99 
    100 // StarredEntry ----------------------------------------------------------------
    101 
    102 StarredEntry::StarredEntry()
    103     : id(0),
    104       parent_folder_id(0),
    105       folder_id(0),
    106       visual_order(0),
    107       type(URL),
    108       url_id(0) {
    109 }
    110 
    111 StarredEntry::~StarredEntry() {
    112 }
    113 
    114 void StarredEntry::Swap(StarredEntry* other) {
    115   std::swap(id, other->id);
    116   title.swap(other->title);
    117   std::swap(date_added, other->date_added);
    118   std::swap(parent_folder_id, other->parent_folder_id);
    119   std::swap(folder_id, other->folder_id);
    120   std::swap(visual_order, other->visual_order);
    121   std::swap(type, other->type);
    122   url.Swap(&other->url);
    123   std::swap(url_id, other->url_id);
    124   std::swap(date_folder_modified, other->date_folder_modified);
    125 }
    126 
    127 // URLResult -------------------------------------------------------------------
    128 
    129 URLResult::URLResult() {
    130 }
    131 
    132 URLResult::URLResult(const GURL& url, base::Time visit_time)
    133     : URLRow(url),
    134       visit_time_(visit_time) {
    135 }
    136 
    137 URLResult::URLResult(const GURL& url,
    138                      const Snippet::MatchPositions& title_matches)
    139     : URLRow(url) {
    140   title_match_positions_ = title_matches;
    141 }
    142 
    143 URLResult::~URLResult() {
    144 }
    145 
    146 void URLResult::SwapResult(URLResult* other) {
    147   URLRow::Swap(other);
    148   std::swap(visit_time_, other->visit_time_);
    149   snippet_.Swap(&other->snippet_);
    150   title_match_positions_.swap(other->title_match_positions_);
    151 }
    152 
    153 // QueryResults ----------------------------------------------------------------
    154 
    155 QueryResults::QueryResults() : reached_beginning_(false) {
    156 }
    157 
    158 QueryResults::~QueryResults() {
    159   // Free all the URL objects.
    160   STLDeleteContainerPointers(results_.begin(), results_.end());
    161 }
    162 
    163 const size_t* QueryResults::MatchesForURL(const GURL& url,
    164                                           size_t* num_matches) const {
    165   URLToResultIndices::const_iterator found = url_to_results_.find(url);
    166   if (found == url_to_results_.end()) {
    167     if (num_matches)
    168       *num_matches = 0;
    169     return NULL;
    170   }
    171 
    172   // All entries in the map should have at least one index, otherwise it
    173   // shouldn't be in the map.
    174   DCHECK(!found->second->empty());
    175   if (num_matches)
    176     *num_matches = found->second->size();
    177   return &found->second->front();
    178 }
    179 
    180 void QueryResults::Swap(QueryResults* other) {
    181   std::swap(first_time_searched_, other->first_time_searched_);
    182   std::swap(reached_beginning_, other->reached_beginning_);
    183   results_.swap(other->results_);
    184   url_to_results_.swap(other->url_to_results_);
    185 }
    186 
    187 void QueryResults::AppendURLBySwapping(URLResult* result) {
    188   URLResult* new_result = new URLResult;
    189   new_result->SwapResult(result);
    190 
    191   results_.push_back(new_result);
    192   AddURLUsageAtIndex(new_result->url(), results_.size() - 1);
    193 }
    194 
    195 void QueryResults::AppendResultsBySwapping(QueryResults* other,
    196                                            bool remove_dupes) {
    197   if (remove_dupes) {
    198     // Delete all entries in the other array that are already in this one.
    199     for (size_t i = 0; i < results_.size(); i++)
    200       other->DeleteURL(results_[i]->url());
    201   }
    202 
    203   if (first_time_searched_ > other->first_time_searched_)
    204     std::swap(first_time_searched_, other->first_time_searched_);
    205 
    206   if (reached_beginning_ != other->reached_beginning_)
    207     std::swap(reached_beginning_, other->reached_beginning_);
    208 
    209   for (size_t i = 0; i < other->results_.size(); i++) {
    210     // Just transfer pointer ownership.
    211     results_.push_back(other->results_[i]);
    212     AddURLUsageAtIndex(results_.back()->url(), results_.size() - 1);
    213   }
    214 
    215   // We just took ownership of all the results in the input vector.
    216   other->results_.clear();
    217   other->url_to_results_.clear();
    218 }
    219 
    220 void QueryResults::DeleteURL(const GURL& url) {
    221   // Delete all instances of this URL. We re-query each time since each
    222   // mutation will cause the indices to change.
    223   while (const size_t* match_indices = MatchesForURL(url, NULL))
    224     DeleteRange(*match_indices, *match_indices);
    225 }
    226 
    227 void QueryResults::DeleteRange(size_t begin, size_t end) {
    228   DCHECK(begin <= end && begin < size() && end < size());
    229 
    230   // First delete the pointers in the given range and store all the URLs that
    231   // were modified. We will delete references to these later.
    232   std::set<GURL> urls_modified;
    233   for (size_t i = begin; i <= end; i++) {
    234     urls_modified.insert(results_[i]->url());
    235     delete results_[i];
    236     results_[i] = NULL;
    237   }
    238 
    239   // Now just delete that range in the vector en masse (the STL ending is
    240   // exclusive, while ours is inclusive, hence the +1).
    241   results_.erase(results_.begin() + begin, results_.begin() + end + 1);
    242 
    243   // Delete the indicies referencing the deleted entries.
    244   for (std::set<GURL>::const_iterator url = urls_modified.begin();
    245        url != urls_modified.end(); ++url) {
    246     URLToResultIndices::iterator found = url_to_results_.find(*url);
    247     if (found == url_to_results_.end()) {
    248       NOTREACHED();
    249       continue;
    250     }
    251 
    252     // Need a signed loop type since we do -- which may take us to -1.
    253     for (int match = 0; match < static_cast<int>(found->second->size());
    254          match++) {
    255       if (found->second[match] >= begin && found->second[match] <= end) {
    256         // Remove this referece from the list.
    257         found->second->erase(found->second->begin() + match);
    258         match--;
    259       }
    260     }
    261 
    262     // Clear out an empty lists if we just made one.
    263     if (found->second->empty())
    264       url_to_results_.erase(found);
    265   }
    266 
    267   // Shift all other indices over to account for the removed ones.
    268   AdjustResultMap(end + 1, std::numeric_limits<size_t>::max(),
    269                   -static_cast<ptrdiff_t>(end - begin + 1));
    270 }
    271 
    272 void QueryResults::AddURLUsageAtIndex(const GURL& url, size_t index) {
    273   URLToResultIndices::iterator found = url_to_results_.find(url);
    274   if (found != url_to_results_.end()) {
    275     // The URL is already in the list, so we can just append the new index.
    276     found->second->push_back(index);
    277     return;
    278   }
    279 
    280   // Need to add a new entry for this URL.
    281   StackVector<size_t, 4> new_list;
    282   new_list->push_back(index);
    283   url_to_results_[url] = new_list;
    284 }
    285 
    286 void QueryResults::AdjustResultMap(size_t begin, size_t end, ptrdiff_t delta) {
    287   for (URLToResultIndices::iterator i = url_to_results_.begin();
    288        i != url_to_results_.end(); ++i) {
    289     for (size_t match = 0; match < i->second->size(); match++) {
    290       size_t match_index = i->second[match];
    291       if (match_index >= begin && match_index <= end)
    292         i->second[match] += delta;
    293     }
    294   }
    295 }
    296 
    297 // QueryOptions ----------------------------------------------------------------
    298 
    299 QueryOptions::QueryOptions() : max_count(0) {}
    300 
    301 void QueryOptions::SetRecentDayRange(int days_ago) {
    302   end_time = base::Time::Now();
    303   begin_time = end_time - base::TimeDelta::FromDays(days_ago);
    304 }
    305 
    306 // KeywordSearchTermVisit -----------------------------------------------------
    307 
    308 KeywordSearchTermVisit::KeywordSearchTermVisit() {}
    309 
    310 KeywordSearchTermVisit::~KeywordSearchTermVisit() {}
    311 
    312 // KeywordSearchTermRow --------------------------------------------------------
    313 
    314 KeywordSearchTermRow::KeywordSearchTermRow() : keyword_id(0), url_id(0) {}
    315 
    316 KeywordSearchTermRow::~KeywordSearchTermRow() {}
    317 
    318 // MostVisitedURL --------------------------------------------------------------
    319 
    320 MostVisitedURL::MostVisitedURL() {}
    321 
    322 MostVisitedURL::MostVisitedURL(const GURL& in_url,
    323                                const GURL& in_favicon_url,
    324                                const string16& in_title)
    325     : url(in_url),
    326       favicon_url(in_favicon_url),
    327       title(in_title) {
    328 }
    329 
    330 MostVisitedURL::~MostVisitedURL() {}
    331 
    332 // Images ---------------------------------------------------------------------
    333 
    334 Images::Images() {}
    335 
    336 Images::~Images() {}
    337 
    338 // TopSitesDelta --------------------------------------------------------------
    339 
    340 TopSitesDelta::TopSitesDelta() {}
    341 
    342 TopSitesDelta::~TopSitesDelta() {}
    343 
    344 // HistoryAddPageArgs ---------------------------------------------------------
    345 
    346 HistoryAddPageArgs::HistoryAddPageArgs(
    347     const GURL& arg_url,
    348     base::Time arg_time,
    349     const void* arg_id_scope,
    350     int32 arg_page_id,
    351     const GURL& arg_referrer,
    352     const history::RedirectList& arg_redirects,
    353     PageTransition::Type arg_transition,
    354     VisitSource arg_source,
    355     bool arg_did_replace_entry)
    356       : url(arg_url),
    357         time(arg_time),
    358         id_scope(arg_id_scope),
    359         page_id(arg_page_id),
    360         referrer(arg_referrer),
    361         redirects(arg_redirects),
    362         transition(arg_transition),
    363         visit_source(arg_source),
    364         did_replace_entry(arg_did_replace_entry) {
    365 }
    366 
    367 HistoryAddPageArgs::~HistoryAddPageArgs() {}
    368 
    369 HistoryAddPageArgs* HistoryAddPageArgs::Clone() const {
    370   return new HistoryAddPageArgs(
    371       url, time, id_scope, page_id, referrer, redirects, transition,
    372       visit_source, did_replace_entry);
    373 }
    374 
    375 ThumbnailMigration::ThumbnailMigration() {}
    376 
    377 ThumbnailMigration::~ThumbnailMigration() {}
    378 
    379 MostVisitedThumbnails::MostVisitedThumbnails() {}
    380 
    381 MostVisitedThumbnails::~MostVisitedThumbnails() {}
    382 
    383 // Autocomplete thresholds -----------------------------------------------------
    384 
    385 const int kLowQualityMatchTypedLimit = 1;
    386 const int kLowQualityMatchVisitLimit = 3;
    387 const int kLowQualityMatchAgeLimitInDays = 3;
    388 
    389 base::Time AutocompleteAgeThreshold() {
    390   return (base::Time::Now() -
    391           base::TimeDelta::FromDays(kLowQualityMatchAgeLimitInDays));
    392 }
    393 
    394 bool RowQualifiesAsSignificant(const URLRow& row,
    395                                const base::Time& threshold) {
    396   const base::Time& real_threshold =
    397       threshold.is_null() ? AutocompleteAgeThreshold() : threshold;
    398   return (row.typed_count() > kLowQualityMatchTypedLimit) ||
    399          (row.visit_count() > kLowQualityMatchVisitLimit) ||
    400          (row.last_visit() >= real_threshold);
    401 }
    402 
    403 // IconMapping ----------------------------------------------------------------
    404 
    405 IconMapping::IconMapping()
    406     : mapping_id(0),
    407       icon_id(0),
    408       icon_type(INVALID_ICON) {
    409 }
    410 
    411 IconMapping::~IconMapping() {}
    412 
    413 
    414 FaviconData::FaviconData()
    415   : known_icon(false),
    416     expired(false),
    417     icon_type(history::INVALID_ICON) {
    418 }
    419 
    420 FaviconData::~FaviconData() {}
    421 
    422 bool FaviconData::is_valid() {
    423   return known_icon && image_data.get() && image_data->size();
    424 }
    425 
    426 }  // namespace history
    427