diff --git a/panhandle.cabal b/panhandle.cabal
--- a/panhandle.cabal
+++ b/panhandle.cabal
@@ -1,5 +1,5 @@
 name:                panhandle
-version:             0.2.0.0
+version:             0.2.1.0
 synopsis:            Pandoc filter to unwrap nested blocks
 description:         Pandoc filter to splice together nested documents
 homepage:            http://chriswarbo.net/projects/activecode
@@ -9,7 +9,7 @@
 maintainer:          chriswarbo@gmail.com
 category:            Text
 build-type:          Simple
-extra-source-files:  README.md
+extra-source-files:  README.md, test.sh
 cabal-version:       >=1.10
 
 source-repository head
@@ -37,6 +37,7 @@
   type:                exitcode-stdio-1.0
   hs-source-dirs:      tests
   main-is:             Main.hs
+  other-modules:       LSC, Generators
   build-depends:       base       >= 4.7
                      , panhandle
                      , QuickCheck
diff --git a/test.sh b/test.sh
new file mode 100644
--- /dev/null
+++ b/test.sh
@@ -0,0 +1,45 @@
+#!/usr/bin/env bash
+set -e
+set -o pipefail
+
+command -v pandoc || {
+    echo "Couldn't find pandoc binary, aborting" 1>&2
+    exit 1
+}
+
+function run {
+    if command -v cabal2nix
+    then
+        EXPR=$(cabal2nix ./.)
+        nix-shell -p "(haskellPackages.callPackage ($EXPR) {})" --run 'panhandle'
+    else
+        cabal run panhandle
+    fi
+}
+
+MARKDOWN="*foo*"
+echo "Got Markdown '$MARKDOWN'"
+
+JSON=$(echo "$MARKDOWN" | pandoc -f markdown -t json)
+echo "Got JSON '$JSON'"
+
+# shellcheck disable=SC2016
+UNWRAP=$(echo '```{.unwrap}'; echo "$JSON"; echo '```')
+echo "Got unwrap '$UNWRAP'"
+
+META=$(echo "$UNWRAP" | pandoc -f markdown -t json)
+echo "Got meta '$META'"
+
+UNWRAP=$(echo "$META" | run) || {
+    echo "Failed to unwrap" 1>&2
+    exit 1
+}
+echo "Got unwrapped '$UNWRAP'"
+
+FINAL=$(echo "$UNWRAP" | pandoc -f json -t html)
+echo "Got HTML '$FINAL'"
+
+echo "$FINAL" | grep '<em>foo</em>' || {
+    echo "Didn't unwrap *foo* in '$FINAL'" 1>&2
+    exit 1
+}
diff --git a/tests/Generators.hs b/tests/Generators.hs
new file mode 100644
--- /dev/null
+++ b/tests/Generators.hs
@@ -0,0 +1,51 @@
+{-# LANGUAGE TemplateHaskell #-}
+
+module Generators where
+
+import Data.DeriveTH
+import Test.QuickCheck
+import Text.Pandoc
+import Data.Derive.Arbitrary
+import Data.Map
+import Test.LazySmallCheck2012
+import Test.LazySmallCheck2012.TH
+
+$( derive makeArbitrary ''Block )
+$( derive makeArbitrary ''Inline )
+$( derive makeArbitrary ''QuoteType )
+$( derive makeArbitrary ''MathType )
+$( derive makeArbitrary ''ListNumberStyle )
+$( derive makeArbitrary ''Citation )
+$( derive makeArbitrary ''ListNumberDelim )
+$( derive makeArbitrary ''CitationMode )
+$( derive makeArbitrary ''Format )
+$( derive makeArbitrary ''Alignment )
+$( derive makeArbitrary ''Pandoc )
+$( derive makeArbitrary ''Meta )
+$( derive makeArbitrary ''MetaValue )
+
+$( deriveSerial ''Pandoc )
+$( deriveSerial ''Block )
+$( deriveSerial ''Inline )
+$( deriveSerial ''MetaValue )
+$( deriveSerial ''QuoteType )
+$( deriveSerial ''ListNumberStyle )
+$( deriveSerial ''MathType )
+$( deriveSerial ''ListNumberDelim )
+$( deriveSerial ''CitationMode )
+$( deriveSerial ''Alignment )
+
+instance (Serial a, Ord a, Serial b) => Serial (Map a b) where
+  series = cons1 fromList
+
+instance Serial Meta where
+  series = cons1 Meta
+
+instance Serial Citation where
+  series = cons5 Citation <*> series
+
+instance Serial Double where
+  series = drawnFrom $ \d -> Prelude.map (fromInteger . toInteger) [(-d)..d]
+
+instance Serial Format where
+  series = cons1 Format
diff --git a/tests/LSC.hs b/tests/LSC.hs
new file mode 100644
--- /dev/null
+++ b/tests/LSC.hs
@@ -0,0 +1,19 @@
+{-# LANGUAGE RankNTypes #-}
+module LSC where
+
+import Data.Data
+import Data.Tagged
+import Test.LazySmallCheck2012
+import Test.Tasty.Providers
+
+newtype LSC a = LSC a
+
+instance (Testable a, Typeable a, Data a) => IsTest (LSC a) where
+  run os (LSC t) p = do b <- depthCheckResult 3 t
+                        return (if b then testPassed ""
+                                     else testFailed "")
+  testOptions = Tagged {
+      unTagged = []
+    }
+
+lazyProperty n t = singleTest n (LSC t)
