Mengakses HTTP Header halaman web dalam JavaScript

Jawaban:

365

Membaca header saat ini tidak mungkin dilakukan. Anda dapat membuat permintaan lain ke URL yang sama dan membaca tajuknya, tetapi tidak ada jaminan bahwa tajuknya persis sama dengan yang sekarang.


Gunakan kode JavaScript berikut untuk mendapatkan semua tajuk HTTP dengan melakukan getpermintaan:

var req = new XMLHttpRequest();
req.open('GET', document.location, false);
req.send(null);
var headers = req.getAllResponseHeaders().toLowerCase();
alert(headers);
Raja
sumber
58
Saeed, mungkin bukan yang terbaik untuk pertanyaan penulis .. Saya kira itu karena tidak mengakses header sumber daya yang dimuat, tetapi membuat permintaan baru .. jelas dia tahu yang terbaik, apa jawaban terbaiknya, dan membuatnya sendiri
mykhal
18
Bergantung pada header apa Anda setelah Anda mungkin ingin menggunakan kata kerja 'KEPALA'.
scottrudy
17
Membuat permintaan baru hanya akan berfungsi jika nilai respons yang Anda butuhkan dijamin sama dari satu permintaan ke yang berikutnya. Ini akan tergantung pada aplikasi Anda, jadi jarak tempuh Anda dengan pendekatan seperti ini akan bervariasi.
keparo
6
Retasan ini mungkin berfungsi dalam beberapa skenario, tetapi tidak akan berfungsi sama sekali jika halaman yang berisi skrip dihasilkan sebagai respons terhadap permintaan POST, dan itu tidak membantu jika Anda mencoba menentukan apakah server mengalami kesalahan (HTTP 5XX) saat memproses permintaan asli.
claymation
9
Jawaban ini sangat salah. Jawaban yang benar adalah "itu tidak mungkin". Atau untuk mencocokkan jawaban ini "Tidak mungkin, tetapi ini adalah retas untuk mencoba mensimulasikannya yang mungkin atau mungkin tidak bekerja sama sekali untuk Anda".
Jan
301

Sayangnya, tidak ada API untuk memberi Anda header respons HTTP untuk permintaan halaman awal Anda. Itu adalah pertanyaan asli yang diposting di sini. Sudah berulang kali ditanyakan juga, karena beberapa orang ingin mendapatkan tajuk respons aktual dari permintaan halaman asli tanpa mengeluarkan yang lain.


Untuk Permintaan AJAX:

Jika permintaan HTTP dibuat melalui AJAX, dimungkinkan untuk mendapatkan header respons dengan getAllResponseHeaders()metode ini. Itu bagian dari API XMLHttpRequest. Untuk melihat bagaimana ini dapat diterapkan, periksa fetchSimilarHeaders()fungsi di bawah ini. Perhatikan bahwa ini adalah solusi untuk masalah yang tidak dapat diandalkan untuk beberapa aplikasi.

myXMLHttpRequest.getAllResponseHeaders();

Ini tidak akan memberi Anda informasi tentang tajuk respons HTTP permintaan laman asli, tetapi bisa digunakan untuk membuat tebakan yang mendidik tentang tajuk itu. Lebih lanjut tentang itu dijelaskan selanjutnya.


Mendapatkan nilai tajuk dari Permintaan Halaman Awal:

Pertanyaan ini pertama kali ditanyakan beberapa tahun yang lalu, menanyakan secara khusus tentang bagaimana mendapatkan header respons HTTP asli untuk halaman saat ini (yaitu halaman yang sama di mana javascript berjalan). Ini adalah pertanyaan yang sangat berbeda dari sekadar mendapatkan header respons untuk setiap permintaan HTTP. Untuk permintaan halaman awal, header tidak tersedia untuk javascript. Apakah nilai header yang Anda butuhkan akan konsisten dan cukup konsisten jika Anda meminta halaman yang sama lagi melalui AJAX akan tergantung pada aplikasi khusus Anda.

Berikut ini adalah beberapa saran untuk mengatasi masalah itu.


1. Permintaan Sumber Daya yang sebagian besar statis

