diff --git a/CHANGELOG.md b/CHANGELOG.md
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,5 +1,16 @@
 # Changelog
 
+# v0.1.2 (2014-10-11)
+
+- Support GHC 7.6.
+- Support aeson 0.8.
+- Support criterion 1.0.
+- Support transformers 0.4.
+
+# v0.1.1 (2014-10-11)
+
+- Switch PostgreSQL username from "taylor" to "postgres".
+
 # v0.1.0 (2014-10-11)
 
 - Initial release.
diff --git a/README.md b/README.md
--- a/README.md
+++ b/README.md
@@ -1,9 +1,89 @@
 # [Hairy][1]
 
-[![Build Status][2]][3]
+[![Package version][2]][3]
+[![Build status][4]][5]
+[![Dependency status][6]][7]
 
-A RESTful CRUD web app.
+Hairy is a JSON REST API built in Haskell. It uses Scotty to create a WAI
+application served by the Warp web server. The Aeson library handles encoding
+and decoding JSON, while Persistent manages the PostgreSQL database. Hairy
+features an Hspec test suite and Criterion benchmarks.
 
+The entire project is meant to be easy to build, understand, and use. It doesn't
+really do anything useful, but it shows how to do anything at all. Take a look
+at [the literate source][8] to see how it all works.
+
+- [Requirements](#requirements)
+- [Installation](#installation)
+- [Setup](#setup)
+- [Configuration](#configuration)
+
+## Requirements
+
+Hairy works best with the latest [Haskell Platform][9], but it also supports GHC
+7.8 and 7.6. [PostgreSQL][10] 9.1 or later is also required.
+
+## Installation
+
+Add it to your Cabal file:
+
+```
+library
+  build-depends:
+    hairy ==0.1.*
+```
+
+Or install it manually:
+
+``` sh
+$ cabal update
+$ cabal install hairy-0.1.2
+```
+
+This package uses [Semantic Versioning][11].
+
+## Setup
+
+First create a database user for Hairy.
+
+``` sh
+$ createuser --createdb postgres
+```
+
+Then create databases for each environment.
+
+``` sh
+$ psql --username postgres --command 'CREATE DATABASE hairy_development'
+$ psql --username postgres --command 'CREATE DATABASE hairy_production'
+$ psql --username postgres --command 'CREATE DATABASE hairy_test'
+```
+
+Then just start the server!
+
+``` sh
+$ hairy
+# => http://localhost:3000
+```
+
+## Configuration
+
+Hairy can be configured through environment variables. To configure the
+environment, use the `SCOTTY_ENV` environment variable.
+
+``` sh
+$ env SCOTTY_ENV=Production hairy
+```
+
+Possible environments include `Development`, `Production`, and `Test`.
+
 [1]: https://github.com/tfausak/hairy
-[2]: https://travis-ci.org/tfausak/hairy.svg?branch=master
-[3]: https://travis-ci.org/tfausak/hairy
+[2]: https://img.shields.io/hackage/v/hairy.svg?style=flat
+[3]: https://hackage.haskell.org/package/hairy
+[4]: https://img.shields.io/travis/tfausak/hairy/master.svg?style=flat
+[5]: https://travis-ci.org/tfausak/hairy
+[6]: https://img.shields.io/hackage-deps/v/hairy.svg?style=flat
+[7]: http://packdeps.haskellers.com/feed?needle=hairy
+[8]: ./library/Hairy.lhs
+[9]: https://www.haskell.org/platform/
+[10]: http://www.postgresql.org
+[11]: http://semver.org/spec/v2.0.0.html
diff --git a/hairy.cabal b/hairy.cabal
--- a/hairy.cabal
+++ b/hairy.cabal
@@ -1,5 +1,5 @@
 name: hairy
-version: 0.1.1
+version: 0.1.2
 cabal-version: >=1.10
 build-type: Simple
 license: MIT
@@ -8,15 +8,15 @@
 maintainer: Taylor Fausak <taylor@fausak.me>
 homepage: https://github.com/tfausak/hairy
 bug-reports: https://github.com/tfausak/hairy/issues
-synopsis: A RESTful CRUD web app.
+synopsis: A JSON REST API
 description:
-    A RESTful CRUD web app.
+    Hairy is a JSON REST API.
     .
     Check out <https://github.com/tfausak/hairy#readme the readme> for
     documentation.
 category: Web
 author: Taylor Fausak <taylor@fausak.me>
-tested-with: GHC ==7.8.*
+tested-with: GHC ==7.6.* GHC ==7.8.*
 extra-source-files:
     CHANGELOG.md
     CONTRIBUTING.md
@@ -29,7 +29,7 @@
 library
     build-depends:
         base ==4.*,
-        aeson ==0.7.*,
+        aeson >=0.7 && <0.9,
         data-default ==0.5.*,
         http-types ==0.8.*,
         mtl ==2.*,
@@ -40,7 +40,7 @@
         scotty ==0.9.*,
         text ==1.*,
         time ==1.*,
-        transformers ==0.3.*,
+        transformers >=0.3 && <0.5,
         wai ==3.*,
         wai-extra ==3.*,
         warp ==3.*
@@ -84,7 +84,7 @@
     build-depends:
         base -any,
         hairy -any,
-        criterion ==0.8.*,
+        criterion >=0.8 && <2,
         http-types -any,
         mtl -any,
         persistent -any,
diff --git a/library/Hairy.lhs b/library/Hairy.lhs
--- a/library/Hairy.lhs
+++ b/library/Hairy.lhs
@@ -1,9 +1,32 @@
+Before we can begin, we need to enable a few language extensions.
+
+> {-# LANGUAGE OverloadedStrings #-}
+
+This extension allows string literals (like `"cheese"`) to represent string-like
+types such as `ByteString` and `Text`. It's not strictly required since you
+could do the same thing using `pack`, for instance. But it's so convenient that
+it's hard to live without.
+
 > {-# LANGUAGE FlexibleContexts #-}
 > {-# LANGUAGE GeneralizedNewtypeDeriving #-}
-> {-# LANGUAGE OverloadedStrings #-}
 
+These are a little harder to explain, so instead I'll explain them when they're
+used.
+
+Now we have to let GHC know that our module is called `Hairy`, not `Main` like
+it would otherwise assume.
+
 > module Hairy where
 
+Imports make up the last bit of the preamble. These are a little overly-specific
+in order to make it easier to see where everything came from. In the real world
+you might import everything from, say, `Web.Scotty.Trans` instead of explicitly
+listing everything you needed from it.
+
+For the most part, you don't have to worry about these imports. If you're
+curious about something later on, come back up here to see where it's imported
+from. Then look it up on Hackage.
+
 > import Control.Applicative (Applicative)
 > import Control.Monad.IO.Class (MonadIO, liftIO)
 > import Control.Monad.Logger (runNoLoggingT, runStdoutLoggingT)
@@ -15,7 +38,8 @@
 > import qualified Database.Persist as DB
 > import qualified Database.Persist.Postgresql as DB
 > import Hairy.Models (Task, TaskId, migrateAll)
-> import Network.HTTP.Types.Status (created201, internalServerError500, notFound404)
+> import Network.HTTP.Types.Status (created201, internalServerError500,
+>   notFound404)
 > import Network.Wai (Middleware)
 > import Network.Wai.Handler.Warp (defaultSettings)
 > import Network.Wai.Middleware.RequestLogger (logStdout, logStdoutDev)
@@ -86,6 +110,7 @@
 >       r m = runReaderT (runConfigM m) c
 >   scottyOptsT o r r application
 
+> -- GeneralizedNewtypeDeriving
 > newtype ConfigM a = ConfigM
 >  { runConfigM :: ReaderT Config IO a
 >  } deriving (Applicative, Functor, Monad, MonadIO, MonadReader Config)
@@ -171,6 +196,7 @@
 >   runDB (DB.delete (toKey i :: TaskId))
 >   json Null
 
+> -- FlexibleContexts
 > toKey :: DB.ToBackendKey DB.SqlBackend a => Integer -> DB.Key a
 > toKey i = DB.toSqlKey (fromIntegral (i :: Integer))
 
