moved the caching logic to its own module
added first pass at tests