Jika responsnya sebagian besar statis dan tajuknya tidak diharapkan banyak berubah di antara permintaan, Anda dapat membuat permintaan AJAX untuk halaman yang sama dengan yang Anda gunakan saat ini dan menganggap bahwa mereka adalah nilai yang sama dengan yang merupakan bagian dari halaman Tanggapan HTTP. Ini bisa memungkinkan Anda untuk mengakses tajuk yang Anda butuhkan menggunakan API XMLHttpRequest yang bagus seperti dijelaskan di atas.

function fetchSimilarHeaders (callback) {
    var request = new XMLHttpRequest();
    request.onreadystatechange = function () {
        if (request.readyState === XMLHttpRequest.DONE) {
            //
            // The following headers may often be similar
            // to those of the original page request...
            //
            if (callback && typeof callback === 'function') {
                callback(request.getAllResponseHeaders());
            }
        }
    };

    //
    // Re-request the same page (document.location)
    // We hope to get the same or similar response headers to those which 
    // came with the current page, but we have no guarantee.
    // Since we are only after the headers, a HEAD request may be sufficient.
    //
    request.open('HEAD', document.location, true);
    request.send(null);
}

Pendekatan ini akan bermasalah jika Anda benar-benar harus bergantung pada nilai-nilai yang konsisten di antara permintaan, karena Anda tidak dapat sepenuhnya menjamin bahwa mereka sama. Ini akan tergantung pada aplikasi spesifik Anda dan apakah Anda tahu bahwa nilai yang Anda butuhkan adalah sesuatu yang tidak akan berubah dari satu permintaan ke yang berikutnya.


2. Buat kesimpulan

Ada beberapa properti BOM (Model Objek Browser) yang ditentukan browser dengan melihat header. Beberapa properti ini mencerminkan header HTTP secara langsung (mis. navigator.userAgentDiatur ke nilai User-Agentbidang header HTTP ). Dengan mengendus-endus properti yang tersedia Anda mungkin dapat menemukan apa yang Anda butuhkan, atau beberapa petunjuk untuk menunjukkan apa yang terkandung dalam respons HTTP.


3. Simpan mereka

Jika Anda mengontrol sisi server, Anda dapat mengakses header apa pun yang Anda suka saat membangun respons penuh. Nilai dapat diteruskan ke klien dengan halaman, disimpan dalam beberapa markup atau mungkin dalam struktur JSON yang digarisbawahi. Jika Anda ingin agar setiap tajuk permintaan HTTP tersedia untuk javascript Anda, Anda dapat mengulanginya melalui server dan mengirimkannya kembali sebagai nilai tersembunyi di markup. Mungkin tidak ideal untuk mengirim nilai header seperti ini, tetapi Anda tentu bisa melakukannya untuk nilai spesifik yang Anda butuhkan. Solusi ini bisa dibilang tidak efisien juga, tetapi akan berhasil jika Anda membutuhkannya.

keparo
sumber
2
Bagaimana Google mendeteksinya seperti yang saya jelaskan di sini: stackoverflow.com/questions/7191242/...
kamaci
Pembaruan RE: permintaan ajax adalah bagian standar dari cara pengembangan web kembali pada tahun 2008 juga -_-
BlueRaja - Danny Pflughoeft
5
BOM adalah singkatan dari "Browser Object Model", untuk mereka yang bertanya-tanya. Lihat stackoverflow.com/questions/2213594/… untuk beberapa latar belakang.
Myrne Stol
1
3) Anda juga bisa menyimpannya di header cookie http. Maka Anda tidak perlu mengubah markup dokumen.
skibulk
Ada cara sederhana untuk mengakses elemen tajuk respons seperti elemen tautan: gunakan contoh dokumen di sini: gist.github.com/FunThomas424242/...
FunThomas424242
28

Menggunakan XmlHttpRequestAnda dapat menarik halaman saat ini dan kemudian memeriksa header http dari respons.

Kasus terbaik adalah dengan hanya melakukan HEADpermintaan dan kemudian memeriksa header.

Untuk beberapa contoh melakukan hal ini, lihat di http://www.jibbering.com/2002/4/httprequest.html

