Bring across files from causes.git

There are a couple of dependencies that prevent this from actually
working in isolation as-is (for one, we depended on Active Support's
`#blank?` method; for another our specs rely on the custom async
dispatcher that we use in causes.git).

I wanted this commit to be a straight move so that the edits from the
original versions would be obvious.

Change-Id: Id85d76c95c081b77d96df8c11bad84fc8616debd
Reviewed-on: https://gerrit.causes.com/26273
Reviewed-by: Lann Martin <lann@causes.com>
Reviewed-by: Henric Trotzig <henric.trotzig@causes.com>
Tested-by: Greg Hurrell <greg@causes.com>