74

Is there a built in way to get the headers of a specific address via node.js?

something like,

var headers = getUrlHeaders("http://stackoverflow.com");

would return

HTTP/1.1 200 OK.
Cache-Control: public, max-age=60.
Content-Type: text/html; charset=utf-8.
Content-Encoding: gzip.
Expires: Sat, 07 May 2011 17:32:38 GMT.
Last-Modified: Sat, 07 May 2011 17:31:38 GMT.
Vary: *.
Date: Sat, 07 May 2011 17:31:37 GMT.
Content-Length: 32516.
simhumileco
  • 31,877
  • 16
  • 137
  • 115
lostsource
  • 21,070
  • 8
  • 66
  • 88

6 Answers6

144

This sample code should work:

var http = require('http');
var options = {method: 'HEAD', host: 'stackoverflow.com', port: 80, path: '/'};
var req = http.request(options, function(res) {
    console.log(JSON.stringify(res.headers));
  }
);
req.end();
clee
  • 10,943
  • 6
  • 36
  • 28
  • 4
    You might note, that (depending on the server and the header fields you’re trying to get) you might actually need a "full" GET request, as some servers don’t include certain header fields, like `set-cookie`, in responses from HEAD requests. – max Feb 27 '15 at 17:12
23

Try to look at http.get and response headers.

var http = require("http");

var options = {
  host: 'stackoverflow.com',
  port: 80,
  path: '/'
};

http.get(options, function(res) {
  console.log("Got response: " + res.statusCode);

  for(var item in res.headers) {
    console.log(item + ": " + res.headers[item]);
  }
}).on('error', function(e) {
  console.log("Got error: " + e.message);
});
yojimbo87
  • 65,684
  • 25
  • 123
  • 131
  • 23
    This might work fine for small files, but it's better to use HTTP HEAD if you don't plan to do anything with the body of the data. – clee May 14 '11 at 11:14
21

Using the excellent request module:

var request = require('request');
  request("http://stackoverflow.com", {method: 'HEAD'}, function (err, res, body){
  console.log(res.headers);
});

You can change the method to GET if you wish, but using HEAD will save you from getting the entire response body if you only wish to look at the headers.

Nemo
  • 3,104
  • 2
  • 30
  • 46
  • 3
    This will get the entire body! Imagine you want the header to decide whether you want to get the url content or it's over the size limit. This 3 lines for a url to a 5 MB PDF will download the entire pdf body then it will show you the header! As the name refers, header must be at the beginning not at the end of operation. I forgot to mention you can easily add {method: 'HEAD'} after url as an option and just get the header. – Maziyar Aug 12 '15 at 12:48
  • 1
    What is excellent about a library that just provides a thin layer over something that was already easy to use? – Kyle Emmerich Dec 02 '15 at 02:25
  • 3
    Not for this particular case, but request is downloaded half a million times every day. It supports streaming, all forms of auth and has many more features. – Nemo Dec 02 '15 at 05:08
11

Here is my contribution, that deals with any URL using http or https, and use Promises.

const http = require('http')
const https = require('https')
const url = require('url')

function getHeaders(myURL) {
  const parsedURL = url.parse(myURL)
  const options = {
    protocol: parsedURL.protocol,
    hostname: parsedURL.hostname,
    method: 'HEAD',
    path: parsedURL.path
  }
  let protocolHandler = (parsedURL.protocol === 'https:' ? https : http)

  return new Promise((resolve, reject) => {
    let req = protocolHandler.request(options, (res) => {
      resolve(res.headers)
    })
    req.on('error', (e) => {
      reject(e)
    })
    req.end()
  })
}

getHeaders(myURL).then((headers) => {
  console.log(headers)
})
Mick F
  • 7,312
  • 6
  • 51
  • 98
7

I had some problems with http.get; so I switched to the lib request:

var request = require('request');

var url = 'http://blog.mynotiz.de/';

var options = {
    url: url,
    method: 'HEAD'
};

request(options, function (error, response, body) {
        if (error) {
            return console.error('upload failed:', error);
        }

        if (response.headers['content-length']) {
            var file_size = response.headers['content-length'];
            console.log(file_size);
        }
    }
);
Frank Roth
  • 6,191
  • 3
  • 25
  • 33
7

I'm not sure how you might do this with Node, but the general idea would be to send an HTTP HEAD request to the URL you're interested in.

HEAD

Asks for the response identical to the one that would correspond to a GET request, but without the response body. This is useful for retrieving meta-information written in response headers, without having to transport the entire content.


Something like this, based it on this question:

var cli = require('cli');
var http = require('http');
var url = require('url');

cli.parse();

cli.main(function(args, opts) {
        this.debug(args[0]);

        var siteUrl = url.parse(args[0]);
        var site = http.createClient(80, siteUrl.host);
        console.log(siteUrl);

        var request = site.request('HEAD', siteUrl.pathname, {'host' : siteUrl.host})
        request.end();

        request.on('response', function(response) {
                response.setEncoding('utf8');
                console.log('STATUS: ' + response.statusCode);
                response.on('data', function(chunk) {
                        console.log("DATA: " + chunk);
                });
        });
});
Community
  • 1
  • 1
Matt Ball
  • 354,903
  • 100
  • 647
  • 710