Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add button in AdBlock settings to update AdBlock components #22881

Merged
merged 1 commit into from
Apr 12, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 12 additions & 0 deletions app/brave_settings_strings.grdp
Original file line number Diff line number Diff line change
Expand Up @@ -423,6 +423,18 @@
<message name="IDS_BRAVE_ADBLOCK_SHOW_FULL_LISTS_BUTTON_LABEL" desc="A button label to expand full custom filter lists">
Show full list
</message>
<message name="IDS_BRAVE_ADBLOCK_UPDATE_LISTS_BUTTON_LABEL" desc="A button label to update all active filter lists">
Update lists
</message>
<message name="IDS_BRAVE_ADBLOCK_UPDATE_LISTS_RETRY_BUTTON_LABEL" desc="A button label to retry the update of all active filter lists">
Update failed - Retry
</message>
<message name="IDS_BRAVE_ADBLOCK_UPDATE_LISTS_UPDATED_BUTTON_LABEL" desc="A button label when list updates have finished">
Lists updated
</message>
<message name="IDS_BRAVE_ADBLOCK_UPDATE_LISTS_UPDATING_BUTTON_LABEL" desc="A button label when lists are updating">
Lists updating
</message>
<message name="IDS_BRAVE_ADBLOCK_CUSTOM_FILTER_LISTS_INPUT_PLACEHOLDER" desc="A placeholder label for the input form to ask the user to enter a URL">
Enter filter list URL
</message>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import { sendWithPromise, addWebUiListener } from 'chrome://resources/js/cr.js';
export interface BraveAdblockBrowserProxy {
getRegionalLists(): Promise<any[]> // TODO(petemill): Define the expected type
enableFilterList(uuid: string, enabled: boolean)
updateFilterList(uuid: string): Promise<boolean>
getListSubscriptions(): Promise<any> // TODO(petemill): Define the expected type
getCustomFilters(): Promise<any> // TODO(petemill): Define the expected type
setSubscriptionEnabled(url: string, enabled: boolean)
Expand Down Expand Up @@ -44,6 +45,11 @@ export class BraveAdblockBrowserProxyImpl implements BraveAdblockBrowserProxy {
chrome.send('brave_adblock.enableFilterList', [uuid, enabled])
}

/** @returns {Promise<boolean>} */
updateFilterLists () {
return sendWithPromise('brave_adblock.updateFilterLists')
}

setSubscriptionEnabled (url, enabled) {
chrome.send('brave_adblock.setSubscriptionEnabled', [url, enabled])
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -86,8 +86,18 @@
font-weight: 500;
}

.show-list-button-box {
.list-actions-box {
display: flex;
margin-bottom: 10px;
gap: 8px;
}

.update-lists-updated {
--leo-button-color: var(--leo-color-systemfeedback-success-text);
}

.update-lists-failed {
--leo-button-color: var(--leo-color-systemfeedback-error-text);
}

.subscribe-url-form {
Expand Down Expand Up @@ -186,11 +196,38 @@
</div>
</template>
</div>
<template is="dom-if" if="[[!hasListExpanded_]]">
<div class="show-list-button-box">
<cr-button on-click="handleShowList_">$i18n{adblockShowFullListsButtonLabel}</cr-button>
<div class="list-actions-box">
<template is="dom-if" if="[[!hasListExpanded_]]">
<div>
<cr-button on-click="handleShowList_">$i18n{adblockShowFullListsButtonLabel}</cr-button>
</div>
</template>
<div class$="update-lists-[[listsUpdatingState_]]">
<template is="dom-if" if="[[!listsUpdatingState_]]">
<cr-button on-click="handleUpdateLists_">
<span>$i18n{adblockUpdateListsButtonLabel}</span>
</cr-button>
</template>
<template is="dom-if" if="[[isEqual_(listsUpdatingState_, 'updating')]]">
<cr-button on-click="handleUpdateLists_">
<leo-progressring slot="prefix-icon"></leo-progressring>
<span>$i18n{adblockUpdateListsUpdatingButtonLabel}</span>
</cr-button>
</template>
<template is="dom-if" if="[[isEqual_(listsUpdatingState_, 'updated')]]">
<cr-button on-click="handleUpdateLists_">
<leo-icon name="check-circle-outline" slot="prefix-icon"></leo-icon>
<span>$i18n{adblockUpdateListsUpdatedButtonLabel}</span>
</cr-button>
</template>
<template is="dom-if" if="[[isEqual_(listsUpdatingState_, 'failed')]]">
<cr-button on-click="handleUpdateLists_">
<leo-icon name="warning-circle-outline" slot="prefix-icon"></leo-icon>
<span>$i18n{adblockUpdateListsRetryButtonLabel}</span>
</cr-button>
</template>
</div>
</template>
</div>
</div>
</div>
<div class="settings-box">
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ class AdBlockSubpage extends AdBlockSubpageBase {
subscriptionList_: Array,
customFilters_: String,
subscribeUrl_: String,
listsUpdatingState_: String,
hasListExpanded_: {
type: Boolean,
value: false
Expand All @@ -47,6 +48,9 @@ class AdBlockSubpage extends AdBlockSubpageBase {

ready() {
super.ready()

this.listsUpdatingState_ = ''

this.browserProxy_.getRegionalLists().then(value => {
this.filterList_ = value
})
Expand All @@ -71,6 +75,20 @@ class AdBlockSubpage extends AdBlockSubpageBase {
}
}

handleUpdateLists_() {
if (this.listsUpdatingState_ === 'updating') {
return
}

this.listsUpdatingState_ = 'updating'

this.browserProxy_.updateFilterLists().then(() => {
this.listsUpdatingState_ = 'updated'
}, () => {
this.listsUpdatingState_ = 'failed'
})
}

searchListBy_(title) {
if (!title) {
this.hasListExpanded_ = false
Expand Down
35 changes: 35 additions & 0 deletions browser/ui/webui/settings/brave_adblock_handler.cc
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,11 @@ void BraveAdBlockHandler::RegisterMessages() {
base::BindRepeating(&BraveAdBlockHandler::EnableFilterList,
base::Unretained(this)));

web_ui()->RegisterMessageCallback(
"brave_adblock.updateFilterLists",
base::BindRepeating(&BraveAdBlockHandler::UpdateFilterLists,
base::Unretained(this)));

web_ui()->RegisterMessageCallback(
"brave_adblock.getListSubscriptions",
base::BindRepeating(&BraveAdBlockHandler::GetListSubscriptions,
Expand Down Expand Up @@ -123,6 +128,23 @@ void BraveAdBlockHandler::EnableFilterList(const base::Value::List& args) {
->EnableFilterList(uuid, enabled);
}

void BraveAdBlockHandler::UpdateFilterLists(const base::Value::List& args) {
AllowJavascript();

DCHECK_EQ(args.size(), 1U);
if (!args[0].is_string()) {
return;
}

std::string callback_id = args[0].GetString();

g_brave_browser_process->ad_block_service()
->component_service_manager()
->UpdateFilterLists(
base::BindOnce(&BraveAdBlockHandler::OnFilterListsUpdated,
weak_factory_.GetWeakPtr(), std::move(callback_id)));
}

void BraveAdBlockHandler::GetListSubscriptions(const base::Value::List& args) {
AllowJavascript();
ResolveJavascriptCallback(args[0], GetSubscriptions());
Expand Down Expand Up @@ -284,3 +306,16 @@ base::Value::List BraveAdBlockHandler::GetSubscriptions() {

return list_value;
}

void BraveAdBlockHandler::OnFilterListsUpdated(std::string callback_id,
bool success) {
if (!IsJavascriptAllowed()) {
return;
}

if (success) {
ResolveJavascriptCallback(base::Value(callback_id), base::Value());
} else {
RejectJavascriptCallback(base::Value(callback_id), base::Value());
}
}
8 changes: 8 additions & 0 deletions browser/ui/webui/settings/brave_adblock_handler.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,12 @@
#ifndef BRAVE_BROWSER_UI_WEBUI_SETTINGS_BRAVE_ADBLOCK_HANDLER_H_
#define BRAVE_BROWSER_UI_WEBUI_SETTINGS_BRAVE_ADBLOCK_HANDLER_H_

#include <string>

#include "base/scoped_observation.h"

#include "base/memory/raw_ptr.h"
#include "base/memory/weak_ptr.h"
#include "brave/components/brave_shields/content/browser/ad_block_subscription_service_manager.h"
#include "brave/components/brave_shields/content/browser/ad_block_subscription_service_manager_observer.h"
#include "chrome/browser/ui/webui/settings/settings_page_ui_handler.h"
Expand Down Expand Up @@ -37,6 +40,7 @@ class BraveAdBlockHandler : public settings::SettingsPageUIHandler,

void GetRegionalLists(const base::Value::List& args);
void EnableFilterList(const base::Value::List& args);
void UpdateFilterLists(const base::Value::List& args);
void GetListSubscriptions(const base::Value::List& args);
void GetCustomFilters(const base::Value::List& args);
void AddSubscription(const base::Value::List& args);
Expand All @@ -50,11 +54,15 @@ class BraveAdBlockHandler : public settings::SettingsPageUIHandler,

base::Value::List GetSubscriptions();

void OnFilterListsUpdated(std::string callback_id, bool success);

raw_ptr<Profile> profile_ = nullptr;

base::ScopedObservation<AdBlockSubscriptionServiceManager,
AdBlockSubscriptionServiceManagerObserver>
service_observer_{this};

base::WeakPtrFactory<BraveAdBlockHandler> weak_factory_{this};
};

#endif // BRAVE_BROWSER_UI_WEBUI_SETTINGS_BRAVE_ADBLOCK_HANDLER_H_
Original file line number Diff line number Diff line change
Expand Up @@ -689,6 +689,14 @@ void BraveAddCommonStrings(content::WebUIDataSource* html_source,
{"adblockAddListsButtonLabel", IDS_BRAVE_ADBLOCK_ADD_LISTS_BUTTON_LABEL},
{"adblockShowFullListsButtonLabel",
IDS_BRAVE_ADBLOCK_SHOW_FULL_LISTS_BUTTON_LABEL},
{"adblockUpdateListsButtonLabel",
IDS_BRAVE_ADBLOCK_UPDATE_LISTS_BUTTON_LABEL},
{"adblockUpdateListsRetryButtonLabel",
IDS_BRAVE_ADBLOCK_UPDATE_LISTS_RETRY_BUTTON_LABEL},
{"adblockUpdateListsUpdatedButtonLabel",
IDS_BRAVE_ADBLOCK_UPDATE_LISTS_UPDATED_BUTTON_LABEL},
{"adblockUpdateListsUpdatingButtonLabel",
IDS_BRAVE_ADBLOCK_UPDATE_LISTS_UPDATING_BUTTON_LABEL},
{"adblockFilterListsInputURLPlaceholder",
IDS_BRAVE_ADBLOCK_CUSTOM_FILTER_LISTS_INPUT_PLACEHOLDER},
{"adblockContentFiltersLabel", IDS_BRAVE_ADBLOCK_CONTENT_FILTERS},
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,14 +14,19 @@ class BraveComponentUpdaterAndroid;
}
} // namespace chrome

namespace brave_shields {
class AdBlockComponentFiltersProvider;
}

#define BRAVE_COMPONENT_UPDATER_SERVICE_H_ \
friend class ::IPFSDOMHandler; \
friend class ::chrome::android::BraveComponentUpdaterAndroid;

#define BRAVE_COMPONENT_UPDATER_SERVICE_H_ON_DEMAND_UPDATER \
private: \
friend void BraveOnDemandUpdate(const std::string&); \
\
#define BRAVE_COMPONENT_UPDATER_SERVICE_H_ON_DEMAND_UPDATER \
private: \
friend void BraveOnDemandUpdate(const std::string&); \
friend class brave_shields::AdBlockComponentFiltersProvider; \
\
public:
#include "src/components/component_updater/component_updater_service.h" // IWYU pragma: export
#undef BRAVE_COMPONENT_UPDATER_SERVICE_H_ON_DEMAND_UPDATER
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -125,4 +125,21 @@ void AdBlockComponentFiltersProvider::LoadFilterSet(
base::BindOnce(&OnReadDATFileData, std::move(cb), permission_mask_));
}

void AdBlockComponentFiltersProvider::UpdateComponent(
base::OnceCallback<void(bool)> callback) {
if (!component_updater_service_) {
std::move(callback).Run(false);
return;
}

auto on_updated = [](decltype(callback) cb, update_client::Error error) {
std::move(cb).Run(error == update_client::Error::NONE ||
error == update_client::Error::UPDATE_IN_PROGRESS);
};

component_updater_service_->GetOnDemandUpdater().OnDemandUpdate(
component_id_, component_updater::OnDemandUpdater::Priority::FOREGROUND,
base::BindOnce(on_updated, std::move(callback)));
}

} // namespace brave_shields
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,10 @@ class AdBlockComponentFiltersProvider : public AdBlockFiltersProvider {
base::OnceCallback<void(
base::OnceCallback<void(rust::Box<adblock::FilterSet>*)>)>) override;

// Updates the component, and when complete executes the specified callback
// with a value indicating success or failure.
void UpdateComponent(base::OnceCallback<void(bool)> callback);

// Remove the component. This will force it to be redownloaded next time it
// is registered.
void UnregisterComponent();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,9 +9,11 @@
#include <utility>
#include <vector>

#include "base/barrier_callback.h"
#include "base/feature_list.h"
#include "base/memory/raw_ref.h"
#include "base/metrics/histogram_macros.h"
#include "base/ranges/algorithm.h"
#include "base/values.h"
#include "brave/components/brave_shields/core/browser/ad_block_component_filters_provider.h"
#include "brave/components/brave_shields/core/browser/ad_block_filters_provider_manager.h"
Expand Down Expand Up @@ -259,6 +261,35 @@ void AdBlockComponentServiceManager::EnableFilterList(const std::string& uuid,
UpdateFilterListPrefs(uuid, enabled);
}

void AdBlockComponentServiceManager::UpdateFilterLists(
base::OnceCallback<void(bool)> callback) {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);

// If there are currently no components to update, then run the callback with
// a success value in a future turn.
if (component_filters_providers_.empty()) {
std::move(callback).Run(true);
return;
}

// This callback will be executed by our barrier callback once all filter
// list components have been updated.
auto on_all_updated = [](decltype(callback) cb, std::vector<bool> results) {
std::move(cb).Run(
base::ranges::all_of(results, [](bool result) { return result; }));
};

// This barrier callback maintains a "completed count". When it has been
// called the expected number of times, it will execute `on_all_updated`.
auto barrier_callback = base::BarrierCallback<bool>(
component_filters_providers_.size(),
base::BindOnce(on_all_updated, std::move(callback)));

for (auto& [key, provider] : component_filters_providers_) {
provider->UpdateComponent(barrier_callback);
}
}

void AdBlockComponentServiceManager::SetFilterListCatalog(
std::vector<FilterListCatalogEntry> catalog) {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,8 @@ class AdBlockComponentServiceManager
bool IsFilterListEnabled(const std::string& uuid) const;
void EnableFilterList(const std::string& uuid, bool enabled);

void UpdateFilterLists(base::OnceCallback<void(bool)> callback);

// AdBlockFilterListCatalogProvider::Observer
void OnFilterListCatalogLoaded(const std::string& catalog_json) override;

Expand Down
1 change: 1 addition & 0 deletions ui/webui/resources/leo/web_components.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
import '@brave/leo/web-components/button'
import '@brave/leo/web-components/dropdown'
import '@brave/leo/web-components/checkbox'
import '@brave/leo/web-components/progressRing'
import '@brave/leo/web-components/toggle'
import { setIconBasePath } from '@brave/leo/web-components/icon'
import iconsMeta from '@brave/leo/icons/meta'
Expand Down
Loading