Add caching API.

The caching API enables data to be fetched asynchronously. It also has
a dual locking scheme in place: keys can be locked for a specific
amount of time, and only one process can update the key at a time.

This augments the Impromptu process by splitting it into two
phases. The first generates your prompt using cached values. The
second is run in the background and asynchronously updates any cached
values. They use the same API; the magic occurs behind the scenes.