npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

bluecache

v4.1.3

Published

Read-through, in-memory, least recently used (lru) cache

Downloads

2,215

Readme

bluecache

Build Status Coverage Status

Read-through, in-memory, least recently used (lru) cache

Use

First, instantiate the cache – passing options if necessary.

const Bluecache = require('bluecache');
const options = {
  max: 500,
  maxAge: '1h'
};

const cache = Bluecache(options);

Traditional cache "getting" and "setting" takes place within a single call, promoting functional use. The cache instance is a Promise-returning function which takes two parameters: a cache key and a priming value.

cache(Promise.resolve('dinosaur'), (key) => {
  console.log(`the invoked key was: ${key}`); // "the invoked key was: dinosaur"
  return Promise.resolve('rar');
})
.then((value) => {
  console.log(`the resolved value is: ${value}`); // "the resolved value is: rar"
});

Options

Options are passed to lru-cache at instantiation:

  • max: The maximum size of the cache, checked by applying the length function to all values in the cache
  • maxAge: Maximum age in ms (or a valid ms expression); lazily enforced; expired keys will return undefined
  • length: Function called to calculate the length of stored items (e.g. function (n) { return n.length; }); defaults to function (n) { return 1; }
  • dispose: Function called on items immediately before they are dropped from the cache; called with parameters (key, value)
  • stale: Allow the cache to return a stale (expired via maxAge) value before it is deleted

In addition, the following options are specific to bluecache:

  • pruneInterval: Interval at which the cache will pro-actively remove stale entries; by default stale items remain in memory until the next attempted read

Note: the underlying cache stores a memo for the promised value and a default length of 1 while the value is being resolved. After the value is first resolved, the length is updated to reflect the desired options.length passed at instantiation. (In short, peak cache "max" may exceed the specified max while values are being resolved.)

API

cache(key, primingValue)

Attempts to get the current value of key from the cache. If the key was previously used, the "recently-used"-ness of the key is updated and the cached value is returned. If the key does not exist, the primingValue is determined and the underlying cache value is set. If the primingValue is a function, it is invoked with the resolved key (resolved as a String) as its single argument.

Both key and primingValue can be a Boolean, Number, String, Symbol, Object, a Function that returns one of these primitives, or a Promise that resolves to one of these primitives.

By immediately caching and returning a Promise, the cache avoids a stampede for the target primingValue. However, a stampede may occur for a key because it resolves on each cache call. If you plan to asynchronously resolve the key, consider caching the key function as well.

A rejected Promise is returned if key is empty (null or undefined) or if there is an error resolving the primingValue.

cache#del(key)

Returns a Promise that resolves to undefined after deleting key from the cache.

cache#reset()

Clears the cache entirely, throwing away all values. Returns a Promise that resolves to null after the cache has been reset.

cache#on(eventName, eventHandler)

eventName is a string, corresponding to a supported event. eventHandler is a function which responds to the data provided by the target event.

cache.on('cache:hit', (data) => {
  console.log(`The cache took ${data.ms} milliseconds to respond to key: ${data.key}.`);
});

Emitted events

The cache instance is also an event emitter which provides an on method against which the implementing application can listen for the below events.

cache:hit

{
  'key': <String>,
  'ms': <Number:Integer:Milliseconds>
}

Note: ms is milliseconds elapsed between cache invocation and final resolution of the cached value.

cache:miss

{
  'key': <String>,
  'ms': <Number:Integer:Milliseconds>
}

Note: ms is milliseconds elapsed between cache invocation and final resolution of the priming value.

Changelog

v3 → v4

v2 → v3

  • [breaking] Removed support for interval Object options in favor of ms expression
  • [minor] Added support for automatic pruning via pruneInterval option

v1 → v2

  • [breaking] Addressed thundering herd problem identified by @ketilovre and others (a minor api change but the side-effects in underlying _lrucache are considered breaking)
  • [breaking] Removed #reset instance method which was abused in practice; use a key-specific #del instead
  • [minor] Generalized key and priming values to any primitive, promise, or function
  • [patch] Upgraded dependencies
  • [patch] Reorganized test suite

Contribute

PRs are welcome! For bugs, please include a failing test which passes when your PR is applied.

Thanks @ismriv!

Tests

To run the unit test suite:

npm test

Or, to determine unit test coverage:

npm run coverage

This project maintains 100% coverage of statements, branches, and functions.