|
|
/*! * Connect - favicon * Copyright(c) 2010 Sencha Inc. * Copyright(c) 2011 TJ Holowaychuk * MIT Licensed */
/** * Module dependencies. */
var crypto = require('crypto') , fs = require('fs');
/** * Favicon cache. */
var icon;
/** * Return md5 hash of the given string and optional encoding, * defaulting to hex. * * utils.md5('wahoo'); * // => "e493298061761236c96b02ea6aa8a2ad"
* * @param {String} str * @param {String} encoding * @return {String} * @api public */
exports.md5 = function (str, encoding) { return crypto .createHash('md5') .update(str) .digest(encoding || 'hex'); };
/** * By default serves the connect favicon, or the favicon * located by the given `path`. * * Options: * * - `maxAge` cache-control max-age directive, defaulting to 1 day * * Examples: * * connect.createServer( * connect.favicon() * ); * * connect.createServer( * connect.favicon(__dirname + '/public/favicon.ico') * ); * * @param {String} path * @param {Object} options * @return {Function} * @api public */
module.exports = function favicon(path, options) { var options = options || {} , path = path || __dirname + '/../public/favicon.ico' , maxAge = options.maxAge || 86400000;
return function favicon(req, res, next) { if ('/favicon.ico' == req.url) { if (icon) { res.writeHead(200, icon.headers); res.end(icon.body); } else { fs.readFile(path, function (err, buf) { if (err) return next(err); icon = { headers: { 'Content-Type': 'image/x-icon' , 'Content-Length': buf.length , 'ETag': '"' + exports.md5(buf) + '"' , 'Cache-Control': 'public, max-age=' + (maxAge / 1000) }, body: buf }; res.writeHead(200, icon.headers); res.end(icon.body); }); } } else { next(); } }; };
|