Voglio vedere se la scheda corrente è un file PDF da una pagina di sfondo.
Posso controllare l’url per .pdf alla fine ma ci sono alcuni file PDF che non hanno questo.
Non puoi ottenerlo utilizzando l’afAk dell’API di Chrome corrente. Quello che puoi fare è caricare di nuovo questa pagina tramite XHR e controllare l’intestazione del tipo di contenuto restituito. Qualcosa come questo:
background html:
chrome.tabs.onUpdated.addListener(function(tabId, changeInfo, tab) { if(changeInfo.status == "loading") { if(checkIfUrlHasPdfExtension(tab.url)) { //.pdf pdfDetected(tab); } else { var xhr = new XMLHttpRequest(); xhr.open("GET", tab.url, true); xhr.onreadystatechange = function() { if (xhr.readyState == 4) { var contentType = xhr.getResponseHeader("Content-Type"); if(checkIfContentTypeIsPdf(contentType)) { pdfDetected(tab); } } } xhr.send(); } } });
manifest.json:
"permissions": [ "tabs", "http://*/*", "https://*/*" ]
Per i file PDF il tipo di contenuto restituito deve essere application/pdf
. Qualcosa da tenere a mente però è che l’intestazione content-type potrebbe contenere anche la codifica: text/html; charset=UTF-8
text/html; charset=UTF-8
.
L’emissione di una nuova richiesta solo per ottenere il tipo MIME è un po ‘pesante e non affidabile. Ad esempio, se la pagina attualmente visualizzata è il risultato di un invio di moduli POST, l’invio di una richiesta GET
solito non porta alla stessa pagina.
Se stai sviluppando un’estensione che richiede spesso l’accesso a queste informazioni, utilizza l’API chrome.webRequest
per tenere traccia delle risposte. La seguente estensione demo mostra il tipo di contenuto al clic del pulsante del browser:
// background.js var tabToMimeType = {}; chrome.webRequest.onHeadersReceived.addListener(function(details) { if (details.tabId !== -1) { var header = getHeaderFromHeaders(details.responseHeaders, 'content-type'); // If the header is set, use its value. Otherwise, use undefined. tabToMimeType[details.tabId] = header && header.value.split(';', 1)[0]; } }, { urls: ['*://*/*'], types: ['main_frame'] }, ['responseHeaders']); chrome.browserAction.onClicked.addListener(function(tab) { alert('Tab with URL ' + tab.url + ' has MIME-type ' + tabToMimeType[tab.id]); }); function getHeaderFromHeaders(headers, headerName) { for (var i = 0; i < headers.length; ++i) { var header = headers[i]; if (header.name.toLowerCase() === headerName) { return header; } } }
Gli appunti:
text/plain
, Chrome torna a eseguire lo sniffing MIME a meno che non sia impostato X-Content-Type-Options: nosniff
. Nel primo caso, il tipo MIME rilevato potrebbe essere qualsiasi cosa. In quest'ultimo caso, il tipo MIME predefinito è text/plain
. Per completezza, ecco un file manifest.json
che può essere utilizzato per testare il codice precedente:
{ "name": "Click button to see MIME", "version": "1", "manifest_version": 2, "background": { "scripts": ["background.js"], "persistent": true }, "browser_action": { "default_title": "Show MIME" }, "permissions": [ "webRequest", "activeTab", "*://*/*" ] }
Un modo un po ‘hacker (non ho idea se funzioni sempre o solo qualche volta) è guardare il contenuto della pagina. Lì troverai un elemento per il visualizzatore PDF di Chrome. Guarda lungo queste linee:
Puoi controllare l’attributo “tipo” per vedere con cosa hai a che fare.
Ho dovuto fare qualcosa di simile in una delle mie estensioni e ho fatto qualcosa di molto simile alla risposta data da @serg ma usando invece una richiesta HEAD. In teoria, una richiesta HEAD dovrebbe essere identica a una richiesta GET ma senza inviare il corpo della risposta, che nel caso di un’immagine o di un file potrebbe essere un bel po ‘di dati extra e di tempo in attesa.
Ho anche diviso e spostato l’intestazione per eliminare tutti i set di caratteri che potrebbero essere aggiunti al tipo di contenuto.
getContentType: function(tab, callback){ var xhr = new XMLHttpRequest(); xhr.open("HEAD", tab.url, false); xhr.onload = function(e) { if (xhr.readyState === 4) { if(xhr.status === 200) { callback(xhr.getResponseHeader("Content-Type").split(";").shift()); } else{ callback('Unknown'); console.error(xhr.statusText); return; } } }; xhr.onerror = function (e) { console.error(xhr.statusText); return; }; xhr.send(); }
È ansible valutare la proprietà document.contentType
nella scheda corrente. Ecco un esempio su browserAction
:
chrome.browserAction.onClicked.addListener(() => { chrome.tabs.getSelected((tab) => { chrome.tabs.executeScript(tab.id, { code: 'document.contentType' }, ([ mimeType ]) => { alert(mimeType); }); }) });
Questa proprietà restituisce il tipo MIME in cui viene eseguito il rendering del documento, non l’intestazione Content-Type
(nessuna informazione sul set di caratteri).