memory.js 2.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116
  1. /**
  2. * Module dependencies.
  3. */
  4. var crypto = require('crypto')
  5. , nodes = require('../nodes');
  6. var MemoryCache = module.exports = function(options) {
  7. options = options || {};
  8. this.limit = options['cache limit'] || 256;
  9. this._cache = {};
  10. this.length = 0;
  11. this.head = this.tail = null;
  12. };
  13. /**
  14. * Set cache item with given `key` to `value`.
  15. *
  16. * @param {String} key
  17. * @param {Object} value
  18. * @api private
  19. */
  20. MemoryCache.prototype.set = function(key, value) {
  21. var clone = value.clone()
  22. , item;
  23. clone.filename = nodes.filename;
  24. clone.lineno = nodes.lineno;
  25. clone.column = nodes.column;
  26. item = { key: key, value: clone };
  27. this._cache[key] = item;
  28. if (this.tail) {
  29. this.tail.next = item;
  30. item.prev = this.tail;
  31. } else {
  32. this.head = item;
  33. }
  34. this.tail = item;
  35. if (this.length++ == this.limit) this.purge();
  36. };
  37. /**
  38. * Get cache item with given `key`.
  39. *
  40. * @param {String} key
  41. * @return {Object}
  42. * @api private
  43. */
  44. MemoryCache.prototype.get = function(key) {
  45. var item = this._cache[key]
  46. , val = item.value.clone();
  47. if (item == this.tail) return val;
  48. if (item.next) {
  49. if (item == this.head) this.head = item.next;
  50. item.next.prev = item.prev;
  51. }
  52. if (item.prev) item.prev.next = item.next;
  53. item.next = null;
  54. item.prev = this.tail;
  55. if (this.tail) this.tail.next = item;
  56. this.tail = item;
  57. return val;
  58. };
  59. /**
  60. * Check if cache has given `key`.
  61. *
  62. * @param {String} key
  63. * @return {Boolean}
  64. * @api private
  65. */
  66. MemoryCache.prototype.has = function(key) {
  67. return !!this._cache[key];
  68. };
  69. /**
  70. * Generate key for the source `str` with `options`.
  71. *
  72. * @param {String} str
  73. * @param {Object} options
  74. * @return {String}
  75. * @api private
  76. */
  77. MemoryCache.prototype.key = function(str, options) {
  78. var hash = crypto.createHash('sha1');
  79. hash.update(str + options.prefix);
  80. return hash.digest('hex');
  81. };
  82. /**
  83. * Remove the oldest item from the cache.
  84. *
  85. * @api private
  86. */
  87. MemoryCache.prototype.purge = function() {
  88. var item = this.head;
  89. if (this.head.next) {
  90. this.head = this.head.next;
  91. this.head.prev = null;
  92. }
  93. this._cache[item.key] = item.prev = item.next = null;
  94. this.length--;
  95. };