组态:
重现此问题的步骤:
预期的行为是什么?
PDF可以像Firefox之外的其他所有浏览器一样打印
什么地方出了错?
Error: Permission denied to access property 'print'
请解决此问题,因为自Firefox包含pdf.js以来,Firefox中浏览器PDF的通用打印解决方案已被中断5年。
由于单个项目pdf.js ,Web开发人员社区对此有数百种不良解决方案。
与https://github.com/mozilla/pdf.js/issues/5397相似,但是是否使用iframe
没有关系。
如果使用<object>
则会出现相同的问题
<object type="application/pdf"
data="/media/examples/In-CC0.pdf"
width="250"
height="200">
</object>
重现此问题的步骤:
1. https://bugzilla.mozilla.org/show_bug.cgi?id=911444#c53
如果在Bugzilla中已经明确跟踪了此问题,为什么还要在此处打开重复的问题?
特别是因为这甚至不是(通用)PDF.js库本身中的错误,而是Firefox浏览器中的一个限制(如链接的错误中所述,因此该存储库中也不会发生任何修复)。
@Snuffleupagus因为Firefox错误是5年前报告的,其根本原因是pdf.js,而不是Firefox。 没有Firefox开发人员可以解决这个问题,我已经多次遇到这个问题,只能通过更改pdf.js而不是Firefox来解决。
澄清一下, pdf.js的工作方式是正常打印文档(15年以上),在使用pdf.js的情况下,在这种情况下为PDF, print()
抛出错误。过去5年在Firefox中显示PDF的默认方式。
我可能是错的,因为错误实际上是pdf.jsprint()
并使用其内部逻辑来打印PDF文档。
window.onbeforeprint = function() {
console.log('This will be called before the user prints.');
};
window.onafterprint = function() {
console.log('This will be called after the user prints');
};
自Firefox 6起应该可以使用
window.matchMedia('print')
可能无法工作,因为错误https://bugzilla.mozilla.org/show_bug.cgi?id=774398未标记为已修复或已解决。
这是#5397的重复副本–问题的根本原因是pdf.js嵌入到具有“ resource://pdf.js ”安全主体的文档中。 它与嵌入主体不同,因此同源策略会阻止对print和其他属性的访问。 嵌入到iframe还是对象中都没关系。
@Snuffleupagus是Firefox中嵌入的pdf.js软件包的Web文件夹部分吗?
我发现的唯一打印逻辑是在https://github.com/mozilla/pdf.js/blob/master/web/firefox_print_service.js
#5397的主要问题是,一半是关于使用pdf.js时的打印,另一半是关于pdf.js呈现文档时如何在Firefox中打印文档的,就像这张票证一样。 @automatedbugreportingfacility你是正确的,但是我觉得这需要一个新的问题,因为#5397令人困惑。
更改URI应该在https://bugzilla.mozilla.org/show_bug.cgi?id=911444#c53中进行,但是代替Firefox中的修复(5年内不会发生),一种解决方法是监听参加beforeprint
事件,并开始通过pdf.js打印。 如果beforeprint
由于相同的安全策略而被Firefox阻止,则只能在Firefox中发生。
也许你们其中一个可以澄清这个问题?
解决方法是监听preprint事件并通过pdf.js开始打印。
你能澄清一下吗? 为了将beforeprint
事件发送到嵌入式pdf.js文档,您需要在父窗口的上下文中调用print()
。 然后,浏览器将打印父窗口的内容。 您无法在事件处理程序中“开始打印”,因为它已经开始打印父文档。
pdf.js方面可能的解决方法是实现onmessage
处理程序,以允许通过pdfWindow.postMessage("print");
打印,但是我不确定这是否是理想的解决方案。
pdf.js方面的一种可能的解决方法是实现onmessage处理程序以允许通过pdfWindow.postMessage(“ print”);进行打印,但是我不确定这是否是理想的解决方案。
@automatedbugreportingfacility uf,这根本不是不希望的。 完美的解决方案是与所有其他浏览器具有DOM API奇偶校验,您可以在其中使用.print()
在PDF文档容器上。
我没有创建此问题,因为我使用的是pdf.js,但是由于Firefox使用的是pdf.js,并且自pdf.js成为在Firefox中呈现PDF的标准以来, print()
一直没有用。
如果在Firefox中解决此问题,而不是在pdf.js中解决此问题,我会很高兴-要么我会很高兴😃
[...]那么它只能在Firefox中发生。
也许你们其中一个可以澄清这个问题?
我已经在https://github.com/mozilla/pdf.js/issues/10290#issuecomment -441132851中声明与该存储库无关,以及https://github.com/mozilla/pdf.js/issues/ 10290#issuecomment -441202543概述了(为什么会这样)。 同样,请注意,没有必要/不希望重复出现问题。
为了甚至触摸.print
而不会引发安全错误,需要针对我在上文中描述的resource://pdf.js
情况进行修复,这将在Firefox中完成。 由于这里没有pdf.js的工作,并且我们在#5397中反映了上游错误,因此我们可以解决此问题。
@Snuffleupagus和@automatedbugreportingfacility只是为了确保我理解您在说什么。
调用print()
时,无法在pdf.js中创建变通方法Firefox安全策略。
以上正确吗?
是的,您无法在浏览器的安全性机制上打个洞。 首先,将pdf.js嵌入半特权文档中是一个大错误,但是没有回头路了,Mozilla遗憾地更喜欢花钱购买“ Project Mortar”这类临时性的东西。 但是我离题了。
砂浆实验已经结束。 Mozilla认为PDF用例不能证明在Gecko中实现和维护PDFium和Pepper API实现的负担。
那么至少Motar已停产。
这个问题肯定可以解决,但是在我(您)这样做之前,由于我在这里拥有2位pdf.js专家,所以我有两个问题可能会帮助https://bugzilla.mozilla.org/show_bug.cgi?id=911444在正确的方向。
首先将pdf.js嵌入半特权文档中是一个大错误,但没有回头路可走
@automatedbugreportingfacility为什么这个决定是不可逆的?
您难道不可以使用pdf.js创建一个新的空白文档,并且其原始来源与父窗口相同,然后将PDF文件提供给pdf.js吗?
<iframe id="pdf" src="some-same-origin.pdf"></iframe>
<script>
document.getElementById('pdf').print()
</script>
奖励积分是,如果pdf.js收听beforeprint
,则取消该事件并打印<canvas>
(PDF文档),而不让FIrefox打印pdf.js UI。
我想,如果将pdf.js作为常规文档嵌入,您将能够收听父窗口。
window.opener.addEventListener('beforeprint', event => {
event.preventDefault()
window.print() // pdf.js overrides the native print function already
})
或将pdf.js更改为:
let print = (window.opener || window).print;
window.print = function print() {
if (activeService) {
console.warn('Ignored window.print() because of a pending print job.');
return;
}
...
再三考虑,这意味着pdf.js会吞下父级的打印品,这不是我们想要的。
实际上pdf.js已经在做正确的事情。 我们只需要firefox在嵌入pdf.js的文档上调度print()
。
摘录自_pdf_print_service.js_(位于https://mozilla.github.io/pdf.js/web/viewer.html):
let print = window.print;
window.print = function print() {
if (activeService) {
console.warn('Ignored window.print() because of a pending print job.');
return;
}
ensureOverlay().then(function() {
if (activeService) {
overlayManager.open('printServiceOverlay');
}
});
try {
dispatchEvent('beforeprint');
} finally {
if (!activeService) {
console.error('Expected print service to be initialized.');
ensureOverlay().then(function() {
if (overlayManager.active === 'printServiceOverlay') {
overlayManager.close('printServiceOverlay');
}
});
return; // eslint-disable-line no-unsafe-finally
}
let activeServiceOnEntry = activeService;
activeService.renderPages().then(function() {
return activeServiceOnEntry.performPrint();
}).catch(function() {
// Ignore any error messages.
}).then(function() {
// aborts acts on the "active" print request, so we need to check
// whether the print request (activeServiceOnEntry) is still active.
// Without the check, an unrelated print request (created after aborting
// this print request while the pages were being generated) would be
// aborted.
if (activeServiceOnEntry.active) {
abort();
}
});
}
};
function dispatchEvent(eventType) {
let event = document.createEvent('CustomEvent');
event.initCustomEvent(eventType, false, false, 'custom');
window.dispatchEvent(event);
}
function abort() {
if (activeService) {
activeService.destroy();
dispatchEvent('afterprint');
}
}
@Ugoku和@jtraulle请在https://bugzilla.mozilla.org/show_bug.cgi?id=911444上投票,以使其受到Firefox开发人员的关注。
感谢@dotnetCarpenter ,我对Bugzilla🐞进行了投票
使用Firefox遇到了相同的问题。 将包含pdf的文件解决成这样的iframe(关键是pdf的链接方式):
`$(“。div_class”)。html(' ');
$('#frame_id')
.attr(“ src”,“ path_to / PDFJS / web / viewer.html?file = path_to / file.pdf”)
.on(“ load”,function(){
setTimeout(printWhenReady,3000);
});
}
函数printWhenReady(){
document.getElementById(frame_id).contentWindow.print();
}`
为什么反复打开它,却被反复说是https://bugzilla.mozilla.org/show_bug.cgi?id=911444的副本,而不能在此存储库中修复!
@timvandermeij您能否关闭此问题?
我重新打开了它,以便成千上万的Web开发人员可以看到
最终碰到这个问题。 它使发现和引导人们变得容易
bugzilla问题。 我认为这比不断得到重复更好
但是我退缩了。
2019年1月8日,星期二,晚上11:21蒂姆·范·德·迈伊notifications@github.com
写道:
已关闭#10290 https://github.com/mozilla/pdf.js/issues/10290 。
-
您收到此消息是因为您修改了打开/关闭状态。
直接回复此电子邮件,在GitHub上查看
https://github.com/mozilla/pdf.js/issues/10290#event-2061484528或静音
线程
https://github.com/notifications/unsubscribe-auth/AACq8wR4vNFtCtaUI-VRshKnQyDCQoZVks5vBRoGgaJpZM4Yv9So
。
使用Firefox遇到了相同的问题。 将包含pdf的文件解决成这样的iframe(关键是pdf的链接方式):
`$(“。div_class”)。html(' ');
$('#frame_id')
.attr(“ src”,“ path_to / PDFJS / web / viewer.html?file = path_to / file.pdf”)
.on(“ load”,function(){
setTimeout(printWhenReady,3000);
});
}函数printWhenReady(){
document.getElementById(frame_id).contentWindow.print();
}`
不,在firefox控制台中仍然SecurityError: Permission denied to access property "print" on cross-origin object
错误
使用Firefox遇到了相同的问题。 将包含pdf的文件解决成这样的iframe(关键是pdf的链接方式):
$(".div_class").html('<iframe id="frame_id"></iframe>'); $('#frame_id') .attr("src", "path_to/PDFJS/web/viewer.html?file=path_to/file.pdf") .on("load", function(){ setTimeout(printWhenReady, 3000); }); } function printWhenReady(){ document.getElementById(frame_id).contentWindow.print(); }
否,firefox控制台中仍然出现
SecurityError: Permission denied to access property "print" on cross-origin object
错误
@shmilyoo请问您如何获得PDFjs的路径?
@vaspervnp如果我可能要问,您是否能够以编程方式调用打印功能?
具有讽刺意味的是, @ vaspervnp与Firefox中嵌入的Mozilla查看器完全相同!
我们确实需要有人来更改pdf.js在Firefox中的嵌入方式: https ://bugzilla.mozilla.org/show_bug.cgi?id=911444#c58
@vaspervnp如果我可能要问,您是否能够以编程方式调用打印功能?
是的,我是。
@vaspervnp ,如果您可以提供一些有关如何执行此操作的代码段,那将很好。
@didagu
我没有写任何其他代码。 我只是从此处包含了javascript和查看器: http :
您是否需要特殊特权才能在bugzilla上投票? 我在任何地方都看不到该选项。
@ mdodge-ecgrow看起来像bugzilla在进行重新设计时删除了投票功能。 我不确定现在应该如何吸引Firefox开发人员的注意...
@dotnetCarpenter锦上添花的是,一年多以前,一位开发人员抱怨说,所有+1注释都使得查看技术性讨论更加困难,因此也难以解决该错误。 好像这就是为什么它开放超过6年并不断增加的原因。 没有投票系统,这些评论现在是引起人们注意的唯一方法,因此,我认为别无选择。
最有用的评论
@dotnetCarpenter锦上添花的是,一年多以前,一位开发人员抱怨说,所有+1注释都使得查看技术性讨论更加困难,因此也难以解决该错误。 好像这就是为什么它开放超过6年并不断增加的原因。 没有投票系统,这些评论现在是引起人们注意的唯一方法,因此,我认为别无选择。