twitst4tz

twitter statistics web application
Log | Files | Refs | README | LICENSE

debug.js (4889B)


      1 
      2 /**
      3  * This is the common logic for both the Node.js and web browser
      4  * implementations of `debug()`.
      5  *
      6  * Expose `debug()` as the module.
      7  */
      8 
      9 exports = module.exports = createDebug.debug = createDebug['default'] = createDebug;
     10 exports.coerce = coerce;
     11 exports.disable = disable;
     12 exports.enable = enable;
     13 exports.enabled = enabled;
     14 exports.humanize = require('ms');
     15 
     16 /**
     17  * Active `debug` instances.
     18  */
     19 exports.instances = [];
     20 
     21 /**
     22  * The currently active debug mode names, and names to skip.
     23  */
     24 
     25 exports.names = [];
     26 exports.skips = [];
     27 
     28 /**
     29  * Map of special "%n" handling functions, for the debug "format" argument.
     30  *
     31  * Valid key names are a single, lower or upper-case letter, i.e. "n" and "N".
     32  */
     33 
     34 exports.formatters = {};
     35 
     36 /**
     37  * Select a color.
     38  * @param {String} namespace
     39  * @return {Number}
     40  * @api private
     41  */
     42 
     43 function selectColor(namespace) {
     44   var hash = 0, i;
     45 
     46   for (i in namespace) {
     47     hash  = ((hash << 5) - hash) + namespace.charCodeAt(i);
     48     hash |= 0; // Convert to 32bit integer
     49   }
     50 
     51   return exports.colors[Math.abs(hash) % exports.colors.length];
     52 }
     53 
     54 /**
     55  * Create a debugger with the given `namespace`.
     56  *
     57  * @param {String} namespace
     58  * @return {Function}
     59  * @api public
     60  */
     61 
     62 function createDebug(namespace) {
     63 
     64   var prevTime;
     65 
     66   function debug() {
     67     // disabled?
     68     if (!debug.enabled) return;
     69 
     70     var self = debug;
     71 
     72     // set `diff` timestamp
     73     var curr = +new Date();
     74     var ms = curr - (prevTime || curr);
     75     self.diff = ms;
     76     self.prev = prevTime;
     77     self.curr = curr;
     78     prevTime = curr;
     79 
     80     // turn the `arguments` into a proper Array
     81     var args = new Array(arguments.length);
     82     for (var i = 0; i < args.length; i++) {
     83       args[i] = arguments[i];
     84     }
     85 
     86     args[0] = exports.coerce(args[0]);
     87 
     88     if ('string' !== typeof args[0]) {
     89       // anything else let's inspect with %O
     90       args.unshift('%O');
     91     }
     92 
     93     // apply any `formatters` transformations
     94     var index = 0;
     95     args[0] = args[0].replace(/%([a-zA-Z%])/g, function(match, format) {
     96       // if we encounter an escaped % then don't increase the array index
     97       if (match === '%%') return match;
     98       index++;
     99       var formatter = exports.formatters[format];
    100       if ('function' === typeof formatter) {
    101         var val = args[index];
    102         match = formatter.call(self, val);
    103 
    104         // now we need to remove `args[index]` since it's inlined in the `format`
    105         args.splice(index, 1);
    106         index--;
    107       }
    108       return match;
    109     });
    110 
    111     // apply env-specific formatting (colors, etc.)
    112     exports.formatArgs.call(self, args);
    113 
    114     var logFn = debug.log || exports.log || console.log.bind(console);
    115     logFn.apply(self, args);
    116   }
    117 
    118   debug.namespace = namespace;
    119   debug.enabled = exports.enabled(namespace);
    120   debug.useColors = exports.useColors();
    121   debug.color = selectColor(namespace);
    122   debug.destroy = destroy;
    123 
    124   // env-specific initialization logic for debug instances
    125   if ('function' === typeof exports.init) {
    126     exports.init(debug);
    127   }
    128 
    129   exports.instances.push(debug);
    130 
    131   return debug;
    132 }
    133 
    134 function destroy () {
    135   var index = exports.instances.indexOf(this);
    136   if (index !== -1) {
    137     exports.instances.splice(index, 1);
    138     return true;
    139   } else {
    140     return false;
    141   }
    142 }
    143 
    144 /**
    145  * Enables a debug mode by namespaces. This can include modes
    146  * separated by a colon and wildcards.
    147  *
    148  * @param {String} namespaces
    149  * @api public
    150  */
    151 
    152 function enable(namespaces) {
    153   exports.save(namespaces);
    154 
    155   exports.names = [];
    156   exports.skips = [];
    157 
    158   var i;
    159   var split = (typeof namespaces === 'string' ? namespaces : '').split(/[\s,]+/);
    160   var len = split.length;
    161 
    162   for (i = 0; i < len; i++) {
    163     if (!split[i]) continue; // ignore empty strings
    164     namespaces = split[i].replace(/\*/g, '.*?');
    165     if (namespaces[0] === '-') {
    166       exports.skips.push(new RegExp('^' + namespaces.substr(1) + '$'));
    167     } else {
    168       exports.names.push(new RegExp('^' + namespaces + '$'));
    169     }
    170   }
    171 
    172   for (i = 0; i < exports.instances.length; i++) {
    173     var instance = exports.instances[i];
    174     instance.enabled = exports.enabled(instance.namespace);
    175   }
    176 }
    177 
    178 /**
    179  * Disable debug output.
    180  *
    181  * @api public
    182  */
    183 
    184 function disable() {
    185   exports.enable('');
    186 }
    187 
    188 /**
    189  * Returns true if the given mode name is enabled, false otherwise.
    190  *
    191  * @param {String} name
    192  * @return {Boolean}
    193  * @api public
    194  */
    195 
    196 function enabled(name) {
    197   if (name[name.length - 1] === '*') {
    198     return true;
    199   }
    200   var i, len;
    201   for (i = 0, len = exports.skips.length; i < len; i++) {
    202     if (exports.skips[i].test(name)) {
    203       return false;
    204     }
    205   }
    206   for (i = 0, len = exports.names.length; i < len; i++) {
    207     if (exports.names[i].test(name)) {
    208       return true;
    209     }
    210   }
    211   return false;
    212 }
    213 
    214 /**
    215  * Coerce `val`.
    216  *
    217  * @param {Mixed} val
    218  * @return {Mixed}
    219  * @api private
    220  */
    221 
    222 function coerce(val) {
    223   if (val instanceof Error) return val.stack || val.message;
    224   return val;
    225 }