【问题标题】:Print PDF to page with PHP & jQuery使用 PHP 和 jQuery 将 PDF 打印到页面
【发布时间】:2018-06-11 20:22:30
【问题描述】:

所以我需要一些关于我正在编写的 php 脚本的帮助,该脚本通过 PHP 脚本将 PDF 加载到新选项卡中。我这样做是为了确保只有在用户登录并具有指向它的链接时才能访问 PDF,否则 PDF 的父目录中的 .htaccess 会阻止访问。
我可以使用以下代码阅读 PDF:

$file = '../path-to-file.pdf';
$filename = 'filename.pdf';
header('Content-type: application/pdf');
header('Content-Disposition: inline; filename="' . $filename . '"');
header('Content-Transfer-Encoding: binary');
header('Accept-Ranges: bytes');
@readfile($file);

然后将其结果传递给如下所示的 AJAX 函数,该函数会生成一个新选项卡并将响应抛出到它上面:

$.ajax({
    url: '../includes/function.projects.php?view-media=' + item,
        success: function(data) {
            $(window.open().document.body).html(data);
        }
    })

这一切都很顺利,只有当新标签打开时,因为我正在将响应直接写入文档 HTML,所以我得到一个充满这样文本的屏幕:

%PDF-1.5 %���� 2 0 obj << /Linearized 1 /L 17007 /H [ 687 126 ] /O 6 /E 16732 /N 1 /T 16731 >>

所以我的问题很简单;有没有人尝试过这样做?如果是这样,是否有任何我应该使用的库/我缺少的标头等

我已经在这里看到了这个问题,但我无法得到人们列出的答案,所以我没有想法。

任何帮助将不胜感激,提前致谢!

【问题讨论】:

  • 这只是一个猜测,尽管我已经做了类似的事情来保护图像。我不认为你可以简单地通过window.open.document.body 传递这样的数据,因为你没有发送任何标题。为什么不直接以您的function.projects.php?view-media=' + item 作为 url 打开一个窗口并在其顶部进行安全检查?
  • 嗯...虽然看看这个:stackoverflow.com/questions/10516463/…
  • 这是个好主意!我已经编写了一个函数来检查会话,这样会很好并且易于实现。我刚刚开始研究的另一种方法是加载一个预先构建的页面,该页面通过 GET 变量传递 PDF 的 url,然后 JS 库接管它并将 PDF 加载到页面上......我喜欢不过你的想法更好:)
  • 祝你好运!不过请查看其他链接 - 也许您需要的只是将其转换为二进制并在您的字符串前面加上 data:application/pdf;base64,,您当前的计划就可以了。
  • 是的,伙计,我会继续修补,然后一旦我有一些可以顺利运行的东西,我就会将其添加为答案

标签: php jquery ajax .htaccess pdf


【解决方案1】:

好的,所以我有一个解决方案。如果有人能想出一个更好的方法,请告诉我,但现在这很好用!我找到了一个名为 PDFObject 的 JS 库,它可用于制作跨浏览器解决方案,以便轻松地将 PDF 嵌入到 html 文档中。有了这个,我可以在服务器上传递一个 PDF 链接以及一个目标 div 以将其嵌入(在我的情况下,我已经在模式内部进行了设置,因此我们保持在同一页面上)。

因为我们停留在同一个页面上,所以我可以使用我之前在项目中编写的函数阻止对整个页面的访问,如果用户没有正确的访问级别,它将重定向到索引。类似这样的东西会起作用:

function checkSession() {
    if(empty($_SESSION)) {
        header("Location: /?cheeky_monkey");
    }
}

如果用户尝试直接访问 PDF,则 htaccess 中的此代码会阻止他们。仅当通过应用程序作为目标时才允许访问:

SetEnvIf Referer "localhost" is_local_referer
<FilesMatch "\.pdf$">
    Require env is_local_referer
</FilesMatch>

除此之外,所有需要发生的事情就是在脚本标记处抛出一个 URL,以便在单击 PDF 时加载,通过以下代码序列完成:

  1. 首先我们需要获取 PDF 的 URL(您可以跳过此步骤)

首先,每当有人点击查看 PDF 时都会调用此 javascript(此调用只是嵌套为 onclick 属性):

function viewMedia(projectID, type, item) {
    $.ajax({
        url: '../includes/function.projects.php?cid=' + projectID + '&type=' + type + '&view-media=' + item,
        success: function(data) {
            $('.pdf-script').html('<script>PDFObject.embed("' + data + '", "#the-pdf");</script>');
            $('#viewMediaModal').modal('toggle');
        }
    })
}

这是在 php 页面上运行的代码。

public function viewMedia($item) {
    $mediaItems = unserialize($this->media);
    $file = '/path/to/pdf/' . $mediaItems[$item]['file'];
    echo $file;
}

此函数返回数据的示例:

/path/to/pdf/example-pdf.pdf
  1. 使用它来加载 PDF

一旦我们获得了正确的 PDF URL 并且 AJAX 返回成功,接收到的数据可用于重新生成 javascript,这次使用新的 PDF 链接:

success: function(data) {
    $('.pdf-script').html('<script>PDFObject.embed("' + data + '", "#the-pdf");</script>');
    $('#viewMediaModal').modal('toggle');
}

这就是模态体的结构:

<div class="modal-body">
    <div id="the-pdf"></div>
    <div class="pdf-script" style="display: none;">
        <script>PDFObject.embed('', '#the-pdf');</script>
    </div>
</div>
  1. 结果

上述代码序列的结果切换了如下所示的模式:



如果用户尝试直接访问该文件:

【讨论】:

  • 哇——真的很棒。感谢分享。
  • 别担心! :))
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2013-08-01
  • 1970-01-01
  • 2021-07-10
  • 2017-04-11
  • 2021-09-27
  • 1970-01-01
相关资源
最近更新 更多