Commit c775d5d2 authored by Hesen Zhang's avatar Hesen Zhang Committed by Commit Bot

[Notification scheduler]: Handle icon load failure.

- Cleanup notifications if their icons fail to load.

Bug: 963290
Change-Id: I9cfc3b4bf4ebb5526a7986f8dbf8906b2c3c9354
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/1790473Reviewed-by: default avatarXing Liu <xingliu@chromium.org>
Commit-Queue: Hesen Zhang <hesen@chromium.org>
Cr-Commit-Position: refs/heads/master@{#694986}
parent 34839008
...@@ -192,7 +192,7 @@ class ScheduledNotificationManagerImpl : public ScheduledNotificationManager { ...@@ -192,7 +192,7 @@ class ScheduledNotificationManagerImpl : public ScheduledNotificationManager {
while (it != notifications_[type].end()) { while (it != notifications_[type].end()) {
const auto& entry = *it->second; const auto& entry = *it->second;
++it; ++it;
DeleteNotificationInDb(entry); DeleteNotification(entry, false /*should_delete_in_memory*/);
} }
notifications_.erase(type); notifications_.erase(type);
} }
...@@ -265,33 +265,13 @@ class ScheduledNotificationManagerImpl : public ScheduledNotificationManager { ...@@ -265,33 +265,13 @@ class ScheduledNotificationManagerImpl : public ScheduledNotificationManager {
bool valid = ValidateNotificationEntry(*entry); bool valid = ValidateNotificationEntry(*entry);
bool deprecated_client = !base::Contains(clients_, entry->type); bool deprecated_client = !base::Contains(clients_, entry->type);
if (expired || deprecated_client || !valid) { if (expired || deprecated_client || !valid) {
DeleteNotificationInDb(*entry); DeleteNotification(*entry, false /*should_delete_in_memory*/);
} else { } else {
notifications_[entry->type].emplace(entry->guid, std::move(*it)); notifications_[entry->type].emplace(entry->guid, std::move(*it));
} }
} }
} }
// Deletes a notification entry and its associated icon resources from
// database.
void DeleteNotificationInDb(const NotificationEntry& entry) {
// Deletes icon first.
std::vector<std::string> icons_to_delete;
for (const auto& icon_id : entry.icons_uuid) {
icons_to_delete.emplace_back(icon_id.second);
}
icon_store_->DeleteIcons(
std::move(icons_to_delete),
base::BindOnce(&ScheduledNotificationManagerImpl::OnIconDeleted,
weak_ptr_factory_.GetWeakPtr()));
// Deletes notification entry.
notification_store_->Delete(
entry.guid,
base::BindOnce(&ScheduledNotificationManagerImpl::OnNotificationDeleted,
weak_ptr_factory_.GetWeakPtr()));
}
void OnIconsAdded(std::unique_ptr<NotificationEntry> entry, void OnIconsAdded(std::unique_ptr<NotificationEntry> entry,
ScheduleCallback schedule_callback, ScheduleCallback schedule_callback,
IconStore::IconTypeUuidMap icons_uuid_map, IconStore::IconTypeUuidMap icons_uuid_map,
...@@ -355,24 +335,14 @@ class ScheduledNotificationManagerImpl : public ScheduledNotificationManager { ...@@ -355,24 +335,14 @@ class ScheduledNotificationManagerImpl : public ScheduledNotificationManager {
IconStore::LoadedIconsMap loaded_icons_map) { IconStore::LoadedIconsMap loaded_icons_map) {
stats::LogDbOperation(stats::DatabaseType::kIconDb, success); stats::LogDbOperation(stats::DatabaseType::kIconDb, success);
// TODO(hesen): delete notification entry if icons failed to load. auto* entry_ptr = FindNotificationEntry(client_type, guid);
if (!success) { if (!entry_ptr) {
std::move(display_callback).Run(nullptr); std::move(display_callback).Run(nullptr);
return; return;
} }
// Delete icons from database. if (!success) {
std::vector<std::string> icons_to_delete; DeleteNotification(*entry_ptr, true /*should_delete_in_memory*/);
for (const auto& loaded_icon : loaded_icons_map) {
icons_to_delete.emplace_back(loaded_icon.first);
}
icon_store_->DeleteIcons(
std::move(icons_to_delete),
base::BindOnce(&ScheduledNotificationManagerImpl::OnIconDeleted,
weak_ptr_factory_.GetWeakPtr()));
// Can't find the entry.
if (!FindNotificationEntry(client_type, guid)) {
std::move(display_callback).Run(nullptr); std::move(display_callback).Run(nullptr);
return; return;
} }
...@@ -388,13 +358,7 @@ class ScheduledNotificationManagerImpl : public ScheduledNotificationManager { ...@@ -388,13 +358,7 @@ class ScheduledNotificationManagerImpl : public ScheduledNotificationManager {
} }
// Before moving out the entry, delete it from container and disk. // Before moving out the entry, delete it from container and disk.
notifications_[entry->type].erase(entry->guid); DeleteNotification(*entry.get(), true /*should_delete_in_memory*/);
if (notifications_[entry->type].empty())
notifications_.erase(entry->type);
notification_store_->Delete(
entry->guid,
base::BindOnce(&ScheduledNotificationManagerImpl::OnNotificationDeleted,
weak_ptr_factory_.GetWeakPtr()));
std::move(display_callback).Run(std::move(entry)); std::move(display_callback).Run(std::move(entry));
} }
...@@ -406,6 +370,35 @@ class ScheduledNotificationManagerImpl : public ScheduledNotificationManager { ...@@ -406,6 +370,35 @@ class ScheduledNotificationManagerImpl : public ScheduledNotificationManager {
return notifications_[type][guid].get(); return notifications_[type][guid].get();
} }
// Delete NotitificationEntry from memory and disk.
void DeleteNotification(const NotificationEntry& entry,
bool should_delete_in_memory) {
// Deletes icon first.
std::vector<std::string> icons_to_delete;
for (const auto& icon_id : entry.icons_uuid) {
icons_to_delete.emplace_back(icon_id.second);
}
icon_store_->DeleteIcons(
std::move(icons_to_delete),
base::BindOnce(&ScheduledNotificationManagerImpl::OnIconDeleted,
weak_ptr_factory_.GetWeakPtr()));
auto guid = entry.guid;
auto type = entry.type;
// Deletes notification entry.
notification_store_->Delete(
guid,
base::BindOnce(&ScheduledNotificationManagerImpl::OnNotificationDeleted,
weak_ptr_factory_.GetWeakPtr()));
if (should_delete_in_memory) {
notifications_[type].erase(guid);
if (notifications_[type].empty())
notifications_.erase(type);
}
}
// Create two default buttons {Helpful, Unhelpful} for notification. // Create two default buttons {Helpful, Unhelpful} for notification.
void CreateInhrButtonsPair(std::vector<NotificationData::Button>* buttons) { void CreateInhrButtonsPair(std::vector<NotificationData::Button>* buttons) {
buttons->clear(); buttons->clear();
......
...@@ -698,14 +698,14 @@ TEST_F(ScheduledNotificationManagerTest, DisplayNotificationWithIconsFailed) { ...@@ -698,14 +698,14 @@ TEST_F(ScheduledNotificationManagerTest, DisplayNotificationWithIconsFailed) {
IconStore::LoadIconsCallback callback) { IconStore::LoadIconsCallback callback) {
std::move(callback).Run(false, {}); std::move(callback).Run(false, {});
})); }));
EXPECT_CALL(*notification_store(), Delete(kGuid, _));
EXPECT_CALL(*icon_store(), DeleteIcons(_, _));
DisplayNotification(kGuid, nullptr /*expected_entry*/); DisplayNotification(kGuid, nullptr /*expected_entry*/);
// Verify in-memory data. // Verify in-memory data.
ScheduledNotificationManager::Notifications notifications; ScheduledNotificationManager::Notifications notifications;
manager()->GetAllNotifications(&notifications); manager()->GetAllNotifications(&notifications);
// TODO(hesen): need to delete notification entry if icons failed to load. EXPECT_TRUE(notifications.empty());
EXPECT_EQ(notifications.size(), 1u);
} }
} // namespace } // namespace
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment