| Index: chrome/browser/predictors/resource_prefetch_predictor_tables.cc
|
| diff --git a/chrome/browser/predictors/resource_prefetch_predictor_tables.cc b/chrome/browser/predictors/resource_prefetch_predictor_tables.cc
|
| index 75cfb3942947b5820fb761d5309cb80159e00c25..8ca0fe1e4e1764265702720d80d523513801a344 100644
|
| --- a/chrome/browser/predictors/resource_prefetch_predictor_tables.cc
|
| +++ b/chrome/browser/predictors/resource_prefetch_predictor_tables.cc
|
| @@ -24,13 +24,19 @@ using sql::Statement;
|
| namespace {
|
|
|
| using ResourceRow = predictors::ResourcePrefetchPredictorTables::ResourceRow;
|
| +using RedirectRow = predictors::ResourcePrefetchPredictorTables::RedirectRow;
|
| +using RedirectData = predictors::ResourcePrefetchPredictorTables::RedirectData;
|
|
|
| const char kMetadataTableName[] = "resource_prefetch_predictor_metadata";
|
| -const char kUrlResourceTableName[] = "resource_prefetch_predictor_url";
|
| +const char kUrlResourceTableName[] = "resource_prefetch_predictor_url_resource";
|
| const char kUrlMetadataTableName[] = "resource_prefetch_predictor_url_metadata";
|
| -const char kHostResourceTableName[] = "resource_prefetch_predictor_host";
|
| +const char kUrlRedirectTableName[] = "resource_prefetch_predictor_url_redirect";
|
| +const char kHostResourceTableName[] =
|
| + "resource_prefetch_predictor_host_resource";
|
| const char kHostMetadataTableName[] =
|
| "resource_prefetch_predictor_host_metadata";
|
| +const char kHostRedirectTableName[] =
|
| + "resource_prefetch_predictor_host_redirect";
|
|
|
| const char kCreateGlobalMetadataStatementTemplate[] =
|
| "CREATE TABLE %s ( "
|
| @@ -47,9 +53,16 @@ const char kCreateMetadataTableStatementTemplate[] =
|
| "main_page_url TEXT, "
|
| "last_visit_time INTEGER, "
|
| "PRIMARY KEY(main_page_url))";
|
| +const char kCreateRedirectTableStatementTemplate[] =
|
| + "CREATE TABLE %s ( "
|
| + "main_page_url TEXT, "
|
| + "proto BLOB, "
|
| + "PRIMARY KEY(main_page_url))";
|
|
|
| const char kInsertResourceTableStatementTemplate[] =
|
| "INSERT INTO %s (main_page_url, resource_url, proto) VALUES (?,?,?)";
|
| +const char kInsertRedirectTableStatementTemplate[] =
|
| + "INSERT INTO %s (main_page_url, proto) VALUES (?,?)";
|
| const char kInsertMetadataTableStatementTemplate[] =
|
| "INSERT INTO %s (main_page_url, last_visit_time) VALUES (?,?)";
|
| const char kDeleteStatementTemplate[] = "DELETE FROM %s WHERE main_page_url=?";
|
| @@ -68,6 +81,18 @@ void BindResourceRowToStatement(const ResourceRow& row,
|
| statement->BindBlob(2, &proto_buffer[0], size);
|
| }
|
|
|
| +void BindRedirectDataToStatement(const RedirectData& data,
|
| + Statement* statement) {
|
| + chrome_browser_predictors::RedirectProto proto;
|
| + data.ToProto(&proto);
|
| + int size = proto.ByteSize();
|
| + std::vector<char> proto_buffer(size);
|
| + proto.SerializeToArray(&proto_buffer[0], size);
|
| +
|
| + statement->BindString(0, data.primary_key);
|
| + statement->BindBlob(1, &proto_buffer[0], size);
|
| +}
|
| +
|
| bool StepAndInitializeResourceRow(Statement* statement,
|
| ResourceRow* row,
|
| std::string* primary_key) {
|
| @@ -89,6 +114,25 @@ bool StepAndInitializeResourceRow(Statement* statement,
|
| return true;
|
| }
|
|
|
| +bool StepAndInitializeRedirectData(Statement* statement,
|
| + RedirectData* redirect_data,
|
| + std::string* primary_key) {
|
| + if (!statement->Step())
|
| + return false;
|
| +
|
| + *primary_key = statement->ColumnString(0);
|
| + redirect_data->primary_key = *primary_key;
|
| +
|
| + int size = statement->ColumnByteLength(1);
|
| + const void* data = statement->ColumnBlob(1);
|
| + DCHECK(data);
|
| + chrome_browser_predictors::RedirectProto proto;
|
| + proto.ParseFromArray(data, size);
|
| + RedirectData::FromProto(proto, redirect_data);
|
| +
|
| + return true;
|
| +}
|
| +
|
| } // namespace
|
|
|
| namespace predictors {
|
| @@ -168,6 +212,21 @@ bool ResourceRow::operator==(const ResourceRow& rhs) const {
|
| always_revalidate == rhs.always_revalidate && score == rhs.score;
|
| }
|
|
|
| +// static
|
| +void ResourceRow::FromProto(const ResourceData& proto, ResourceRow* row) {
|
| + row->resource_url = GURL(proto.resource_url());
|
| + row->resource_type =
|
| + static_cast<content::ResourceType>(proto.resource_type());
|
| + row->number_of_hits = proto.number_of_hits();
|
| + row->number_of_misses = proto.number_of_misses();
|
| + row->consecutive_misses = proto.consecutive_misses();
|
| + row->average_position = proto.average_position();
|
| + row->priority = static_cast<net::RequestPriority>(proto.priority());
|
| + row->has_validators = proto.has_validators();
|
| + row->always_revalidate = proto.always_revalidate();
|
| + row->UpdateScore();
|
| +}
|
| +
|
| void ResourceRow::ToProto(ResourceData* resource_data) const {
|
| using chrome_browser_predictors::ResourceData_Priority;
|
| using chrome_browser_predictors::ResourceData_ResourceType;
|
| @@ -185,22 +244,8 @@ void ResourceRow::ToProto(ResourceData* resource_data) const {
|
| }
|
|
|
| // static
|
| -void ResourceRow::FromProto(const ResourceData& proto, ResourceRow* row) {
|
| - row->resource_url = GURL(proto.resource_url());
|
| - row->resource_type =
|
| - static_cast<content::ResourceType>(proto.resource_type());
|
| - row->number_of_hits = proto.number_of_hits();
|
| - row->number_of_misses = proto.number_of_misses();
|
| - row->consecutive_misses = proto.consecutive_misses();
|
| - row->average_position = proto.average_position();
|
| - row->priority = static_cast<net::RequestPriority>(proto.priority());
|
| - row->has_validators = proto.has_validators();
|
| - row->always_revalidate = proto.always_revalidate();
|
| - row->UpdateScore();
|
| -}
|
| -
|
| -// static
|
| -void ResourcePrefetchPredictorTables::SortResourceRows(ResourceRows* rows) {
|
| +void ResourcePrefetchPredictorTables::SortResourceRows(
|
| + std::vector<ResourceRow>* rows) {
|
| std::sort(rows->begin(), rows->end(),
|
| [](const ResourceRow& x, const ResourceRow& y) {
|
| return x.score > y.score;
|
| @@ -231,47 +276,193 @@ bool ResourcePrefetchPredictorTables::PrefetchData::operator==(
|
| resources == rhs.resources;
|
| }
|
|
|
| +RedirectRow::RedirectRow()
|
| + : number_of_hits(0),
|
| + number_of_misses(0),
|
| + consecutive_misses(0),
|
| + score(0.0) {}
|
| +
|
| +RedirectRow::RedirectRow(const RedirectRow& other)
|
| + : url(other.url),
|
| + number_of_hits(other.number_of_hits),
|
| + number_of_misses(other.number_of_misses),
|
| + consecutive_misses(other.consecutive_misses),
|
| + score(other.score) {}
|
| +
|
| +RedirectRow::RedirectRow(const std::string& i_url,
|
| + size_t i_number_of_hits,
|
| + size_t i_number_of_misses,
|
| + size_t i_consecutive_misses)
|
| + : url(i_url),
|
| + number_of_hits(i_number_of_hits),
|
| + number_of_misses(i_number_of_misses),
|
| + consecutive_misses(i_consecutive_misses),
|
| + score(0.0) {}
|
| +
|
| +void RedirectRow::UpdateScore() {
|
| + // TODO(alexilin): invent some scoring
|
| +}
|
| +
|
| +bool RedirectRow::operator==(const RedirectRow& rhs) const {
|
| + return url == rhs.url && number_of_hits == rhs.number_of_hits &&
|
| + number_of_misses == rhs.number_of_misses &&
|
| + consecutive_misses == rhs.consecutive_misses;
|
| +}
|
| +
|
| +// static
|
| +void RedirectRow::FromProto(const RedirectStat& proto, RedirectRow* row) {
|
| + row->url = proto.url();
|
| + row->number_of_hits = proto.number_of_hits();
|
| + row->number_of_misses = proto.number_of_misses();
|
| + row->consecutive_misses = proto.consecutive_misses();
|
| + row->UpdateScore();
|
| +}
|
| +
|
| +void RedirectRow::ToProto(RedirectStat* redirect_stat) const {
|
| + redirect_stat->set_url(url);
|
| + redirect_stat->set_number_of_hits(number_of_hits);
|
| + redirect_stat->set_number_of_misses(number_of_misses);
|
| + redirect_stat->set_consecutive_misses(consecutive_misses);
|
| +}
|
| +
|
| +// static
|
| +void ResourcePrefetchPredictorTables::SortRedirectRows(
|
| + std::vector<RedirectRow>* rows) {
|
| + std::sort(rows->begin(), rows->end(),
|
| + [](const RedirectRow& x, const RedirectRow& y) {
|
| + return x.score > y.score;
|
| + });
|
| +}
|
| +
|
| +ResourcePrefetchPredictorTables::RedirectData::RedirectData(
|
| + PrefetchKeyType i_key_type,
|
| + const std::string& i_primary_key)
|
| + : key_type(i_key_type), primary_key(i_primary_key) {}
|
| +
|
| +ResourcePrefetchPredictorTables::RedirectData::RedirectData(
|
| + const RedirectData& other)
|
| + : key_type(other.key_type),
|
| + primary_key(other.primary_key),
|
| + last_visit(other.last_visit),
|
| + redirects(other.redirects) {}
|
| +
|
| +ResourcePrefetchPredictorTables::RedirectData::~RedirectData() {}
|
| +
|
| +bool ResourcePrefetchPredictorTables::RedirectData::operator==(
|
| + const RedirectData& rhs) const {
|
| + return key_type == rhs.key_type && primary_key == rhs.primary_key &&
|
| + redirects == rhs.redirects;
|
| +}
|
| +
|
| +// static
|
| +void ResourcePrefetchPredictorTables::RedirectData::FromProto(
|
| + const RedirectProto& proto,
|
| + RedirectData* data) {
|
| + data->last_visit = base::Time::FromInternalValue(proto.last_visit_time());
|
| + data->redirects.clear();
|
| + for (const auto& stat : proto.redirects()) {
|
| + RedirectRow row;
|
| + RedirectRow::FromProto(stat, &row);
|
| + data->redirects.push_back(row);
|
| + }
|
| +}
|
| +
|
| +void ResourcePrefetchPredictorTables::RedirectData::ToProto(
|
| + RedirectProto* proto) const {
|
| + proto->set_last_visit_time(last_visit.ToInternalValue());
|
| + proto->clear_redirects();
|
| + for (const auto& row : redirects) {
|
| + RedirectStat* stat = proto->add_redirects();
|
| + row.ToProto(stat);
|
| + }
|
| +}
|
| +
|
| void ResourcePrefetchPredictorTables::GetAllData(
|
| PrefetchDataMap* url_data_map,
|
| - PrefetchDataMap* host_data_map) {
|
| + PrefetchDataMap* host_data_map,
|
| + RedirectDataMap* url_redirect_data_map,
|
| + RedirectDataMap* host_redirect_data_map) {
|
| DCHECK_CURRENTLY_ON(BrowserThread::DB);
|
| if (CantAccessDatabase())
|
| return;
|
|
|
| DCHECK(url_data_map);
|
| DCHECK(host_data_map);
|
| + DCHECK(url_redirect_data_map);
|
| + DCHECK(host_redirect_data_map);
|
| url_data_map->clear();
|
| host_data_map->clear();
|
| + url_redirect_data_map->clear();
|
| + host_redirect_data_map->clear();
|
|
|
| std::vector<std::string> urls_to_delete, hosts_to_delete;
|
| - GetAllDataHelper(PREFETCH_KEY_TYPE_URL, url_data_map, &urls_to_delete);
|
| - GetAllDataHelper(PREFETCH_KEY_TYPE_HOST, host_data_map, &hosts_to_delete);
|
| + GetAllResourceDataHelper(PREFETCH_KEY_TYPE_URL, url_data_map,
|
| + &urls_to_delete);
|
| + GetAllResourceDataHelper(PREFETCH_KEY_TYPE_HOST, host_data_map,
|
| + &hosts_to_delete);
|
| + GetAllRedirectDataHelper(PREFETCH_KEY_TYPE_URL, url_redirect_data_map);
|
| + GetAllRedirectDataHelper(PREFETCH_KEY_TYPE_HOST, host_redirect_data_map);
|
|
|
| if (!urls_to_delete.empty() || !hosts_to_delete.empty())
|
| - DeleteData(urls_to_delete, hosts_to_delete);
|
| + DeleteResourceData(urls_to_delete, hosts_to_delete);
|
| }
|
|
|
| void ResourcePrefetchPredictorTables::UpdateData(
|
| const PrefetchData& url_data,
|
| - const PrefetchData& host_data) {
|
| + const PrefetchData& host_data,
|
| + const RedirectData& url_redirect_data,
|
| + const RedirectData& host_redirect_data) {
|
| DCHECK_CURRENTLY_ON(BrowserThread::DB);
|
| if (CantAccessDatabase())
|
| return;
|
|
|
| DCHECK(!url_data.is_host() && host_data.is_host());
|
| - DCHECK(!url_data.primary_key.empty() || !host_data.primary_key.empty());
|
| + DCHECK(!url_redirect_data.is_host() && host_redirect_data.is_host());
|
| + DCHECK(!url_data.primary_key.empty() || !host_data.primary_key.empty() ||
|
| + !url_redirect_data.primary_key.empty() ||
|
| + !host_redirect_data.primary_key.empty());
|
|
|
| DB()->BeginTransaction();
|
|
|
| - bool success = (url_data.primary_key.empty() || UpdateDataHelper(url_data)) &&
|
| - (host_data.primary_key.empty() || UpdateDataHelper(host_data));
|
| + bool success =
|
| + (url_data.primary_key.empty() || UpdateResourceDataHelper(url_data)) &&
|
| + (host_data.primary_key.empty() || UpdateResourceDataHelper(host_data)) &&
|
| + (url_redirect_data.primary_key.empty() ||
|
| + UpdateRedirectDataHelper(url_redirect_data)) &&
|
| + (host_redirect_data.primary_key.empty() ||
|
| + UpdateRedirectDataHelper(host_redirect_data));
|
| if (!success)
|
| DB()->RollbackTransaction();
|
| + else
|
| + DB()->CommitTransaction();
|
| +}
|
| +
|
| +void ResourcePrefetchPredictorTables::DeleteResourceData(
|
| + const std::vector<std::string>& urls,
|
| + const std::vector<std::string>& hosts) {
|
| + DCHECK_CURRENTLY_ON(BrowserThread::DB);
|
| + if (CantAccessDatabase())
|
| + return;
|
| +
|
| + DCHECK(!urls.empty() || !hosts.empty());
|
| +
|
| + if (!urls.empty())
|
| + DeleteResourceDataHelper(PREFETCH_KEY_TYPE_URL, urls);
|
| + if (!hosts.empty())
|
| + DeleteResourceDataHelper(PREFETCH_KEY_TYPE_HOST, hosts);
|
| +}
|
|
|
| - DB()->CommitTransaction();
|
| +void ResourcePrefetchPredictorTables::DeleteSingleResourceDataPoint(
|
| + const std::string& key,
|
| + PrefetchKeyType key_type) {
|
| + DCHECK_CURRENTLY_ON(BrowserThread::DB);
|
| + if (CantAccessDatabase())
|
| + return;
|
| +
|
| + DeleteResourceDataHelper(key_type, {key});
|
| }
|
|
|
| -void ResourcePrefetchPredictorTables::DeleteData(
|
| +void ResourcePrefetchPredictorTables::DeleteRedirectData(
|
| const std::vector<std::string>& urls,
|
| const std::vector<std::string>& hosts) {
|
| DCHECK_CURRENTLY_ON(BrowserThread::DB);
|
| @@ -281,19 +472,19 @@ void ResourcePrefetchPredictorTables::DeleteData(
|
| DCHECK(!urls.empty() || !hosts.empty());
|
|
|
| if (!urls.empty())
|
| - DeleteDataHelper(PREFETCH_KEY_TYPE_URL, urls);
|
| + DeleteRedirectDataHelper(PREFETCH_KEY_TYPE_URL, urls);
|
| if (!hosts.empty())
|
| - DeleteDataHelper(PREFETCH_KEY_TYPE_HOST, hosts);
|
| + DeleteRedirectDataHelper(PREFETCH_KEY_TYPE_HOST, hosts);
|
| }
|
|
|
| -void ResourcePrefetchPredictorTables::DeleteSingleDataPoint(
|
| +void ResourcePrefetchPredictorTables::DeleteSingleRedirectDataPoint(
|
| const std::string& key,
|
| PrefetchKeyType key_type) {
|
| DCHECK_CURRENTLY_ON(BrowserThread::DB);
|
| if (CantAccessDatabase())
|
| return;
|
|
|
| - DeleteDataHelper(key_type, std::vector<std::string>(1, key));
|
| + DeleteRedirectDataHelper(key_type, {key});
|
| }
|
|
|
| void ResourcePrefetchPredictorTables::DeleteAllData() {
|
| @@ -302,8 +493,9 @@ void ResourcePrefetchPredictorTables::DeleteAllData() {
|
|
|
| Statement deleter;
|
| for (const char* table_name :
|
| - {kUrlResourceTableName, kUrlMetadataTableName, kHostResourceTableName,
|
| - kHostMetadataTableName}) {
|
| + {kUrlResourceTableName, kUrlMetadataTableName, kUrlRedirectTableName,
|
| + kHostResourceTableName, kHostMetadataTableName,
|
| + kHostRedirectTableName}) {
|
| deleter.Assign(DB()->GetUniqueStatement(
|
| base::StringPrintf("DELETE FROM %s", table_name).c_str()));
|
| deleter.Run();
|
| @@ -317,7 +509,7 @@ ResourcePrefetchPredictorTables::ResourcePrefetchPredictorTables()
|
| ResourcePrefetchPredictorTables::~ResourcePrefetchPredictorTables() {
|
| }
|
|
|
| -void ResourcePrefetchPredictorTables::GetAllDataHelper(
|
| +void ResourcePrefetchPredictorTables::GetAllResourceDataHelper(
|
| PrefetchKeyType key_type,
|
| PrefetchDataMap* data_map,
|
| std::vector<std::string>* to_delete) {
|
| @@ -346,8 +538,8 @@ void ResourcePrefetchPredictorTables::GetAllDataHelper(
|
|
|
| // Read the metadata and keep track of entries that have metadata, but no
|
| // resource entries, so they can be deleted.
|
| - const char* metadata_table_name = is_host ? kHostMetadataTableName :
|
| - kUrlMetadataTableName;
|
| + const char* metadata_table_name =
|
| + is_host ? kHostMetadataTableName : kUrlMetadataTableName;
|
| Statement metadata_reader(DB()->GetUniqueStatement(
|
| base::StringPrintf("SELECT * FROM %s", metadata_table_name).c_str()));
|
|
|
| @@ -364,7 +556,25 @@ void ResourcePrefetchPredictorTables::GetAllDataHelper(
|
| }
|
| }
|
|
|
| -bool ResourcePrefetchPredictorTables::UpdateDataHelper(
|
| +void ResourcePrefetchPredictorTables::GetAllRedirectDataHelper(
|
| + PrefetchKeyType key_type,
|
| + RedirectDataMap* redirect_map) {
|
| + bool is_host = key_type == PREFETCH_KEY_TYPE_HOST;
|
| +
|
| + const char* redirect_table_name =
|
| + is_host ? kHostRedirectTableName : kUrlRedirectTableName;
|
| + Statement redirect_reader(DB()->GetUniqueStatement(
|
| + base::StringPrintf("SELECT * FROM %s", redirect_table_name).c_str()));
|
| +
|
| + RedirectData data(key_type);
|
| + std::string primary_key;
|
| + while (StepAndInitializeRedirectData(&redirect_reader, &data, &primary_key)) {
|
| + auto result = redirect_map->insert(std::make_pair(primary_key, data));
|
| + DCHECK(result.second);
|
| + }
|
| +}
|
| +
|
| +bool ResourcePrefetchPredictorTables::UpdateResourceDataHelper(
|
| const PrefetchData& data) {
|
| DCHECK(!data.primary_key.empty());
|
|
|
| @@ -381,8 +591,8 @@ bool ResourcePrefetchPredictorTables::UpdateDataHelper(
|
| if (!deleter->Run())
|
| return false;
|
|
|
| - deleter.reset(data.is_host() ? GetHostMetadataDeleteStatement() :
|
| - GetUrlMetadataDeleteStatement());
|
| + deleter.reset(data.is_host() ? GetHostMetadataDeleteStatement()
|
| + : GetUrlMetadataDeleteStatement());
|
| deleter->BindString(0, data.primary_key);
|
| if (!deleter->Run())
|
| return false;
|
| @@ -409,7 +619,35 @@ bool ResourcePrefetchPredictorTables::UpdateDataHelper(
|
| return true;
|
| }
|
|
|
| -void ResourcePrefetchPredictorTables::DeleteDataHelper(
|
| +bool ResourcePrefetchPredictorTables::UpdateRedirectDataHelper(
|
| + const RedirectData& data) {
|
| + DCHECK(!data.primary_key.empty());
|
| +
|
| + if (!StringsAreSmallerThanDBLimit(data)) {
|
| + UMA_HISTOGRAM_BOOLEAN("ResourcePrefetchPredictor.DbStringTooLong", true);
|
| + return false;
|
| + }
|
| +
|
| + // Delete the older data from the table.
|
| + std::unique_ptr<Statement> deleter(data.is_host()
|
| + ? GetHostRedirectDeleteStatement()
|
| + : GetUrlRedirectDeleteStatement());
|
| + deleter->BindString(0, data.primary_key);
|
| + if (!deleter->Run())
|
| + return false;
|
| +
|
| + // Add the new data to the table.
|
| + std::unique_ptr<Statement> inserter(data.is_host()
|
| + ? GetHostRedirectUpdateStatement()
|
| + : GetUrlRedirectUpdateStatement());
|
| + BindRedirectDataToStatement(data, inserter.get());
|
| + if (!inserter->Run())
|
| + return false;
|
| +
|
| + return true;
|
| +}
|
| +
|
| +void ResourcePrefetchPredictorTables::DeleteResourceDataHelper(
|
| PrefetchKeyType key_type,
|
| const std::vector<std::string>& keys) {
|
| bool is_host = key_type == PREFETCH_KEY_TYPE_HOST;
|
| @@ -421,8 +659,22 @@ void ResourcePrefetchPredictorTables::DeleteDataHelper(
|
| deleter->BindString(0, key);
|
| deleter->Run();
|
|
|
| - deleter.reset(is_host ? GetHostMetadataDeleteStatement() :
|
| - GetUrlMetadataDeleteStatement());
|
| + deleter.reset(is_host ? GetHostMetadataDeleteStatement()
|
| + : GetUrlMetadataDeleteStatement());
|
| + deleter->BindString(0, key);
|
| + deleter->Run();
|
| + }
|
| +}
|
| +
|
| +void ResourcePrefetchPredictorTables::DeleteRedirectDataHelper(
|
| + PrefetchKeyType key_type,
|
| + const std::vector<std::string>& keys) {
|
| + bool is_host = key_type == PREFETCH_KEY_TYPE_HOST;
|
| +
|
| + for (const std::string& key : keys) {
|
| + std::unique_ptr<Statement> deleter(is_host
|
| + ? GetHostRedirectDeleteStatement()
|
| + : GetUrlRedirectDeleteStatement());
|
| deleter->BindString(0, key);
|
| deleter->Run();
|
| }
|
| @@ -442,6 +694,19 @@ bool ResourcePrefetchPredictorTables::StringsAreSmallerThanDBLimit(
|
| }
|
|
|
| // static
|
| +bool ResourcePrefetchPredictorTables::StringsAreSmallerThanDBLimit(
|
| + const RedirectData& data) {
|
| + if (data.primary_key.length() > kMaxStringLength)
|
| + return false;
|
| +
|
| + for (const RedirectRow& row : data.redirects) {
|
| + if (row.url.length() > kMaxStringLength)
|
| + return false;
|
| + }
|
| + return true;
|
| +}
|
| +
|
| +// static
|
| bool ResourcePrefetchPredictorTables::DropTablesIfOutdated(
|
| sql::Connection* db) {
|
| int version = GetDatabaseVersion(db);
|
| @@ -452,7 +717,8 @@ bool ResourcePrefetchPredictorTables::DropTablesIfOutdated(
|
| if (incompatible_version) {
|
| for (const char* table_name :
|
| {kMetadataTableName, kUrlResourceTableName, kHostResourceTableName,
|
| - kUrlMetadataTableName, kHostMetadataTableName}) {
|
| + kUrlRedirectTableName, kHostRedirectTableName, kUrlMetadataTableName,
|
| + kHostMetadataTableName}) {
|
| success =
|
| success &&
|
| db->Execute(base::StringPrintf("DROP TABLE IF EXISTS %s", table_name)
|
| @@ -519,6 +785,10 @@ void ResourcePrefetchPredictorTables::CreateTableIfNonExistent() {
|
| db->Execute(base::StringPrintf(kCreateMetadataTableStatementTemplate,
|
| kUrlMetadataTableName)
|
| .c_str())) &&
|
| + (db->DoesTableExist(kUrlRedirectTableName) ||
|
| + db->Execute(base::StringPrintf(kCreateRedirectTableStatementTemplate,
|
| + kUrlRedirectTableName)
|
| + .c_str())) &&
|
| (db->DoesTableExist(kHostResourceTableName) ||
|
| db->Execute(base::StringPrintf(kCreateResourceTableStatementTemplate,
|
| kHostResourceTableName)
|
| @@ -526,6 +796,10 @@ void ResourcePrefetchPredictorTables::CreateTableIfNonExistent() {
|
| (db->DoesTableExist(kHostMetadataTableName) ||
|
| db->Execute(base::StringPrintf(kCreateMetadataTableStatementTemplate,
|
| kHostMetadataTableName)
|
| + .c_str())) &&
|
| + (db->DoesTableExist(kHostRedirectTableName) ||
|
| + db->Execute(base::StringPrintf(kCreateRedirectTableStatementTemplate,
|
| + kHostRedirectTableName)
|
| .c_str()));
|
|
|
| if (success)
|
| @@ -555,6 +829,20 @@ void ResourcePrefetchPredictorTables::LogDatabaseStats() {
|
| if (statement.Step())
|
| UMA_HISTOGRAM_COUNTS("ResourcePrefetchPredictor.HostTableRowCount",
|
| statement.ColumnInt(0));
|
| +
|
| + statement.Assign(DB()->GetUniqueStatement(
|
| + base::StringPrintf("SELECT count(*) FROM %s", kUrlRedirectTableName)
|
| + .c_str()));
|
| + if (statement.Step())
|
| + UMA_HISTOGRAM_COUNTS("ResourcePrefetchPredictor.UrlRedirectTableRowCount",
|
| + statement.ColumnInt(0));
|
| +
|
| + statement.Assign(DB()->GetUniqueStatement(
|
| + base::StringPrintf("SELECT count(*) FROM %s", kHostRedirectTableName)
|
| + .c_str()));
|
| + if (statement.Step())
|
| + UMA_HISTOGRAM_COUNTS("ResourcePrefetchPredictor.HostRedirectTableRowCount",
|
| + statement.ColumnInt(0));
|
| }
|
|
|
| Statement*
|
| @@ -573,22 +861,34 @@ Statement*
|
| .c_str()));
|
| }
|
|
|
| -Statement*
|
| - ResourcePrefetchPredictorTables::GetUrlMetadataDeleteStatement() {
|
| +Statement* ResourcePrefetchPredictorTables::GetUrlMetadataDeleteStatement() {
|
| return new Statement(DB()->GetCachedStatement(
|
| SQL_FROM_HERE,
|
| base::StringPrintf(kDeleteStatementTemplate, kUrlMetadataTableName)
|
| .c_str()));
|
| }
|
|
|
| -Statement*
|
| - ResourcePrefetchPredictorTables::GetUrlMetadataUpdateStatement() {
|
| +Statement* ResourcePrefetchPredictorTables::GetUrlMetadataUpdateStatement() {
|
| return new Statement(DB()->GetCachedStatement(
|
| SQL_FROM_HERE, base::StringPrintf(kInsertMetadataTableStatementTemplate,
|
| kUrlMetadataTableName)
|
| .c_str()));
|
| }
|
|
|
| +Statement* ResourcePrefetchPredictorTables::GetUrlRedirectDeleteStatement() {
|
| + return new Statement(DB()->GetCachedStatement(
|
| + SQL_FROM_HERE,
|
| + base::StringPrintf(kDeleteStatementTemplate, kUrlRedirectTableName)
|
| + .c_str()));
|
| +}
|
| +
|
| +Statement* ResourcePrefetchPredictorTables::GetUrlRedirectUpdateStatement() {
|
| + return new Statement(DB()->GetCachedStatement(
|
| + SQL_FROM_HERE, base::StringPrintf(kInsertRedirectTableStatementTemplate,
|
| + kUrlRedirectTableName)
|
| + .c_str()));
|
| +}
|
| +
|
| Statement*
|
| ResourcePrefetchPredictorTables::GetHostResourceDeleteStatement() {
|
| return new Statement(DB()->GetCachedStatement(
|
| @@ -605,8 +905,7 @@ Statement*
|
| .c_str()));
|
| }
|
|
|
| -Statement*
|
| - ResourcePrefetchPredictorTables::GetHostMetadataDeleteStatement() {
|
| +Statement* ResourcePrefetchPredictorTables::GetHostMetadataDeleteStatement() {
|
| return new Statement(DB()->GetCachedStatement(
|
| SQL_FROM_HERE,
|
| base::StringPrintf(kDeleteStatementTemplate, kHostMetadataTableName)
|
| @@ -620,4 +919,18 @@ Statement* ResourcePrefetchPredictorTables::GetHostMetadataUpdateStatement() {
|
| .c_str()));
|
| }
|
|
|
| +Statement* ResourcePrefetchPredictorTables::GetHostRedirectDeleteStatement() {
|
| + return new Statement(DB()->GetCachedStatement(
|
| + SQL_FROM_HERE,
|
| + base::StringPrintf(kDeleteStatementTemplate, kHostRedirectTableName)
|
| + .c_str()));
|
| +}
|
| +
|
| +Statement* ResourcePrefetchPredictorTables::GetHostRedirectUpdateStatement() {
|
| + return new Statement(DB()->GetCachedStatement(
|
| + SQL_FROM_HERE, base::StringPrintf(kInsertRedirectTableStatementTemplate,
|
| + kHostRedirectTableName)
|
| + .c_str()));
|
| +}
|
| +
|
| } // namespace predictors
|
|
|