diff --git a/chrome/app/generated_resources.grd b/chrome/app/generated_resources.grd
index a816fdfbcbe7c..d0a02e08fa9e7 100644
--- a/chrome/app/generated_resources.grd
+++ b/chrome/app/generated_resources.grd
@@ -10461,6 +10461,16 @@ Please help our engineers fix this problem. Tell us what happened right before y
+
+
+
+ Open $1.txt, .csv, .md files
+
+
+ , '''
+
+
+
diff --git a/chrome/app/generated_resources_grd/IDS_WEB_APP_FILE_HANDLING_EXTENSION_LIST_SEPARATOR.png.sha1 b/chrome/app/generated_resources_grd/IDS_WEB_APP_FILE_HANDLING_EXTENSION_LIST_SEPARATOR.png.sha1
new file mode 100644
index 0000000000000..6ee6d61a3e4af
--- /dev/null
+++ b/chrome/app/generated_resources_grd/IDS_WEB_APP_FILE_HANDLING_EXTENSION_LIST_SEPARATOR.png.sha1
@@ -0,0 +1 @@
+aa286efbaee111ce1a8e37854ff384fa397f929e
\ No newline at end of file
diff --git a/chrome/app/generated_resources_grd/IDS_WEB_APP_FILE_HANDLING_PERMISSION_TEXT.png.sha1 b/chrome/app/generated_resources_grd/IDS_WEB_APP_FILE_HANDLING_PERMISSION_TEXT.png.sha1
new file mode 100644
index 0000000000000..6ee6d61a3e4af
--- /dev/null
+++ b/chrome/app/generated_resources_grd/IDS_WEB_APP_FILE_HANDLING_PERMISSION_TEXT.png.sha1
@@ -0,0 +1 @@
+aa286efbaee111ce1a8e37854ff384fa397f929e
\ No newline at end of file
diff --git a/chrome/browser/permissions/permission_manager_factory.cc b/chrome/browser/permissions/permission_manager_factory.cc
index 4012e39323ee3..3811b0d846c91 100644
--- a/chrome/browser/permissions/permission_manager_factory.cc
+++ b/chrome/browser/permissions/permission_manager_factory.cc
@@ -32,7 +32,6 @@
#include "components/keyed_service/content/browser_context_dependency_manager.h"
#include "components/permissions/contexts/clipboard_read_write_permission_context.h"
#include "components/permissions/contexts/clipboard_sanitized_write_permission_context.h"
-#include "components/permissions/contexts/file_handling_permission_context.h"
#include "components/permissions/contexts/font_access_permission_context.h"
#include "components/permissions/contexts/midi_permission_context.h"
#include "components/permissions/contexts/midi_sysex_permission_context.h"
@@ -51,6 +50,7 @@
#include "components/permissions/contexts/nfc_permission_context_android.h"
#else
#include "chrome/browser/geolocation/geolocation_permission_context_delegate.h"
+#include "chrome/browser/web_applications/components/file_handling_permission_context.h"
#include "components/permissions/contexts/geolocation_permission_context.h"
#include "components/permissions/contexts/nfc_permission_context.h"
#endif
@@ -141,8 +141,10 @@ permissions::PermissionManager::PermissionContextMap CreatePermissionContexts(
std::make_unique(profile);
permission_contexts[ContentSettingsType::DISPLAY_CAPTURE] =
std::make_unique(profile);
+#if !defined(OS_ANDROID) // File Handling is not available on Android.
permission_contexts[ContentSettingsType::FILE_HANDLING] =
std::make_unique(profile);
+#endif // !defined(OS_ANDROID)
return permission_contexts;
}
} // namespace
diff --git a/chrome/browser/web_applications/components/BUILD.gn b/chrome/browser/web_applications/components/BUILD.gn
index f4326094e0980..bbf26dcd6e8f3 100644
--- a/chrome/browser/web_applications/components/BUILD.gn
+++ b/chrome/browser/web_applications/components/BUILD.gn
@@ -24,6 +24,10 @@ source_set("components") {
"externally_managed_app_manager.h",
"file_handler_manager.cc",
"file_handler_manager.h",
+ "file_handling_permission_context.cc",
+ "file_handling_permission_context.h",
+ "file_handling_permission_request_impl.cc",
+ "file_handling_permission_request_impl.h",
"install_bounce_metric.cc",
"install_bounce_metric.h",
"install_finalizer.cc",
@@ -181,6 +185,7 @@ source_set("components") {
"//chrome/common",
"//components/crx_file",
"//components/keyed_service/content",
+ "//components/permissions:permissions",
"//components/pref_registry",
"//components/services/app_service/public/cpp:protocol_handling",
"//components/services/app_service/public/mojom",
diff --git a/chrome/browser/web_applications/components/file_handling_permission_context.cc b/chrome/browser/web_applications/components/file_handling_permission_context.cc
new file mode 100644
index 0000000000000..1d344b77e402b
--- /dev/null
+++ b/chrome/browser/web_applications/components/file_handling_permission_context.cc
@@ -0,0 +1,40 @@
+// Copyright 2021 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "chrome/browser/web_applications/components/file_handling_permission_context.h"
+
+#include
+
+#include "chrome/browser/web_applications/components/file_handling_permission_request_impl.h"
+#include "components/content_settings/core/common/content_settings_types.h"
+#include "components/permissions/permission_context_base.h"
+#include "content/public/browser/web_contents.h"
+#include "third_party/blink/public/mojom/permissions_policy/permissions_policy.mojom.h"
+
+FileHandlingPermissionContext::FileHandlingPermissionContext(
+ content::BrowserContext* browser_context)
+ : PermissionContextBase(browser_context,
+ ContentSettingsType::FILE_HANDLING,
+ blink::mojom::PermissionsPolicyFeature::kNotFound) {
+}
+
+FileHandlingPermissionContext::~FileHandlingPermissionContext() = default;
+
+bool FileHandlingPermissionContext::IsRestrictedToSecureOrigins() const {
+ return true;
+}
+
+std::unique_ptr
+FileHandlingPermissionContext::CreatePermissionRequest(
+ const GURL& request_origin,
+ ContentSettingsType content_settings_type,
+ bool has_gesture,
+ content::WebContents* web_contents,
+ permissions::PermissionRequestImpl::PermissionDecidedCallback
+ permission_decided_callback,
+ base::OnceClosure delete_callback) const {
+ return std::make_unique(
+ request_origin, content_settings_type, has_gesture, web_contents,
+ std::move(permission_decided_callback), std::move(delete_callback));
+}
diff --git a/components/permissions/contexts/file_handling_permission_context.h b/chrome/browser/web_applications/components/file_handling_permission_context.h
similarity index 50%
rename from components/permissions/contexts/file_handling_permission_context.h
rename to chrome/browser/web_applications/components/file_handling_permission_context.h
index 16442e7903178..6c65928c94044 100644
--- a/components/permissions/contexts/file_handling_permission_context.h
+++ b/chrome/browser/web_applications/components/file_handling_permission_context.h
@@ -2,11 +2,15 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef COMPONENTS_PERMISSIONS_CONTEXTS_FILE_HANDLING_PERMISSION_CONTEXT_H_
-#define COMPONENTS_PERMISSIONS_CONTEXTS_FILE_HANDLING_PERMISSION_CONTEXT_H_
+#ifndef CHROME_BROWSER_WEB_APPLICATIONS_COMPONENTS_FILE_HANDLING_PERMISSION_CONTEXT_H_
+#define CHROME_BROWSER_WEB_APPLICATIONS_COMPONENTS_FILE_HANDLING_PERMISSION_CONTEXT_H_
#include "components/permissions/permission_context_base.h"
+namespace content {
+class WebContents;
+} // namespace content
+
class FileHandlingPermissionContext
: public permissions::PermissionContextBase {
public:
@@ -21,6 +25,14 @@ class FileHandlingPermissionContext
protected:
// PermissionContextBase:
bool IsRestrictedToSecureOrigins() const override;
+ std::unique_ptr CreatePermissionRequest(
+ const GURL& request_origin,
+ ContentSettingsType content_settings_type,
+ bool has_gesture,
+ content::WebContents* web_contents,
+ permissions::PermissionRequestImpl::PermissionDecidedCallback
+ permission_decided_callback,
+ base::OnceClosure delete_callback) const override;
};
-#endif // COMPONENTS_PERMISSIONS_CONTEXTS_FILE_HANDLING_PERMISSION_CONTEXT_H_
+#endif // CHROME_BROWSER_WEB_APPLICATIONS_COMPONENTS_FILE_HANDLING_PERMISSION_CONTEXT_H_
diff --git a/chrome/browser/web_applications/components/file_handling_permission_request_impl.cc b/chrome/browser/web_applications/components/file_handling_permission_request_impl.cc
new file mode 100644
index 0000000000000..c47de69c44b23
--- /dev/null
+++ b/chrome/browser/web_applications/components/file_handling_permission_request_impl.cc
@@ -0,0 +1,51 @@
+// Copyright 2021 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "chrome/browser/web_applications/components/file_handling_permission_request_impl.h"
+
+#include "base/strings/utf_string_conversions.h"
+#include "chrome/browser/profiles/profile.h"
+#include "chrome/browser/web_applications/components/web_app_utils.h"
+#include "chrome/grit/generated_resources.h"
+#include "components/strings/grit/components_strings.h"
+#include "content/public/browser/web_contents.h"
+#include "ui/base/l10n/l10n_util.h"
+
+namespace permissions {
+
+FileHandlingPermissionRequestImpl::FileHandlingPermissionRequestImpl(
+ const GURL& request_origin,
+ ContentSettingsType content_settings_type,
+ bool has_gesture,
+ content::WebContents* web_contents,
+ PermissionDecidedCallback permission_decided_callback,
+ base::OnceClosure delete_callback)
+ : PermissionRequestImpl(request_origin,
+ content_settings_type,
+ has_gesture,
+ std::move(permission_decided_callback),
+ std::move(delete_callback)) {
+ auto* browser = web_contents->GetBrowserContext();
+ if (!browser) {
+ return;
+ }
+ Profile* profile = Profile::FromBrowserContext(browser);
+ DCHECK(profile);
+
+ std::u16string extensions_list =
+ web_app::GetFileExtensionsHandledByWebAppDisplayedAsList(
+ profile, web_contents->GetLastCommittedURL());
+ message_text_fragment_ = l10n_util::GetStringFUTF16(
+ IDS_WEB_APP_FILE_HANDLING_PERMISSION_TEXT, extensions_list);
+}
+
+FileHandlingPermissionRequestImpl::~FileHandlingPermissionRequestImpl() =
+ default;
+
+std::u16string FileHandlingPermissionRequestImpl::GetMessageTextFragment()
+ const {
+ return message_text_fragment_;
+}
+
+} // namespace permissions
diff --git a/chrome/browser/web_applications/components/file_handling_permission_request_impl.h b/chrome/browser/web_applications/components/file_handling_permission_request_impl.h
new file mode 100644
index 0000000000000..c1287e2ae4b01
--- /dev/null
+++ b/chrome/browser/web_applications/components/file_handling_permission_request_impl.h
@@ -0,0 +1,36 @@
+// Copyright 2021 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef CHROME_BROWSER_WEB_APPLICATIONS_COMPONENTS_FILE_HANDLING_PERMISSION_REQUEST_IMPL_H_
+#define CHROME_BROWSER_WEB_APPLICATIONS_COMPONENTS_FILE_HANDLING_PERMISSION_REQUEST_IMPL_H_
+
+#include
+#include "components/permissions/permission_request_impl.h"
+
+namespace content {
+class WebContents;
+}
+
+namespace permissions {
+
+// Provides a custom message text fragment that differs based on file handlers
+// requested by a web app.
+class FileHandlingPermissionRequestImpl : public PermissionRequestImpl {
+ public:
+ FileHandlingPermissionRequestImpl(
+ const GURL& request_origin,
+ ContentSettingsType content_settings_type,
+ bool has_gesture,
+ content::WebContents* web_contents,
+ PermissionDecidedCallback permission_decided_callback,
+ base::OnceClosure delete_callback);
+ ~FileHandlingPermissionRequestImpl() override;
+
+ private:
+ std::u16string GetMessageTextFragment() const override;
+ std::u16string message_text_fragment_;
+};
+} // namespace permissions
+
+#endif // CHROME_BROWSER_WEB_APPLICATIONS_COMPONENTS_FILE_HANDLING_PERMISSION_REQUEST_IMPL_H_
diff --git a/chrome/browser/web_applications/components/web_app_utils.cc b/chrome/browser/web_applications/components/web_app_utils.cc
index 5f91d23f48556..dde204bb82ca2 100644
--- a/chrome/browser/web_applications/components/web_app_utils.cc
+++ b/chrome/browser/web_applications/components/web_app_utils.cc
@@ -5,10 +5,18 @@
#include "chrome/browser/web_applications/components/web_app_utils.h"
#include "base/files/file_path.h"
+#include "base/strings/string_util.h"
+#include "base/strings/utf_string_conversions.h"
#include "build/chromeos_buildflags.h"
#include "chrome/browser/profiles/profile.h"
+#include "chrome/browser/web_applications/components/app_registrar.h"
+#include "chrome/browser/web_applications/components/web_app_provider_base.h"
#include "chrome/common/chrome_constants.h"
+#include "chrome/grit/generated_resources.h"
+#include "components/services/app_service/public/cpp/file_handler.h"
#include "components/site_engagement/content/site_engagement_service.h"
+#include "ui/base/l10n/l10n_util.h"
+#include "url/gurl.h"
#if BUILDFLAG(IS_CHROMEOS_ASH)
#include "base/feature_list.h"
@@ -131,4 +139,25 @@ bool IsChromeOs() {
#endif
}
+std::vector GetFileExtensionsHandledByWebApp(Profile* profile,
+ const GURL& url) {
+ auto* provider = WebAppProviderBase::GetProviderBase(profile);
+ const AppRegistrar& registrar = provider->registrar();
+ const apps::FileHandlers* handlers =
+ registrar.GetAppFileHandlers(*registrar.FindAppWithUrlInScope(url));
+ DCHECK(handlers);
+ std::set extensions =
+ apps::GetFileExtensionsFromFileHandlers(*handlers);
+ return std::vector(extensions.begin(), extensions.end());
+}
+
+std::u16string GetFileExtensionsHandledByWebAppDisplayedAsList(
+ Profile* profile,
+ const GURL& url) {
+ return base::UTF8ToUTF16(base::JoinString(
+ GetFileExtensionsHandledByWebApp(profile, url),
+ l10n_util::GetStringUTF8(
+ IDS_WEB_APP_FILE_HANDLING_EXTENSION_LIST_SEPARATOR)));
+}
+
} // namespace web_app
diff --git a/chrome/browser/web_applications/components/web_app_utils.h b/chrome/browser/web_applications/components/web_app_utils.h
index 6955d1b0f13fb..a083f0f1f9dd9 100644
--- a/chrome/browser/web_applications/components/web_app_utils.h
+++ b/chrome/browser/web_applications/components/web_app_utils.h
@@ -6,9 +6,11 @@
#define CHROME_BROWSER_WEB_APPLICATIONS_COMPONENTS_WEB_APP_UTILS_H_
#include
+#include
#include "chrome/browser/web_applications/components/web_app_id.h"
+class GURL;
class Profile;
namespace base {
@@ -69,6 +71,18 @@ std::string GetProfileCategoryForLogging(Profile* profile);
// Returns true if the WebApp should have `web_app::WebAppChromeOsData()`.
bool IsChromeOs();
+// Returns a vector of file extensions of the form ".csv" which are handled by
+// the app for `url`. It is an error to call this with a URL that doesn't
+// correspond to an app in `profile`.
+std::vector GetFileExtensionsHandledByWebApp(Profile* profile,
+ const GURL& url);
+
+// Returns a display-ready string that holds all the file extensions handled by
+// the app for `url`. It is an error to call this with a URL that doesn't
+// correspond to an app in `profile`.
+std::u16string GetFileExtensionsHandledByWebAppDisplayedAsList(Profile* profile,
+ const GURL& url);
+
} // namespace web_app
#endif // CHROME_BROWSER_WEB_APPLICATIONS_COMPONENTS_WEB_APP_UTILS_H_
diff --git a/components/permissions/BUILD.gn b/components/permissions/BUILD.gn
index 44a59ca4e57f3..7639bb137b6bc 100644
--- a/components/permissions/BUILD.gn
+++ b/components/permissions/BUILD.gn
@@ -21,8 +21,6 @@ source_set("permissions") {
"contexts/clipboard_read_write_permission_context.h",
"contexts/clipboard_sanitized_write_permission_context.cc",
"contexts/clipboard_sanitized_write_permission_context.h",
- "contexts/file_handling_permission_context.cc",
- "contexts/file_handling_permission_context.h",
"contexts/font_access_permission_context.cc",
"contexts/font_access_permission_context.h",
"contexts/geolocation_permission_context.cc",
diff --git a/components/permissions/contexts/file_handling_permission_context.cc b/components/permissions/contexts/file_handling_permission_context.cc
deleted file mode 100644
index c1f7d2bac795b..0000000000000
--- a/components/permissions/contexts/file_handling_permission_context.cc
+++ /dev/null
@@ -1,21 +0,0 @@
-// Copyright 2021 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "components/permissions/contexts/file_handling_permission_context.h"
-
-#include "components/content_settings/core/common/content_settings_types.h"
-#include "third_party/blink/public/mojom/permissions_policy/permissions_policy.mojom.h"
-
-FileHandlingPermissionContext::FileHandlingPermissionContext(
- content::BrowserContext* browser_context)
- : PermissionContextBase(browser_context,
- ContentSettingsType::FILE_HANDLING,
- blink::mojom::PermissionsPolicyFeature::kNotFound) {
-}
-
-FileHandlingPermissionContext::~FileHandlingPermissionContext() = default;
-
-bool FileHandlingPermissionContext::IsRestrictedToSecureOrigins() const {
- return true;
-}
diff --git a/components/permissions/permission_context_base.cc b/components/permissions/permission_context_base.cc
index 2d8b6a5f3cec1..d98bac37cb4d0 100644
--- a/components/permissions/permission_context_base.cc
+++ b/components/permissions/permission_context_base.cc
@@ -219,6 +219,20 @@ void PermissionContextBase::UserMadePermissionDecision(
const GURL& embedding_origin,
ContentSetting content_setting) {}
+std::unique_ptr
+PermissionContextBase::CreatePermissionRequest(
+ const GURL& request_origin,
+ ContentSettingsType content_settings_type,
+ bool has_gesture,
+ content::WebContents* web_contents,
+ PermissionRequestImpl::PermissionDecidedCallback
+ permission_decided_callback,
+ base::OnceClosure delete_callback) const {
+ return std::make_unique(
+ request_origin, content_settings_type, has_gesture,
+ std::move(permission_decided_callback), std::move(delete_callback));
+}
+
PermissionResult PermissionContextBase::GetPermissionStatus(
content::RenderFrameHost* render_frame_host,
const GURL& requesting_origin,
@@ -373,14 +387,13 @@ void PermissionContextBase::DecidePermission(
if (!permission_request_manager)
return;
- std::unique_ptr request_ptr =
- std::make_unique(
- requesting_origin, content_settings_type_, user_gesture,
- base::BindOnce(&PermissionContextBase::PermissionDecided,
- weak_factory_.GetWeakPtr(), id, requesting_origin,
- embedding_origin, std::move(callback)),
- base::BindOnce(&PermissionContextBase::CleanUpRequest,
- weak_factory_.GetWeakPtr(), id));
+ std::unique_ptr request_ptr = CreatePermissionRequest(
+ requesting_origin, content_settings_type_, user_gesture, web_contents,
+ base::BindOnce(&PermissionContextBase::PermissionDecided,
+ weak_factory_.GetWeakPtr(), id, requesting_origin,
+ embedding_origin, std::move(callback)),
+ base::BindOnce(&PermissionContextBase::CleanUpRequest,
+ weak_factory_.GetWeakPtr(), id));
PermissionRequest* request = request_ptr.get();
bool inserted =
diff --git a/components/permissions/permission_context_base.h b/components/permissions/permission_context_base.h
index d310912d82380..93b981d2c3878 100644
--- a/components/permissions/permission_context_base.h
+++ b/components/permissions/permission_context_base.h
@@ -17,6 +17,7 @@
#include "components/content_settings/core/common/content_settings_types.h"
#include "components/keyed_service/core/keyed_service.h"
#include "components/permissions/permission_request.h"
+#include "components/permissions/permission_request_impl.h"
#include "components/permissions/permission_result.h"
#include "third_party/blink/public/mojom/permissions_policy/permissions_policy_feature.mojom-forward.h"
@@ -183,6 +184,17 @@ class PermissionContextBase : public KeyedService,
const ContentSettingsPattern& secondary_pattern,
ContentSettingsType content_type) override;
+ // Implementors can override this method to use a different PermissionRequest
+ // implementation.
+ virtual std::unique_ptr CreatePermissionRequest(
+ const GURL& request_origin,
+ ContentSettingsType content_settings_type,
+ bool has_gesture,
+ content::WebContents* web_contents,
+ PermissionRequestImpl::PermissionDecidedCallback
+ permission_decided_callback,
+ base::OnceClosure delete_callback) const;
+
ContentSettingsType content_settings_type() const {
return content_settings_type_;
}
diff --git a/components/permissions/permission_request_impl.cc b/components/permissions/permission_request_impl.cc
index 918449e614212..843d29159f322 100644
--- a/components/permissions/permission_request_impl.cc
+++ b/components/permissions/permission_request_impl.cc
@@ -186,9 +186,6 @@ std::u16string PermissionRequestImpl::GetMessageTextFragment() const {
case ContentSettingsType::IDLE_DETECTION:
message_id = IDS_IDLE_DETECTION_PERMISSION_FRAGMENT;
break;
- case ContentSettingsType::FILE_HANDLING:
- message_id = IDS_FILE_HANDLING_PERMISSION_FRAGMENT;
- break;
default:
NOTREACHED();
return std::u16string();
diff --git a/components/permissions/permission_request_impl.h b/components/permissions/permission_request_impl.h
index 2195d6f9f30fb..8f8645cdec357 100644
--- a/components/permissions/permission_request_impl.h
+++ b/components/permissions/permission_request_impl.h
@@ -35,14 +35,18 @@ class PermissionRequestImpl : public PermissionRequest {
~PermissionRequestImpl() override;
+// PermissionRequest:
+#if !defined(OS_ANDROID)
+ // Implementors can override this method to customize the message text.
+ std::u16string GetMessageTextFragment() const override;
+#endif
+
private:
- // PermissionRequest:
RequestType GetRequestType() const override;
#if defined(OS_ANDROID)
std::u16string GetMessageText() const override;
#else
base::Optional GetChipText() const override;
- std::u16string GetMessageTextFragment() const override;
#endif
GURL GetOrigin() const override;
void PermissionGranted(bool is_one_time) override;
diff --git a/components/permissions_strings.grdp b/components/permissions_strings.grdp
index c3d43fe4a04ec..847c24e04e706 100644
--- a/components/permissions_strings.grdp
+++ b/components/permissions_strings.grdp
@@ -140,10 +140,6 @@ This will otherwise be blocked by your privacy settings. This will allow the con
Allow $1google.com to:
-
- Open files with file type associations.
-
-
Use your location?
diff --git a/components/permissions_strings_grdp/IDS_FILE_HANDLING_PERMISSION_FRAGMENT.png.sha1 b/components/permissions_strings_grdp/IDS_FILE_HANDLING_PERMISSION_FRAGMENT.png.sha1
deleted file mode 100644
index 72ab8b24a86c6..0000000000000
--- a/components/permissions_strings_grdp/IDS_FILE_HANDLING_PERMISSION_FRAGMENT.png.sha1
+++ /dev/null
@@ -1 +0,0 @@
-55ddb345d69ee2187e402f22579fc4459b9563d1
\ No newline at end of file