Hanya 2 sen saya.

Allain Lalonde
sumber
24

Solusi dengan Pekerja Layanan

Pekerja layanan dapat mengakses informasi jaringan, yang mencakup tajuk. Bagian baiknya adalah ia bekerja berdasarkan permintaan apa pun, bukan hanya XMLHttpRequest.

Bagaimana itu bekerja:

  1. Tambahkan pekerja layanan di situs web Anda.
  2. Tonton setiap permintaan yang dikirim.
  3. Buat pekerja layanan fetchpermintaan dengan respondWithfungsi.
  4. Ketika respons datang, baca header.
  5. Kirim header dari pekerja layanan ke halaman dengan postMessagefungsi.

Contoh kerja:

Pekerja layanan agak rumit untuk dipahami, jadi saya telah membangun perpustakaan kecil yang melakukan semua ini. Ini tersedia di github: https://github.com/gmetais/sw-get-headers .

Keterbatasan:

  • situs web perlu dihidupkan HTTPS
  • browser perlu mendukung API Pekerja Layanan
  • kebijakan-domain / lintas-domain yang sama berlaku, seperti pada XMLHttpRequest
Gaël Métais
sumber
12

Bagi mereka yang mencari cara untuk mem-parsing semua header HTTP ke objek yang dapat diakses sebagai kamus headers["content-type"], saya telah membuat sebuah fungsi parseHttpHeaders:

function parseHttpHeaders(httpHeaders) {
    return httpHeaders.split("\n")
     .map(x=>x.split(/: */,2))
     .filter(x=>x[0])
     .reduce((ac, x)=>{ac[x[0]] = x[1];return ac;}, {});
}

var req = new XMLHttpRequest();
req.open('GET', document.location, false);
req.send(null);
var headers = parseHttpHeaders(req.getAllResponseHeaders());
// Now we can do:  headers["content-type"]
Diego
sumber
10

Cara lain untuk mengirim informasi header ke JavaScript adalah melalui cookie. Server dapat mengekstraksi data apa pun yang dibutuhkan dari header permintaan dan mengirimkannya kembali ke dalam Set-Cookieheader respons - dan cookie dapat dibaca dalam JavaScript. Seperti yang dikatakan keparo, yang terbaik adalah melakukan ini hanya satu atau dua header, daripada untuk mereka semua.

savetheclocktower
sumber
1
Pendekatan ini masih mengharuskan Anda mengontrol server untuk JS Anda. Tidak peduli bagaimana Anda mengomunikasikan info itu, kode Anda tiba-tiba dibuat tidak dapat disimpan. Mengapa tidak membuat API untuk permintaan khusus itu agar tidak merusak permintaan aset asli?
MST
5

Jika kita berbicara tentang header Permintaan , Anda dapat membuat header Anda sendiri saat melakukan XmlHttpRequests.

var request = new XMLHttpRequest();
request.setRequestHeader("X-Requested-With", "XMLHttpRequest");
request.open("GET", path, true);
request.send(null);
Leo
sumber
Anda tidak akan dapat memodifikasi header permintaan di mozilla untuk alasan keamanan. mxr.mozilla.org/mozilla1.8.0/source/extensions/xmlextras/base/…
user121196
1
Anda harus memanggil open () sebelum menggunakan metode setRequestHeader (). developer.mozilla.org/en/…
XP1
1
Akses, dalam pertanyaan awal, adalah tentang mendapatkan tajuk, bukan mengatur tajuk.
Timo Tijhof
4

Anda tidak dapat mengakses header http, tetapi beberapa informasi yang disediakan di dalamnya tersedia di DOM. Misalnya, jika Anda ingin melihat pengarah http (sic), gunakan document.referrer. Mungkin ada orang lain seperti ini untuk header http lainnya. Coba googling hal tertentu yang Anda inginkan, seperti "http referer javascript".

Saya tahu ini harus jelas, tetapi saya terus mencari hal-hal seperti "http header javascript" ketika semua yang saya inginkan adalah referer, dan tidak mendapatkan hasil yang bermanfaat. Saya tidak tahu bagaimana saya tidak menyadari bahwa saya bisa membuat permintaan yang lebih spesifik.

