Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(558)

Side by Side Diff: chrome/browser/history/visit_database.cc

Issue 9071014: Database usage adjustment for .../history (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Review fixes Created 8 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. 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 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/history/visit_database.h" 5 #include "chrome/browser/history/visit_database.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <limits> 8 #include <limits>
9 #include <map> 9 #include <map>
10 #include <set> 10 #include <set>
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after
97 visit->visit_id = statement.ColumnInt64(0); 97 visit->visit_id = statement.ColumnInt64(0);
98 visit->url_id = statement.ColumnInt64(1); 98 visit->url_id = statement.ColumnInt64(1);
99 visit->visit_time = base::Time::FromInternalValue(statement.ColumnInt64(2)); 99 visit->visit_time = base::Time::FromInternalValue(statement.ColumnInt64(2));
100 visit->referring_visit = statement.ColumnInt64(3); 100 visit->referring_visit = statement.ColumnInt64(3);
101 visit->transition = content::PageTransitionFromInt(statement.ColumnInt(4)); 101 visit->transition = content::PageTransitionFromInt(statement.ColumnInt(4));
102 visit->segment_id = statement.ColumnInt64(5); 102 visit->segment_id = statement.ColumnInt64(5);
103 visit->is_indexed = !!statement.ColumnInt(6); 103 visit->is_indexed = !!statement.ColumnInt(6);
104 } 104 }
105 105
106 // static 106 // static
107 void VisitDatabase::FillVisitVector(sql::Statement& statement, 107 bool VisitDatabase::FillVisitVector(sql::Statement& statement,
108 VisitVector* visits) { 108 VisitVector* visits) {
109 if (!statement.is_valid())
110 return false;
111
109 while (statement.Step()) { 112 while (statement.Step()) {
110 history::VisitRow visit; 113 history::VisitRow visit;
111 FillVisitRow(statement, &visit); 114 FillVisitRow(statement, &visit);
112 visits->push_back(visit); 115 visits->push_back(visit);
113 } 116 }
117 return true;
Scott Hess - ex-Googler 2012/01/10 22:29:49 WDYT about removing the is_valid() check and retur
Greg Billock 2012/01/11 23:42:12 Done.
114 } 118 }
115 119
116 VisitID VisitDatabase::AddVisit(VisitRow* visit, VisitSource source) { 120 VisitID VisitDatabase::AddVisit(VisitRow* visit, VisitSource source) {
117 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 121 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
118 "INSERT INTO visits " 122 "INSERT INTO visits "
119 "(url, visit_time, from_visit, transition, segment_id, is_indexed) " 123 "(url, visit_time, from_visit, transition, segment_id, is_indexed) "
120 "VALUES (?,?,?,?,?,?)")); 124 "VALUES (?,?,?,?,?,?)"));
121 if (!statement) {
122 VLOG(0) << "Failed to build visit insert statement: "
123 << "url_id = " << visit->url_id;
124 return 0;
125 }
126
127 statement.BindInt64(0, visit->url_id); 125 statement.BindInt64(0, visit->url_id);
128 statement.BindInt64(1, visit->visit_time.ToInternalValue()); 126 statement.BindInt64(1, visit->visit_time.ToInternalValue());
129 statement.BindInt64(2, visit->referring_visit); 127 statement.BindInt64(2, visit->referring_visit);
130 statement.BindInt64(3, visit->transition); 128 statement.BindInt64(3, visit->transition);
131 statement.BindInt64(4, visit->segment_id); 129 statement.BindInt64(4, visit->segment_id);
132 statement.BindInt64(5, visit->is_indexed); 130 statement.BindInt64(5, visit->is_indexed);
133 131
134 if (!statement.Run()) { 132 if (!statement.Run()) {
135 VLOG(0) << "Failed to execute visit insert statement: " 133 VLOG(0) << "Failed to execute visit insert statement: "
136 << "url_id = " << visit->url_id; 134 << "url_id = " << visit->url_id;
137 return 0; 135 return 0;
138 } 136 }
139 137
140 visit->visit_id = GetDB().GetLastInsertRowId(); 138 visit->visit_id = GetDB().GetLastInsertRowId();
141 139
142 if (source != SOURCE_BROWSED) { 140 if (source != SOURCE_BROWSED) {
143 // Record the source of this visit when it is not browsed. 141 // Record the source of this visit when it is not browsed.
144 sql::Statement statement1(GetDB().GetCachedStatement(SQL_FROM_HERE, 142 sql::Statement statement1(GetDB().GetCachedStatement(SQL_FROM_HERE,
145 "INSERT INTO visit_source (id, source) VALUES (?,?)")); 143 "INSERT INTO visit_source (id, source) VALUES (?,?)"));
146 if (!statement1.is_valid()) {
147 VLOG(0) << "Failed to build visit_source insert statement: "
148 << "url_id = " << visit->visit_id;
149 return 0;
150 }
151
152 statement1.BindInt64(0, visit->visit_id); 144 statement1.BindInt64(0, visit->visit_id);
153 statement1.BindInt64(1, source); 145 statement1.BindInt64(1, source);
146
154 if (!statement1.Run()) { 147 if (!statement1.Run()) {
155 VLOG(0) << "Failed to execute visit_source insert statement: " 148 VLOG(0) << "Failed to execute visit_source insert statement: "
156 << "url_id = " << visit->visit_id; 149 << "url_id = " << visit->visit_id;
157 return 0; 150 return 0;
158 } 151 }
159 } 152 }
160 153
161 return visit->visit_id; 154 return visit->visit_id;
162 } 155 }
163 156
164 void VisitDatabase::DeleteVisit(const VisitRow& visit) { 157 void VisitDatabase::DeleteVisit(const VisitRow& visit) {
165 // Patch around this visit. Any visits that this went to will now have their 158 // Patch around this visit. Any visits that this went to will now have their
166 // "source" be the deleted visit's source. 159 // "source" be the deleted visit's source.
167 sql::Statement update_chain(GetDB().GetCachedStatement(SQL_FROM_HERE, 160 sql::Statement update_chain(GetDB().GetCachedStatement(SQL_FROM_HERE,
168 "UPDATE visits SET from_visit=? WHERE from_visit=?")); 161 "UPDATE visits SET from_visit=? WHERE from_visit=?"));
169 if (!update_chain)
170 return;
171 update_chain.BindInt64(0, visit.referring_visit); 162 update_chain.BindInt64(0, visit.referring_visit);
172 update_chain.BindInt64(1, visit.visit_id); 163 update_chain.BindInt64(1, visit.visit_id);
173 update_chain.Run(); 164 if (!update_chain.Run())
165 return;
174 166
175 // Now delete the actual visit. 167 // Now delete the actual visit.
176 sql::Statement del(GetDB().GetCachedStatement(SQL_FROM_HERE, 168 sql::Statement del(GetDB().GetCachedStatement(SQL_FROM_HERE,
177 "DELETE FROM visits WHERE id=?")); 169 "DELETE FROM visits WHERE id=?"));
178 if (!del) 170 del.BindInt64(0, visit.visit_id);
171 if (!del.Run())
179 return; 172 return;
180 del.BindInt64(0, visit.visit_id);
181 del.Run();
182 173
183 // Try to delete the entry in visit_source table as well. 174 // Try to delete the entry in visit_source table as well.
184 // If the visit was browsed, there is no corresponding entry in visit_source 175 // If the visit was browsed, there is no corresponding entry in visit_source
185 // table, and nothing will be deleted. 176 // table, and nothing will be deleted.
186 del.Assign(GetDB().GetCachedStatement(SQL_FROM_HERE, 177 del.Assign(GetDB().GetCachedStatement(SQL_FROM_HERE,
187 "DELETE FROM visit_source WHERE id=?")); 178 "DELETE FROM visit_source WHERE id=?"));
188 if (!del.is_valid())
189 return;
190 del.BindInt64(0, visit.visit_id); 179 del.BindInt64(0, visit.visit_id);
191 del.Run(); 180 del.Run();
192 } 181 }
193 182
194 bool VisitDatabase::GetRowForVisit(VisitID visit_id, VisitRow* out_visit) { 183 bool VisitDatabase::GetRowForVisit(VisitID visit_id, VisitRow* out_visit) {
195 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 184 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
196 "SELECT" HISTORY_VISIT_ROW_FIELDS "FROM visits WHERE id=?")); 185 "SELECT" HISTORY_VISIT_ROW_FIELDS "FROM visits WHERE id=?"));
197 if (!statement) 186 statement.BindInt64(0, visit_id);
198 return false;
199 187
200 statement.BindInt64(0, visit_id);
201 if (!statement.Step()) 188 if (!statement.Step())
202 return false; 189 return false;
203 190
204 FillVisitRow(statement, out_visit); 191 FillVisitRow(statement, out_visit);
205 192
206 // We got a different visit than we asked for, something is wrong. 193 // We got a different visit than we asked for, something is wrong.
207 DCHECK_EQ(visit_id, out_visit->visit_id); 194 DCHECK_EQ(visit_id, out_visit->visit_id);
208 if (visit_id != out_visit->visit_id) 195 if (visit_id != out_visit->visit_id)
209 return false; 196 return false;
210 197
211 return true; 198 return true;
212 } 199 }
213 200
214 bool VisitDatabase::UpdateVisitRow(const VisitRow& visit) { 201 bool VisitDatabase::UpdateVisitRow(const VisitRow& visit) {
215 // Don't store inconsistent data to the database. 202 // Don't store inconsistent data to the database.
216 DCHECK_NE(visit.visit_id, visit.referring_visit); 203 DCHECK_NE(visit.visit_id, visit.referring_visit);
217 if (visit.visit_id == visit.referring_visit) 204 if (visit.visit_id == visit.referring_visit)
218 return false; 205 return false;
219 206
220 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 207 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
221 "UPDATE visits SET " 208 "UPDATE visits SET "
222 "url=?,visit_time=?,from_visit=?,transition=?,segment_id=?,is_indexed=? " 209 "url=?,visit_time=?,from_visit=?,transition=?,segment_id=?,is_indexed=? "
223 "WHERE id=?")); 210 "WHERE id=?"));
224 if (!statement)
225 return false;
226
227 statement.BindInt64(0, visit.url_id); 211 statement.BindInt64(0, visit.url_id);
228 statement.BindInt64(1, visit.visit_time.ToInternalValue()); 212 statement.BindInt64(1, visit.visit_time.ToInternalValue());
229 statement.BindInt64(2, visit.referring_visit); 213 statement.BindInt64(2, visit.referring_visit);
230 statement.BindInt64(3, visit.transition); 214 statement.BindInt64(3, visit.transition);
231 statement.BindInt64(4, visit.segment_id); 215 statement.BindInt64(4, visit.segment_id);
232 statement.BindInt64(5, visit.is_indexed); 216 statement.BindInt64(5, visit.is_indexed);
233 statement.BindInt64(6, visit.visit_id); 217 statement.BindInt64(6, visit.visit_id);
218
234 return statement.Run(); 219 return statement.Run();
235 } 220 }
236 221
237 bool VisitDatabase::GetVisitsForURL(URLID url_id, VisitVector* visits) { 222 bool VisitDatabase::GetVisitsForURL(URLID url_id, VisitVector* visits) {
238 visits->clear(); 223 visits->clear();
239 224
240 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 225 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
241 "SELECT" HISTORY_VISIT_ROW_FIELDS 226 "SELECT" HISTORY_VISIT_ROW_FIELDS
242 "FROM visits " 227 "FROM visits "
243 "WHERE url=? " 228 "WHERE url=? "
244 "ORDER BY visit_time ASC")); 229 "ORDER BY visit_time ASC"));
245 if (!statement)
246 return false;
247
248 statement.BindInt64(0, url_id); 230 statement.BindInt64(0, url_id);
249 FillVisitVector(statement, visits); 231 return FillVisitVector(statement, visits);
250 return true;
251 } 232 }
252 233
253 bool VisitDatabase::GetIndexedVisitsForURL(URLID url_id, VisitVector* visits) { 234 bool VisitDatabase::GetIndexedVisitsForURL(URLID url_id, VisitVector* visits) {
254 visits->clear(); 235 visits->clear();
255 236
256 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 237 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
257 "SELECT" HISTORY_VISIT_ROW_FIELDS 238 "SELECT" HISTORY_VISIT_ROW_FIELDS
258 "FROM visits " 239 "FROM visits "
259 "WHERE url=? AND is_indexed=1")); 240 "WHERE url=? AND is_indexed=1"));
260 if (!statement)
261 return false;
262
263 statement.BindInt64(0, url_id); 241 statement.BindInt64(0, url_id);
264 FillVisitVector(statement, visits); 242 return FillVisitVector(statement, visits);
265 return true;
266 } 243 }
267 244
268 void VisitDatabase::GetAllVisitsInRange(base::Time begin_time, 245 bool VisitDatabase::GetAllVisitsInRange(base::Time begin_time,
269 base::Time end_time, 246 base::Time end_time,
270 int max_results, 247 int max_results,
271 VisitVector* visits) { 248 VisitVector* visits) {
272 visits->clear(); 249 visits->clear();
273 250
274 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 251 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
275 "SELECT" HISTORY_VISIT_ROW_FIELDS "FROM visits " 252 "SELECT" HISTORY_VISIT_ROW_FIELDS "FROM visits "
276 "WHERE visit_time >= ? AND visit_time < ?" 253 "WHERE visit_time >= ? AND visit_time < ?"
277 "ORDER BY visit_time LIMIT ?")); 254 "ORDER BY visit_time LIMIT ?"));
278 if (!statement)
279 return;
280 255
281 // See GetVisibleVisitsInRange for more info on how these times are bound. 256 // See GetVisibleVisitsInRange for more info on how these times are bound.
282 int64 end = end_time.ToInternalValue(); 257 int64 end = end_time.ToInternalValue();
283 statement.BindInt64(0, begin_time.ToInternalValue()); 258 statement.BindInt64(0, begin_time.ToInternalValue());
284 statement.BindInt64(1, end ? end : std::numeric_limits<int64>::max()); 259 statement.BindInt64(1, end ? end : std::numeric_limits<int64>::max());
285 statement.BindInt64(2, 260 statement.BindInt64(2,
286 max_results ? max_results : std::numeric_limits<int64>::max()); 261 max_results ? max_results : std::numeric_limits<int64>::max());
287 262
288 FillVisitVector(statement, visits); 263 return FillVisitVector(statement, visits);
289 } 264 }
290 265
291 void VisitDatabase::GetVisitsInRangeForTransition( 266 bool VisitDatabase::GetVisitsInRangeForTransition(
292 base::Time begin_time, 267 base::Time begin_time,
293 base::Time end_time, 268 base::Time end_time,
294 int max_results, 269 int max_results,
295 content::PageTransition transition, 270 content::PageTransition transition,
296 VisitVector* visits) { 271 VisitVector* visits) {
297 DCHECK(visits); 272 DCHECK(visits);
298 visits->clear(); 273 visits->clear();
299 274
300 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 275 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
301 "SELECT" HISTORY_VISIT_ROW_FIELDS "FROM visits " 276 "SELECT" HISTORY_VISIT_ROW_FIELDS "FROM visits "
302 "WHERE visit_time >= ? AND visit_time < ? " 277 "WHERE visit_time >= ? AND visit_time < ? "
303 "AND (transition & ?) == ?" 278 "AND (transition & ?) == ?"
304 "ORDER BY visit_time LIMIT ?")); 279 "ORDER BY visit_time LIMIT ?"));
305 if (!statement)
306 return;
307 280
308 // See GetVisibleVisitsInRange for more info on how these times are bound. 281 // See GetVisibleVisitsInRange for more info on how these times are bound.
309 int64 end = end_time.ToInternalValue(); 282 int64 end = end_time.ToInternalValue();
310 statement.BindInt64(0, begin_time.ToInternalValue()); 283 statement.BindInt64(0, begin_time.ToInternalValue());
311 statement.BindInt64(1, end ? end : std::numeric_limits<int64>::max()); 284 statement.BindInt64(1, end ? end : std::numeric_limits<int64>::max());
312 statement.BindInt(2, content::PAGE_TRANSITION_CORE_MASK); 285 statement.BindInt(2, content::PAGE_TRANSITION_CORE_MASK);
313 statement.BindInt(3, transition); 286 statement.BindInt(3, transition);
314 statement.BindInt64(4, 287 statement.BindInt64(4,
315 max_results ? max_results : std::numeric_limits<int64>::max()); 288 max_results ? max_results : std::numeric_limits<int64>::max());
316 289
317 FillVisitVector(statement, visits); 290 return FillVisitVector(statement, visits);
318 } 291 }
319 292
320 void VisitDatabase::GetVisibleVisitsInRange(base::Time begin_time, 293 void VisitDatabase::GetVisibleVisitsInRange(base::Time begin_time,
321 base::Time end_time, 294 base::Time end_time,
322 int max_count, 295 int max_count,
323 VisitVector* visits) { 296 VisitVector* visits) {
324 visits->clear(); 297 visits->clear();
325 // The visit_time values can be duplicated in a redirect chain, so we sort 298 // The visit_time values can be duplicated in a redirect chain, so we sort
326 // by id too, to ensure a consistent ordering just in case. 299 // by id too, to ensure a consistent ordering just in case.
327 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 300 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
328 "SELECT" HISTORY_VISIT_ROW_FIELDS "FROM visits " 301 "SELECT" HISTORY_VISIT_ROW_FIELDS "FROM visits "
329 "WHERE visit_time >= ? AND visit_time < ? " 302 "WHERE visit_time >= ? AND visit_time < ? "
330 "AND (transition & ?) != 0 " // CHAIN_END 303 "AND (transition & ?) != 0 " // CHAIN_END
331 "AND (transition & ?) NOT IN (?, ?, ?) " // NO SUBFRAME or 304 "AND (transition & ?) NOT IN (?, ?, ?) " // NO SUBFRAME or
332 // KEYWORD_GENERATED 305 // KEYWORD_GENERATED
333 "ORDER BY visit_time DESC, id DESC")); 306 "ORDER BY visit_time DESC, id DESC"));
334 if (!statement)
335 return;
336 307
337 // Note that we use min/max values for querying unlimited ranges of time using 308 // Note that we use min/max values for querying unlimited ranges of time using
338 // the same statement. Since the time has an index, this will be about the 309 // the same statement. Since the time has an index, this will be about the
339 // same amount of work as just doing a query for everything with no qualifier. 310 // same amount of work as just doing a query for everything with no qualifier.
340 int64 end = end_time.ToInternalValue(); 311 int64 end = end_time.ToInternalValue();
341 statement.BindInt64(0, begin_time.ToInternalValue()); 312 statement.BindInt64(0, begin_time.ToInternalValue());
342 statement.BindInt64(1, end ? end : std::numeric_limits<int64>::max()); 313 statement.BindInt64(1, end ? end : std::numeric_limits<int64>::max());
343 statement.BindInt(2, content::PAGE_TRANSITION_CHAIN_END); 314 statement.BindInt(2, content::PAGE_TRANSITION_CHAIN_END);
344 statement.BindInt(3, content::PAGE_TRANSITION_CORE_MASK); 315 statement.BindInt(3, content::PAGE_TRANSITION_CORE_MASK);
345 statement.BindInt(4, content::PAGE_TRANSITION_AUTO_SUBFRAME); 316 statement.BindInt(4, content::PAGE_TRANSITION_AUTO_SUBFRAME);
(...skipping 17 matching lines...) Expand all
363 334
364 VisitID VisitDatabase::GetMostRecentVisitForURL(URLID url_id, 335 VisitID VisitDatabase::GetMostRecentVisitForURL(URLID url_id,
365 VisitRow* visit_row) { 336 VisitRow* visit_row) {
366 // The visit_time values can be duplicated in a redirect chain, so we sort 337 // The visit_time values can be duplicated in a redirect chain, so we sort
367 // by id too, to ensure a consistent ordering just in case. 338 // by id too, to ensure a consistent ordering just in case.
368 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 339 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
369 "SELECT" HISTORY_VISIT_ROW_FIELDS "FROM visits " 340 "SELECT" HISTORY_VISIT_ROW_FIELDS "FROM visits "
370 "WHERE url=? " 341 "WHERE url=? "
371 "ORDER BY visit_time DESC, id DESC " 342 "ORDER BY visit_time DESC, id DESC "
372 "LIMIT 1")); 343 "LIMIT 1"));
373 if (!statement)
374 return 0;
375
376 statement.BindInt64(0, url_id); 344 statement.BindInt64(0, url_id);
377 if (!statement.Step()) 345 if (!statement.Step())
378 return 0; // No visits for this URL. 346 return 0; // No visits for this URL.
379 347
380 if (visit_row) { 348 if (visit_row) {
381 FillVisitRow(statement, visit_row); 349 FillVisitRow(statement, visit_row);
382 return visit_row->visit_id; 350 return visit_row->visit_id;
383 } 351 }
384 return statement.ColumnInt64(0); 352 return statement.ColumnInt64(0);
385 } 353 }
386 354
387 bool VisitDatabase::GetMostRecentVisitsForURL(URLID url_id, 355 bool VisitDatabase::GetMostRecentVisitsForURL(URLID url_id,
388 int max_results, 356 int max_results,
389 VisitVector* visits) { 357 VisitVector* visits) {
390 visits->clear(); 358 visits->clear();
391 359
392 // The visit_time values can be duplicated in a redirect chain, so we sort 360 // The visit_time values can be duplicated in a redirect chain, so we sort
393 // by id too, to ensure a consistent ordering just in case. 361 // by id too, to ensure a consistent ordering just in case.
394 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 362 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
395 "SELECT" HISTORY_VISIT_ROW_FIELDS 363 "SELECT" HISTORY_VISIT_ROW_FIELDS
396 "FROM visits " 364 "FROM visits "
397 "WHERE url=? " 365 "WHERE url=? "
398 "ORDER BY visit_time DESC, id DESC " 366 "ORDER BY visit_time DESC, id DESC "
399 "LIMIT ?")); 367 "LIMIT ?"));
400 if (!statement)
401 return false;
402
403 statement.BindInt64(0, url_id); 368 statement.BindInt64(0, url_id);
404 statement.BindInt(1, max_results); 369 statement.BindInt(1, max_results);
405 FillVisitVector(statement, visits); 370
406 return true; 371 return FillVisitVector(statement, visits);
407 } 372 }
408 373
409 bool VisitDatabase::GetRedirectFromVisit(VisitID from_visit, 374 bool VisitDatabase::GetRedirectFromVisit(VisitID from_visit,
410 VisitID* to_visit, 375 VisitID* to_visit,
411 GURL* to_url) { 376 GURL* to_url) {
412 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 377 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
413 "SELECT v.id,u.url " 378 "SELECT v.id,u.url "
414 "FROM visits v JOIN urls u ON v.url = u.id " 379 "FROM visits v JOIN urls u ON v.url = u.id "
415 "WHERE v.from_visit = ? " 380 "WHERE v.from_visit = ? "
416 "AND (v.transition & ?) != 0")); // IS_REDIRECT_MASK 381 "AND (v.transition & ?) != 0")); // IS_REDIRECT_MASK
417 if (!statement) 382 if (!statement.is_valid())
418 return false; 383 return false;
Scott Hess - ex-Googler 2012/01/10 22:29:49 !Step() below should cover this, though the commen
Greg Billock 2012/01/11 23:42:12 Done.
419 384
420 statement.BindInt64(0, from_visit); 385 statement.BindInt64(0, from_visit);
421 statement.BindInt(1, content::PAGE_TRANSITION_IS_REDIRECT_MASK); 386 statement.BindInt(1, content::PAGE_TRANSITION_IS_REDIRECT_MASK);
422 387
423 if (!statement.Step()) 388 if (!statement.Step())
424 return false; // No redirect from this visit. 389 return false; // No redirect from this visit.
425 if (to_visit) 390 if (to_visit)
426 *to_visit = statement.ColumnInt64(0); 391 *to_visit = statement.ColumnInt64(0);
427 if (to_url) 392 if (to_url)
428 *to_url = GURL(statement.ColumnString(1)); 393 *to_url = GURL(statement.ColumnString(1));
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after
472 return false; 437 return false;
473 438
474 // We also want to restrict ourselves to main frame navigations that are not 439 // We also want to restrict ourselves to main frame navigations that are not
475 // in the middle of redirect chains, hence the transition checks. 440 // in the middle of redirect chains, hence the transition checks.
476 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 441 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
477 "SELECT MIN(v.visit_time), COUNT(*) " 442 "SELECT MIN(v.visit_time), COUNT(*) "
478 "FROM visits v INNER JOIN urls u ON v.url = u.id " 443 "FROM visits v INNER JOIN urls u ON v.url = u.id "
479 "WHERE u.url >= ? AND u.url < ? " 444 "WHERE u.url >= ? AND u.url < ? "
480 "AND (transition & ?) != 0 " 445 "AND (transition & ?) != 0 "
481 "AND (transition & ?) NOT IN (?, ?, ?)")); 446 "AND (transition & ?) NOT IN (?, ?, ?)"));
482 if (!statement)
483 return false;
484
485 statement.BindString(0, host_query_min); 447 statement.BindString(0, host_query_min);
486 statement.BindString(1, 448 statement.BindString(1,
487 host_query_min.substr(0, host_query_min.size() - 1) + '0'); 449 host_query_min.substr(0, host_query_min.size() - 1) + '0');
488 statement.BindInt(2, content::PAGE_TRANSITION_CHAIN_END); 450 statement.BindInt(2, content::PAGE_TRANSITION_CHAIN_END);
489 statement.BindInt(3, content::PAGE_TRANSITION_CORE_MASK); 451 statement.BindInt(3, content::PAGE_TRANSITION_CORE_MASK);
490 statement.BindInt(4, content::PAGE_TRANSITION_AUTO_SUBFRAME); 452 statement.BindInt(4, content::PAGE_TRANSITION_AUTO_SUBFRAME);
491 statement.BindInt(5, content::PAGE_TRANSITION_MANUAL_SUBFRAME); 453 statement.BindInt(5, content::PAGE_TRANSITION_MANUAL_SUBFRAME);
492 statement.BindInt(6, content::PAGE_TRANSITION_KEYWORD_GENERATED); 454 statement.BindInt(6, content::PAGE_TRANSITION_KEYWORD_GENERATED);
493 455
494 if (!statement.Step()) { 456 if (!statement.Step()) {
495 // We've never been to this page before. 457 // We've never been to this page before.
496 *count = 0; 458 *count = 0;
497 return true; 459 return true;
498 } 460 }
499 461
462 if (!statement.Succeeded())
463 return false;
464
500 *first_visit = base::Time::FromInternalValue(statement.ColumnInt64(0)); 465 *first_visit = base::Time::FromInternalValue(statement.ColumnInt64(0));
501 *count = statement.ColumnInt(1); 466 *count = statement.ColumnInt(1);
502 return true; 467 return true;
503 } 468 }
504 469
505 bool VisitDatabase::GetStartDate(base::Time* first_visit) { 470 bool VisitDatabase::GetStartDate(base::Time* first_visit) {
506 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE, 471 sql::Statement statement(GetDB().GetCachedStatement(SQL_FROM_HERE,
507 "SELECT MIN(visit_time) FROM visits WHERE visit_time != 0")); 472 "SELECT MIN(visit_time) FROM visits WHERE visit_time != 0"));
508 if (!statement || !statement.Step() || statement.ColumnInt64(0) == 0) { 473 if (!statement.Step() || statement.ColumnInt64(0) == 0) {
Scott Hess - ex-Googler 2012/01/10 22:29:49 Odd. I wonder how this code came to be written th
509 *first_visit = base::Time::Now(); 474 *first_visit = base::Time::Now();
510 return false; 475 return false;
511 } 476 }
512 *first_visit = base::Time::FromInternalValue(statement.ColumnInt64(0)); 477 *first_visit = base::Time::FromInternalValue(statement.ColumnInt64(0));
513 return true; 478 return true;
514 } 479 }
515 480
516 void VisitDatabase::GetVisitsSource(const VisitVector& visits, 481 void VisitDatabase::GetVisitsSource(const VisitVector& visits,
517 VisitSourceMap* sources) { 482 VisitSourceMap* sources) {
518 DCHECK(sources); 483 DCHECK(sources);
(...skipping 13 matching lines...) Expand all
532 std::string sql = "SELECT id,source FROM visit_source "; 497 std::string sql = "SELECT id,source FROM visit_source ";
533 sql.append("WHERE id IN ("); 498 sql.append("WHERE id IN (");
534 // Append all the ids in the statement. 499 // Append all the ids in the statement.
535 for (size_t j = start_index; j < end_index; j++) { 500 for (size_t j = start_index; j < end_index; j++) {
536 if (j != start_index) 501 if (j != start_index)
537 sql.push_back(','); 502 sql.push_back(',');
538 sql.append(base::Int64ToString(visits[j].visit_id)); 503 sql.append(base::Int64ToString(visits[j].visit_id));
539 } 504 }
540 sql.append(") ORDER BY id"); 505 sql.append(") ORDER BY id");
541 sql::Statement statement(GetDB().GetUniqueStatement(sql.c_str())); 506 sql::Statement statement(GetDB().GetUniqueStatement(sql.c_str()));
542 if (!statement)
543 return;
544 507
545 // Get the source entries out of the query result. 508 // Get the source entries out of the query result.
546 while (statement.Step()) { 509 while (statement.Step()) {
547 std::pair<VisitID, VisitSource> source_entry(statement.ColumnInt64(0), 510 std::pair<VisitID, VisitSource> source_entry(statement.ColumnInt64(0),
548 static_cast<VisitSource>(statement.ColumnInt(1))); 511 static_cast<VisitSource>(statement.ColumnInt(1)));
549 sources->insert(source_entry); 512 sources->insert(source_entry);
550 } 513 }
551 } 514 }
552 } 515 }
553 516
554 } // namespace history 517 } // namespace history
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698