Mostrar arquivos PDF no navegador dos usuários via PHP / Perl

121

Quero mostrar aos meus usuários arquivos PDF. A razão pela qual eu uso o cgi para mostrar o pdf é que desejo rastrear os cliques do pdf e esconder a localização real do pdf salvo.

Eu estive pesquisando na Internet e só encontrei como mostrar a caixa de diálogo Salvar para os usuários e criar um pdf, não mostrar os arquivos para os usuários.

O que eu queria era mostrar aos usuários meus arquivos PDF, não criando ou baixando o PDF. Aqui está o que eu consegui na documentação oficial do php:

<?php
header('Content-type: application/pdf');
readfile('the.pdf');
?>

Também meu código perl do resultado da pesquisa no google:

open(PDF, "the.pdf") or die "could not open PDF [$!]";
binmode PDF;
my $output = do { local $/; <PDF> };
close (PDF);

print "Content-Type: application/pdf\n";
print "Content-Length: " .length($output) . "\n\n";
print $output

se você fizer isso em rubi, por favor, diga-me. Mas não tenho certeza se meu servidor suporta trilhos.

Desculpe se meu código está muito longe do método para mostrar o pdf, pois não sei nada sobre processamento de pdf e como implementar esse problema.

Vamos supor que os usuários tenham o plug-in do Adobe Reader. Então, como resolver meu problema?

editar : eu quero mostrar arquivo pdf simples. Meu objetivo principal: rastrear meus arquivos PDF e usar alguns URLs sofisticados.

edit : Aqui está o meu código php principal:

<?php
$file='/files/the.pdf';
header('Content-type: application/pdf');
header('Content-Disposition: inline; filename="the.pdf"');
@readfile($file);
?>

edit : Agora o código está funcionando. Mas a barra de progresso do carregamento (no plugin Adobe Reader X) não aparece. Por quê? Alguém pode me ajudar? Aqui está o meu código principal:

<?php
$file='./files/the.pdf';
header('Content-type: application/pdf');
header('Content-Disposition: inline; filename="the.pdf"');
header('Content-Transfer-Encoding: binary');
header('Content-Length: ' . filesize($file));
@readfile($file);
?>

edit : Todos os meus problemas resolvidos. Aqui está o código final:

<?php
$file = './path/to/the.pdf';
$filename = 'Custom file name for the.pdf'; /* Note: Always use .pdf at the end. */

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

@readfile($file);
?>

Obrigado! :)

dimassony
fonte
4
"show" é possível apenas se o cliente tiver o plug-in Acrobat Reader instalado. Caso contrário, ele sempre será servido como um arquivo de download, não há nada que você possa fazer sobre isso. Obscurecer o caminho do PDF também é impossível, é trivial descobrir. O que está tentando fazer? Talvez existam algumas alternativas, se sabemos mais sobre seus objetivos
Pekka
4
o plug-in do Adobe Reader será necessário apenas se você estiver usando um navegador que não lida com PDFs nativamente. Além disso, se o PDF for enviado para o navegador via PHP / Perl, é muito possível ocultar o caminho real do PDF, ou mesmo tê-lo fora da docroot, para que não fique diretamente acessível.
Stephen
1
Adobe Reader é necessário apenas se o usuário está usando um navegador que não lidar com PDFs de forma nativa ...
GolezTrol
@ Stephen, é claro que é possível obscurecer o caminho real, mas o que o OP parece querer é obscurecer a URL para impedir o roubo.
Pekka
Vamos supor que os usuários tenham o plug-in Adobe Reader. Então, como resolver meu problema?
dimassony

Respostas:

49

Suponho que você queira que o PDF seja exibido no navegador, em vez de forçar um download. Se for esse o caso, tente definir o Content-Dispositioncabeçalho com um valor de inline.

Lembre-se também de que isso também será afetado pelas configurações do navegador - alguns navegadores podem estar configurados para sempre baixar arquivos PDF ou abri-los em um aplicativo diferente (por exemplo, Adobe Reader)

Stephen
fonte
Sim. Mas quando estou tentando sua sugestão, recebo um erro dizendo "O arquivo não começa com '% PDF-'". Eu uso 'Content-Disposition: inline; filename = "the.pdf" '. Eu cometi um erro?
dimassony 13/01
4
<? php header ('Tipo de conteúdo: aplicativo / pdf'); header ('Disposição de conteúdo: inline; filename = "the.pdf"'); readfile ('/ dir / para / the.pdf'); ?>
dimassony
parece que não é um arquivo PDF válido?
Stephen
@ Stephen Quando abro o arquivo, ele funciona. Mas quando eu uso a disposição de conteúdo em linha, ela não funciona.
precisa saber é o seguinte
7
bom ouvir e ótimo saber a solução! Seria bom se você pudesse postar o código final mostrando quais cabeçalhos você está enviando para qualquer pessoa que se deparar com essa pergunta.
Stephen
18
    $url ="https://yourFile.pdf";
    $content = file_get_contents($url);

    header('Content-Type: application/pdf');
    header('Content-Length: ' . strlen($content));
    header('Content-Disposition: inline; filename="YourFileName.pdf"');
    header('Cache-Control: private, max-age=0, must-revalidate');
    header('Pragma: public');
    ini_set('zlib.output_compression','0');

    die($content);

Testado e funciona bem. Se você deseja fazer o download do arquivo, substitua

    Content-Disposition: inline

com

    Content-Disposition: attachment
Kareem
fonte
Por que você está desativando a compactação? ini_set ('zlib.output_compression', '0');
Enigma Plus
Como a compactação zlib não funciona com ob_gzhandler () e esse é um trecho de código em vez de um script completo. O Ngnix lida com a compressão melhor que o php. Você pode usar o zlib se for adequado ao seu aplicativo e configuração do servidor.
Kareem
4

Você pode modificar um renderizador de PDF, como xpdf ou evince, para renderizar em uma imagem gráfica no servidor e, em seguida, entregar a imagem ao usuário. É assim que a visualização rápida do Google dos arquivos PDF funciona, eles o renderizam localmente e depois entregam imagens ao usuário. Nenhum arquivo PDF baixado e a fonte está muito bem obscurecida. :)

sarnold
fonte
Essa é a única maneira realmente segura de impedir o roubo do documento original.
Pekka
1
Não me importo com o roubo de documentos originais. Caso contrário, eu queria que os usuários pudessem salvá-lo. Além disso, eu queria bloquear alguns cabeçalhos de clientes. E talvez eu implemente sua sugestão quando o usuário não tiver o Adobe Reader.
dimassony
Além disso, não seria roubo, porque o original ainda está lá.
Svante
@Svante - duvido que os proprietários de propriedade intelectual concordem com sua lógica.
ashleedawg
@ashleedawg: Duvido do apelido de "propriedade intelectual". Isso é apenas um hackeamento de palavras para fazer com que o armazenamento de informações pareça não apenas um modelo de negócios legítimo, mas também que valha a pena o público se defender contra a inovação.
Svante
1

A maneira mais segura de exibir um PDF em vez de fazer o download parece incorporá-lo usando um elemento objectou iframe. Também existem soluções de terceiros, como o visualizador de PDF do Google.

Consulte Melhor maneira de incorporar PDF em HTML para obter uma visão geral.

Há também o DoPDF , um visualizador de PDF no navegador baseado em Java. Não posso falar da sua qualidade, mas parece interessante.

Pekka
fonte
0

Você também pode usar a classe fpdf disponível em: http://www.fpdf.org . Oferece opções para saída em um arquivo e exibição no navegador.

tapananand
fonte