David Winiecki
sumber
4

Seperti banyak orang, saya telah menggali jaring tanpa jawaban nyata :(

Meskipun demikian, saya telah menemukan jalan pintas yang dapat membantu orang lain. Dalam kasus saya, saya sepenuhnya mengontrol server web saya. Sebenarnya itu adalah bagian dari aplikasi saya (lihat referensi akhir). Mudah bagi saya untuk menambahkan skrip ke respons http saya. Saya memodifikasi server httpd saya untuk menyuntikkan skrip kecil di dalam setiap halaman html. Saya hanya mendorong baris 'skrip js' tambahan tepat setelah konstruksi tajuk saya, yang menetapkan variabel yang ada dari dokumen saya di browser saya [saya memilih lokasi], tetapi opsi lain dimungkinkan. Sementara server saya ditulis dalam nodejs, saya tidak ragu bahwa teknik yang sama dapat digunakan dari PHP atau lainnya.

  case ".html":
    response.setHeader("Content-Type", "text/html");
    response.write ("<script>location['GPSD_HTTP_AJAX']=true</script>")
    // process the real contend of my page

Sekarang setiap halaman html diambil dari server saya, buat skrip ini dijalankan oleh browser pada penerimaan. Saya kemudian dapat dengan mudah memeriksa dari JavaScript apakah ada variabel atau tidak. Dalam usecase saya, saya perlu tahu apakah saya harus menggunakan JSON atau profil JSON-P untuk menghindari masalah CORS, tetapi teknik yang sama dapat digunakan untuk tujuan lain [yaitu: memilih di antara server pengembangan / produksi, dapatkan dari server REST / API kunci, dll ....]

Pada browser Anda hanya perlu memeriksa variabel langsung dari JavaScript seperti pada contoh saya, di mana saya menggunakannya untuk memilih profil Json / JQuery saya

 // Select direct Ajax/Json profile if using GpsdTracking/HttpAjax server otherwise use JsonP
  var corsbypass = true;  
  if (location['GPSD_HTTP_AJAX']) corsbypass = false;

  if (corsbypass) { // Json & html served from two different web servers
    var gpsdApi = "http://localhost:4080/geojson.rest?jsoncallback=?";
  } else { // Json & html served from same web server [no ?jsoncallback=]
    var gpsdApi = "geojson.rest?";
  }
  var gpsdRqt = 
      {key   :123456789 // user authentication key
      ,cmd   :'list'    // rest command
      ,group :'all'     // group to retreive
      ,round : true     // ask server to round numbers
   };
   $.getJSON(gpsdApi,gpsdRqt, DevListCB);

Bagi yang ingin memeriksa kode saya: https://www.npmjs.org/package/gpsdtracking

Fulup
sumber
3

Menggunakan mootools, Anda dapat menggunakan this.xhr.getAllResponseHeaders ()


sumber
3

Saya baru saja menguji, dan ini berfungsi untuk saya menggunakan Chrome Versi 28.0.1500.95.

Saya perlu mengunduh file dan membaca nama file. Nama file di header jadi saya melakukan hal berikut:

var xhr = new XMLHttpRequest(); 
xhr.open('POST', url, true); 
xhr.responseType = "blob";
xhr.onreadystatechange = function () { 
    if (xhr.readyState == 4) {
        success(xhr.response); // the function to proccess the response

        console.log("++++++ reading headers ++++++++");
        var headers = xhr.getAllResponseHeaders();
        console.log(headers);
        console.log("++++++ reading headers end ++++++++");

    }
};

Keluaran:

Date: Fri, 16 Aug 2013 16:21:33 GMT
Content-Disposition: attachment;filename=testFileName.doc
Content-Length: 20
Server: Apache-Coyote/1.1
Content-Type: application/octet-stream
buru-buru
sumber
2

Ini skrip saya untuk mendapatkan semua header respons:

var url = "< URL >";

var req = new XMLHttpRequest();
req.open('HEAD', url, false);
req.send(null);
var headers = req.getAllResponseHeaders();

//Show alert with response headers.
alert(headers);

Hasilnya sebagai tajuk respons.

masukkan deskripsi gambar di sini

Ini adalah tes perbandingan menggunakan Hurl.it:

masukkan deskripsi gambar di sini

Jorgesys
sumber
2

Untuk mendapatkan header sebagai objek yang handier (peningkatan jawaban Raja ):

var req = new XMLHttpRequest();
req.open('GET', document.location, false);
req.send(null);
var headers = req.getAllResponseHeaders().toLowerCase();
headers = headers.split(/\n|\r|\r\n/g).reduce(function(a, b) {
    if (b.length) {
        var [ key, value ] = b.split(': ');
        a[key] = value;
    }
    return a;
}, {});
console.log(headers);
shaedrich
sumber
2

Tautan Allain Lalonde membuat hari saya menyenangkan. Cukup tambahkan beberapa kode html yang berfungsi di sini.
Berfungsi dengan peramban yang masuk akal sejak usia plus IE9 + dan Presto-Opera 12.

<!DOCTYPE html>
<title>(XHR) Show all response headers</title>

<h1>All Response Headers with XHR</h1>
<script>
 var X= new XMLHttpRequest();
 X.open("HEAD", location);
 X.send();
 X.onload= function() { 
   document.body.appendChild(document.createElement("pre")).textContent= X.getAllResponseHeaders();
 }
</script>

Catatan: Anda mendapatkan tajuk permintaan kedua, hasilnya mungkin berbeda dari permintaan awal.


Cara lain
adalah fetch()API yang lebih modern
https://developer.mozilla.org/en-US/docs/Web/API/WindowOrWorkerGlobalScope/fetch
Per caniuse.com didukung oleh Firefox 40, Chrome 42, Edge 14, Safari 11
Contoh kerja kode:

<!DOCTYPE html>
<title>fetch() all Response Headers</title>

<h1>All Response Headers with fetch()</h1>
<script>
 var x= "";
 if(window.fetch)
    fetch(location, {method:'HEAD'})
    .then(function(r) {
       r.headers.forEach(
          function(Value, Header) { x= x + Header + "\n" + Value + "\n\n"; }
       );
    })
    .then(function() {
       document.body.appendChild(document.createElement("pre")).textContent= x;
    });
 else
   document.write("This does not work in your browser - no support for fetch API");
</script>
jj
sumber
0

Ini pertanyaan lama. Tidak yakin kapan dukungan menjadi lebih luas, tetapi getAllResponseHeaders()dan getResponseHeader()tampaknya sekarang cukup standar: http://www.w3schools.com/xml/dom_http.asp

dlo
sumber
50
getAllResponseHeaders () dan getResponseHeader () adalah metode dari objek XMLHttpRequest. Yaitu untuk permintaan ajax. Anda tidak dapat menggunakan metode-metode itu untuk melihat tajuk halaman awal - yang menurut saya merupakan pertanyaan awal.
asgeo1
-1

Seperti yang telah disebutkan, jika Anda mengontrol sisi server maka mungkin untuk mengirim header permintaan awal kembali ke klien dalam respons awal.

Di Express, misalnya, berikut ini berfungsi:

app.get('/somepage', (req, res) => { res.render('somepage.hbs', {headers: req.headers}); }) Header kemudian tersedia dalam template, jadi bisa disembunyikan secara visual tetapi dimasukkan dalam markup dan dibaca oleh javascript sisi klien.

Ollie Williams
sumber
Pertanyaannya adalah bertanya tentang header respons , bukan header permintaan.
Quentin
-1

Saya pikir pertanyaannya salah, Jika Anda ingin mengambil header Permintaan dari JQuery / JavaScript jawabannya tidak. Solusi lain adalah membuat halaman aspx atau halaman jsp maka kita dapat dengan mudah mengakses header permintaan. Ambil semua permintaan di halaman aspx dan masukkan ke sesi / cookie maka Anda dapat mengakses cookie di halaman JavaScript ..

santhos jery
sumber
1
Pertanyaannya adalah bertanya tentang membaca header respons . Itu menyebutkan header permintaan hanya dalam konteks pertanyaan yang mungkin terkait.
Quentin