Bug 1972100 - Only block sandboxed pdfs handled internally. r=smaug a=dmeehan

Differential Revision: https://phabricator.services.mozilla.com/D254662
This commit is contained in:
Andreas Farre
2025-06-23 14:00:29 +00:00
committed by dmeehan@mozilla.com
parent 3678041f7b
commit 54d1d9fabc
5 changed files with 70 additions and 11 deletions

View File

@@ -436,8 +436,7 @@ nsresult nsDocumentOpenInfo::DispatchContent(nsIRequest* request) {
// Check if this is a PDF which should be opened internally. We also handle // Check if this is a PDF which should be opened internally. We also handle
// octet-streams that look like they might be PDFs based on their extension. // octet-streams that look like they might be PDFs based on their extension.
if ((maybeForceInternalHandling || IsSandboxed(aChannel)) && if (maybeForceInternalHandling && IsContentPDF(aChannel, mContentType)) {
IsContentPDF(aChannel, mContentType)) {
// For a PDF, check if the preference is set that forces attachments to be // For a PDF, check if the preference is set that forces attachments to be
// opened inline. If so, treat it as a non-attachment by clearing // opened inline. If so, treat it as a non-attachment by clearing
// 'forceExternalHandling' again. This allows it open a PDF directly // 'forceExternalHandling' again. This allows it open a PDF directly

View File

@@ -119,7 +119,11 @@ support-files = [
] ]
["browser_pdf_sandboxed_iframe.js"] ["browser_pdf_sandboxed_iframe.js"]
support-files = ["file_pdf.pdf"] support-files = [
"file_pdf.pdf",
"file_pdf_content_disposition.pdf",
"file_pdf_content_disposition.pdf^headers^",
]
["browser_pdf_save_as.js"] ["browser_pdf_save_as.js"]

View File

@@ -117,10 +117,10 @@ async function onDownload(test) {
ok(true, "Download finished"); ok(true, "Download finished");
} }
async function onBlockedBySandbox(test) { async function onBlockedBySandbox(test, file) {
const expected = `Download of “${TEST_PATH}file_pdf.pdf” was blocked because the triggering iframe has the sandbox flag set.`; const expected = `Download of “${TEST_PATH}${file}” was blocked because the triggering iframe has the sandbox flag set.`;
return new Promise(resolve => { return new Promise(resolve => {
Services.console.registerListener(function onMessage(msg) { Services.console.registerListener(async function onMessage(msg) {
let { message, logLevel } = msg; let { message, logLevel } = msg;
if (logLevel != Ci.nsIConsoleMessage.warn) { if (logLevel != Ci.nsIConsoleMessage.warn) {
return; return;
@@ -146,46 +146,101 @@ const tests = [
preferredAction: alwaysAsk, preferredAction: alwaysAsk,
runTest: onExternalApplication, runTest: onExternalApplication,
header: "preferredAction = alwaysAsk", header: "preferredAction = alwaysAsk",
file: "file_pdf.pdf",
sandbox: "allow-downloads",
}, },
{ {
preferredAction: saveToDisk, preferredAction: saveToDisk,
runTest: onFilePickerShown, runTest: onFilePickerShown,
header: "preferredAction = saveToDisk", header: "preferredAction = saveToDisk",
file: "file_pdf.pdf",
sandbox: "allow-downloads",
}, },
{ {
// The preferredAction handleInternally is only noticed when we're getting
// an externally handled PDF that we forcefully handle internally.
preferredAction: handleInternally, preferredAction: handleInternally,
runTest: onBlockedBySandbox, runTest: onBlockedBySandbox,
header: "preferredAction = handleInternally", header: "preferredAction = handleInternally",
prefs: ["browser.download.open_pdf_attachments_inline", true],
file: "file_pdf_content_disposition.pdf",
sandbox: "allow-downloads",
}, },
{ {
preferredAction: useSystemDefault, preferredAction: useSystemDefault,
runTest: onDownload, runTest: onDownload,
header: "preferredAction = useSystemDefault", header: "preferredAction = useSystemDefault",
file: "file_pdf.pdf",
sandbox: "allow-downloads",
},
{
preferredAction: alwaysAsk,
runTest: onBlockedBySandbox,
header: "preferredAction = alwaysAsk",
file: "file_pdf.pdf",
},
{
preferredAction: saveToDisk,
runTest: onBlockedBySandbox,
header: "preferredAction = saveToDisk",
file: "file_pdf.pdf",
},
{
// The preferredAction handleInternally is only noticed when we're getting
// an externally handled PDF that we forcefully handle internally.
preferredAction: handleInternally,
runTest: onBlockedBySandbox,
header: "preferredAction = handleInternally",
prefs: ["browser.download.open_pdf_attachments_inline", true],
file: "file_pdf_content_disposition.pdf",
},
{
preferredAction: useSystemDefault,
runTest: onBlockedBySandbox,
header: "preferredAction = useSystemDefault",
file: "file_pdf.pdf",
}, },
]; ];
/** /**
* Tests that selecting the context menu item `Save Link As…` on a PDF link * Tests that selecting the context menu item `Save Link As…` on a PDF link
* opens the file picker when always_ask_before_handling_new_types is disabled, * opens the file picker when always_ask_before_handling_new_types is disabled,
* regardless of preferredAction. * regardless of preferredAction if the iframe has sandbox="allow-downloads".
*/ */
add_task(async function test_pdf_save_as_link() { add_task(async function test_pdf_save_as_link() {
let mimeInfo; let mimeInfo;
for (let { preferredAction, runTest, header } of tests) { for (let {
preferredAction,
runTest,
header,
prefs,
file,
sandbox,
} of tests) {
mimeInfo = MIMEService.getFromTypeAndExtension("application/pdf", "pdf"); mimeInfo = MIMEService.getFromTypeAndExtension("application/pdf", "pdf");
mimeInfo.alwaysAskBeforeHandling = preferredAction === alwaysAsk; mimeInfo.alwaysAskBeforeHandling = preferredAction === alwaysAsk;
mimeInfo.preferredAction = preferredAction; mimeInfo.preferredAction = preferredAction;
HandlerService.store(mimeInfo); HandlerService.store(mimeInfo);
info(`Running test: ${header}`); info(`Running test: ${header}, ${sandbox ? sandbox : "no sandbox"}`);
if (prefs) {
await SpecialPowers.pushPrefEnv({
set: [prefs],
});
}
await runTest(() => { await runTest(() => {
gBrowser.selectedTab = BrowserTestUtils.addTab( gBrowser.selectedTab = BrowserTestUtils.addTab(
gBrowser, gBrowser,
`data:text/html,<!doctype html><iframe sandbox="allow-downloads" src=${TEST_PATH}file_pdf.pdf></iframe>` `data:text/html,<!doctype html><iframe sandbox="${sandbox ?? ""}" src=${TEST_PATH}${file}></iframe>`
); );
}); }, file);
if (prefs) {
await SpecialPowers.popPrefEnv();
}
BrowserTestUtils.removeTab(gBrowser.selectedTab); BrowserTestUtils.removeTab(gBrowser.selectedTab);
} }

View File

@@ -0,0 +1 @@
Content-Disposition: attachment