2016-01-04 8 views
11

Quando si genera un PDF nel browser a livello di programmazione (tramite PHP) il PDF sottoposto a rendering viene visualizzato correttamente sia in Firefox che in Safari, ma Chrome restituisce ERR_INVALID_RESPONSE. È un PDF valido: può essere aperto localmente con Adobe Reader/Preview una volta salvato dai browser funzionanti e verrà aperto anche in Chrome una volta salvato il PDF da un altro browser.Risultati di generazione PDF in ERR_INVALID_RESPONSE in Chrome

Il file PDF viene letto tramite file_get_contents(), viene assegnato un timestamp corrente e quindi passato al browser. Una soluzione alternativa consisterebbe nel salvare il file in un punto temporaneo e reindirizzare l'utente (almeno per Chrome), ma questo non è l'ideale.

Ho studiato e sono riuscito a trovare solo bug reports dating from 2008.

Ho un sentore è un errore di intestazione. Dopo la generazione del PDF, le seguenti intestazioni vengono inviati al browser (ancora lavorando bene in FF, Safari e IE):

header('Content-type:application/pdf'); 
    header("HTTP/1.1 200 OK"); 

Ho anche provato ad aggiungere le seguenti intestazioni dopo la ricerca su Stack Overflow, ma per inutile:

header("Content-Transfer-Encoding: binary"); 
    header('Accept-Ranges: bytes'); 

Sono mancate intestazioni che richiede Chrome? Qualcuno ha esperienza con la visualizzazione di PDF generati dinamicamente in Chrome?

EDIT: una delle mie domande più importanti è che cosa potrebbe causare il corretto funzionamento di questo in locale in Chrome, ma non funzionerebbe su un ambiente server.

Grazie in anticipo per qualsiasi aiuto.

+0

Avete provato a cambiare la disposizione all'attaccamento? intestazione ('Content-Disposition: attachment ;; filename = "YourFileName"'); – HNA

+0

@HNA Ho - lo stesso errore si verifica in Chrome sia che si utilizzi o meno l'allegato. Ci sono due pulsanti: "salva" che getta nell'intestazione '(Content-Disposition: attachment; ');' in modo che il file venga scaricato automaticamente (funziona localmente in Chrome, FF e Safari e funziona senza localmente per Safari e Firefox). L'altro pulsante, "visualizza", visualizza semplicemente il PDF senza scaricarlo automaticamente. Attualmente non funzionano in Chrome in un'istanza non locale. –

+0

Inviate un'intestazione '(Content-Length: '. Filesize ($ yourfile));'? – maxhb

risposta

5

Voglio ringraziare tutti per le loro risposte.

Si scopre che questo non era correlato alle intestazioni. Dopo aver tentato di cambiare/rimuovere le intestazioni in vari modi (rilevando la codifica, provando con e senza la lunghezza del contenuto, ecc.) Abbiamo deciso di scavare nei più profondi log httpd per vedere se qualcosa si stava risolvendo in modo diverso per Chrome.

Si scopre che mod_sec sul nostro server stava segnalando la richiesta (solo da Chrome per qualche motivo) come un tentativo di un attacco di file injection e restituiva una risposta proibita 403. Chrome lo ha visualizzato come ERR_INVALID_RESPONSE anziché un 403.

Il nome host del CDN era presente nella richiesta (abbiamo verificato molto sull'endpoint per garantire che il file fosse effettivamente una risorsa consentita), e invece stiamo costruendo il URL fuori sul server.

+0

come lo hai risolto? Sono bloccato con lo stesso problema. – Cyberdelphos

+0

Ho bisogno di conoscere la soluzione a questo problema, sto avendo lo stesso problema. È in grado di visualizzare le immagini ma non visualizzerà PDF citando ERR_INVALID_RESPNSE che in realtà è l'errore 403. – netrox

+0

@netrox La soluzione è contenuta nella risposta. La nostra è stata lanciata a causa dell'URL del nostro CDN (AmazonS3) presente nella query. L'abbiamo rimosso dall'URL, quindi l'abbiamo aggiunto nuovamente all'endpoint. –

5

Prova questa

<?php 
$filename = 'Physical Path to PDf file.pdf'; 
$content = file_get_contents($filename); 

header("Content-type:application/pdf"); 

// It will be called downloaded.pdf 
header("Content-Disposition:inline;filename='".basename($filename)."'"); 
header('Content-Length: '.strlen($content)); 

// The PDF source is in original.pdf 
readfile($filename); 
?> 

<html> 
<body> 
... 
... 
... 

Assicurarsi che il codice di intestazione di cui sopra è chiamato prima uscita di script PHP è inviato al browser.

+0

Grazie per il suggerimento. Ho provato e riprovato quelle intestazioni senza fortuna. Ho pubblicato l'elenco completo delle intestazioni allegate in un commento sulla domanda originale. Nota anche che in realtà non stiamo "leggendo" il file sul browser, ma stiamo leggendo il PDF, modificandolo e quindi fornendo quel file appena creato come un allegato di download immediato o nel visualizzatore PDF del browser (non viene salvato su disco in qualsiasi momento durante questo processo). –

6

Nel mio caso ho dovuto aggiungere questi 2 parametri alle intestazioni perché wordpress è stato l'invio 404 del codice in quanto non ha riconosciuto l'url della mia funzione php:

header("Content-type: application/pdf",true,200); 

come indicato in questo answer on wordpress.stackexchange.

Questo costringe le intestazioni a sostituire (2 ° parametro true) il codice di stato 404 generato da wordpress poiché non riconosce l'URL personalizzato e imposta 200 OK (3 ° parametro 200).

così è finita essere qualcosa di simile:

$pdf_name = "test.pdf"; 
$pdf_file = "/absolute/path/to/my/pdfs/on/my/server/{$pdf_name}"; 
header('Content-type: application/pdf',true,200); 
header("Content-Disposition: attachment; filename={$pdf_name}"); 
header('Cache-Control: public'); 
readfile($pdf_file); 
exit(); 
Problemi correlati