diff --git a/Data/Versions.hs b/Data/Versions.hs
new file mode 100644
--- /dev/null
+++ b/Data/Versions.hs
@@ -0,0 +1,347 @@
+{-# LANGUAGE OverloadedStrings #-}
+
+-- |
+-- Module    : Data.Versions
+-- Copyright : (c) Colin Woodbury, 2015
+-- License   : BSD3
+-- Maintainer: Colin Woodbury <colingw@gmail.com>
+--
+-- A library for parsing and comparing software version numbers.
+--
+-- We like to give version numbers to our software in a myriad of different
+-- ways. Some ways follow strict guidelines for incrementing and comparison.
+-- Some follow conventional wisdom and are generally self-consistent.
+-- Some are just plain asinine. This library provides a means of parsing
+-- and comparing /any/ style of versioning, be it a nice Semantic Version
+-- like this:
+--
+-- > 1.2.3-r1+git123
+--
+-- ...or a monstrosity like this:
+--
+-- > 2:10.2+0.0093r3+1-1
+--
+-- Please switch to <http://semver.org Semantic Versioning> if you
+-- aren't currently using it. It provides consistency in version
+-- incrementing and has the best constraints on comparisons.
+--
+-- == Using the Parsers
+-- In general, `parseV` is the function you want. It attempts to parse
+-- a given @Text@ using the three individual parsers, `semver`, `version`
+-- and `mess`. If one fails, it tries the next. If you know you only want
+-- to parse one specific version type, use that parser directly
+-- (e.g. `semver`).
+
+module Data.Versions
+    (
+      -- * Types
+      Versioning(..)
+    , SemVer(..)
+    , Version(..)
+    , Mess(..)
+    , VUnit(..)
+    , VChunk
+    , VSep(..)
+    , VParser(..)
+      -- * Parsers
+    , semver
+    , semver'
+    , version
+    , version'
+    , mess
+    , mess'
+      -- ** Wrapped Parsers
+    , parseV
+    , semverP
+    , versionP
+    , messP
+      -- * Pretty Printing
+    , prettyV
+    , prettySemVer
+    , prettyVer
+    , prettyMess ) where
+
+import Data.List (intersperse)
+import Data.Semigroup
+import Data.Text (Text,pack,unpack,snoc)
+import Text.ParserCombinators.Parsec
+import TextShow (showt)
+
+---
+
+-- | A top-level Versioning type. Acts as a wrapper for the more specific
+-- types. This allows each subtype to have its own parser, and for said
+-- parsers to be composed. This is useful for specifying custom behaviour
+-- for when a certain parser fails.
+data Versioning = Ideal SemVer | General Version | Complex Mess
+                deriving (Eq,Show)
+
+-- | Comparison of @Ideal@s is always well defined.
+--
+-- If comparison of @General@s is well-defined, then comparison
+-- of @Ideal@ and @General@ is well-defined, as there exists a perfect
+-- mapping from @Ideal@ to @General@.
+--
+-- If comparison of @Complex@es is well-defined, then comparison of @General@
+-- and @Complex@ is well defined for the same reason.
+-- This implies comparison of @Ideal@ and @Complex@ is also well-defined.
+instance Ord Versioning where
+  compare (Ideal s)     (Ideal s')    = compare s s'
+  compare (General v)   (General v')  = compare v v'
+  compare (Complex m)   (Complex m')  = compare m m'
+  compare (Ideal s)     (General v)   = cmpSV s v
+  compare (General v)   (Ideal s)     = opposite $ cmpSV s v
+  compare (General v)   (Complex m)   = compare (mFromV v) m
+  compare (Complex m)   (General v)   = opposite $ compare (mFromV v) m
+  compare (Ideal s)     m@(Complex _) = compare (General $ vFromS s) m
+  compare m@(Complex _) (Ideal s)     = compare m (General $ vFromS s)
+
+cmpSV :: SemVer -> Version -> Ordering
+cmpSV s (Version cs re) = compare (cs' ++ re') $ cs ++ re
+  where (Version cs' re') = vFromS s
+
+-- | Convert a `SemVer` to a `Version`.
+vFromS :: SemVer -> Version
+vFromS (SemVer m i p r _) = Version [[Digits m], [Digits i], [Digits p]] r
+
+-- | Convert a `Version` to a `Mess`.
+mFromV :: Version -> Mess
+mFromV (Version v r) = VNode (chunksAsT v) VHyphen $ VLeaf (chunksAsT r)
+
+-- | An (Ideal) version number that conforms to Semantic Versioning.
+-- This is a /prescriptive/ parser, meaning it follows the SemVer standard.
+--
+-- Legal semvers are of the form: MAJOR.MINOR.PATCH-PREREL+META
+--
+-- Example: 1.2.3-r1+commithash
+--
+-- Extra Rules:
+--
+-- 1. Pre-release versions have /lower/ precedence than normal versions.
+--
+-- 2. Build metadata does not affect version precedence.
+--
+-- For more information, see http://semver.org
+data SemVer = SemVer { svMajor  :: Int
+                     , svMinor  :: Int
+                     , svPatch  :: Int
+                     , svPreRel :: [VChunk]
+                     , svMeta   :: [VChunk] } deriving (Show)
+
+-- | Two SemVers are equal if all fields except metadata are equal.
+instance Eq SemVer where
+  (SemVer ma mi pa pr _) == (SemVer ma' mi' pa' pr' _) =
+    (ma,mi,pa,pr) == (ma',mi',pa',pr')
+
+-- | Build metadata does not affect version precedence.
+instance Ord SemVer where
+  compare (SemVer ma mi pa pr _) (SemVer ma' mi' pa' pr' _) =
+    case compare (ma,mi,pa) (ma',mi',pa') of
+     LT -> LT
+     GT -> GT
+     EQ -> case (pr,pr') of
+            ([],[]) -> EQ
+            ([],_)  -> GT
+            (_,[])  -> LT
+            _       -> compare pr pr'
+
+-- | A single unit of a Version. May be digits or a string of characters.
+-- Groups of these are called `VChunk`s, and are the identifiers separated
+-- by periods in the source.
+data VUnit = Digits Int | Str Text deriving (Eq,Show,Read,Ord)
+
+-- | A logical unit of a version number. Can consist of multiple letters
+-- and numbers.
+type VChunk = [VUnit]
+
+-- | A (General) Version.
+-- Not quite as ideal as a `SemVer`, but has some internal consistancy
+-- from version to version.
+-- Generally conforms to the @x.x.x-x@ pattern.
+--
+-- Examples of @Version@ that are not @SemVer@: 0.25-2, 8.u51-1, 20150826-1
+data Version = Version { vChunks :: [VChunk]
+                       , vRel    :: [VChunk] } deriving (Eq,Ord,Show)
+
+-- | A (Complex) Mess.
+-- This is a /descriptive/ parser, based on examples of stupidly
+-- crafted version numbers used in the wild.
+--
+-- Groups of letters/numbers, separated by a period, can be
+-- further separated by the symbols @_-+:@
+--
+-- Unfortunately, @VChunk@s cannot be used here, as some developers have
+-- numbers like @1.003.04@ which make parsers quite sad.
+--
+-- Not guaranteed to have well-defined ordering (@Ord@) behaviour,
+-- but so far interal tests show consistency.
+data Mess = VLeaf [Text] | VNode [Text] VSep Mess deriving (Eq,Show)
+
+instance Ord Mess where
+  compare (VLeaf l1) (VLeaf l2)     = compare l1 l2
+  compare (VNode t1 _ _) (VLeaf t2) = compare t1 t2
+  compare (VLeaf t1) (VNode t2 _ _) = compare t1 t2
+  compare (VNode t1 _ v1) (VNode t2 _ v2) | t1 < t2 = LT
+                                          | t1 > t2 = GT
+                                          | otherwise = compare v1 v2
+
+-- | Developers use a number of symbols to seperate groups of digits/letters
+-- in their version numbers. These are:
+--
+-- * A colon (:). Often denotes an "epoch".
+-- * A hyphen (-).
+-- * A plus (+). Stop using this outside of metadata if you are. Example: @10.2+0.93+1-1@
+-- * An underscore (_). Stop using this if you are.
+data VSep = VColon | VHyphen | VPlus | VUnder deriving (Eq,Show)
+
+-- | A wrapper for a parser function. Can be composed via their
+-- Semigroup instance, such that a different parser can be tried
+-- if a previous one fails.
+newtype VParser = VParser { runVP :: Text -> Either ParseError Versioning }
+
+instance Semigroup VParser where
+  (VParser f) <> (VParser g) = VParser h
+    where h t = either (const (g t)) Right $ f t
+
+-- | Parse a piece of @Text@ into either an (Ideal) SemVer, a (General)
+-- Version, or a (Complex) Mess.
+parseV :: Text -> Either ParseError Versioning
+parseV = runVP $ semverP <> versionP <> messP
+
+-- | A wrapped `SemVer` parser. Can be composed with other parsers.
+semverP :: VParser
+semverP = VParser $ fmap Ideal . semver
+
+-- | Parse a (Ideal) Semantic Version.
+semver :: Text -> Either ParseError SemVer
+semver = semver' . unpack
+
+-- | Parse a Semantic Version, as a legacy String.
+semver' :: String -> Either ParseError SemVer
+semver' = parse semanticVersion "Semantic Version"
+
+semanticVersion :: Parser SemVer
+semanticVersion = p <* eof
+  where p = SemVer <$> major <*> minor <*> patch <*> preRel <*> metaData
+
+-- | Parse a group of digits, which can't be lead by a 0, unless it is 0.
+digits :: Parser Int
+digits = read <$> (string "0" <|> many1 digit)
+
+major :: Parser Int
+major = digits <* char '.'
+
+minor :: Parser Int
+minor = major
+
+patch :: Parser Int
+patch = digits
+
+preRel :: Parser [VChunk]
+preRel = (char '-' *> chunks) <|> pure []
+
+metaData :: Parser [VChunk]
+metaData = (char '+' *> chunks) <|> pure []
+
+chunks :: Parser [VChunk]
+chunks = (oneZero <|> many (iunit <|> sunit)) `sepBy` char '.'
+  where oneZero = (:[]) . Digits . read <$> string "0"
+
+iunit :: Parser VUnit
+iunit = Digits . read <$> many1 digit
+
+sunit :: Parser VUnit
+sunit = Str . pack <$> many1 letter
+
+-- | A wrapped `Version` parser. Can be composed with other parsers.
+versionP :: VParser
+versionP = VParser $ fmap General . version
+
+-- | Parse a (General) `Version`, as defined above.
+version :: Text -> Either ParseError Version
+version = version' . unpack
+
+-- | Parse a `Version`, where the input is a legacy String.
+version' :: String -> Either ParseError Version
+version' = parse versionNum "Version"
+
+versionNum :: Parser Version
+versionNum = Version <$> chunks <*> preRel <* eof
+
+-- | A wrapped `Mess` parser. Can be composed with other parsers.
+messP :: VParser
+messP = VParser $ fmap Complex . mess
+
+-- | Parse a (Complex) `Mess`, as defined above. 
+mess :: Text -> Either ParseError Mess
+mess = mess' . unpack
+
+-- | Parse a `Mess`, where the input is a legacy String.
+mess' :: String -> Either ParseError Mess
+mess' = parse messNumber "Mess"
+
+messNumber :: Parser Mess
+messNumber = try node <|> leaf
+
+leaf :: Parser Mess
+leaf = VLeaf <$> tchunks <* eof
+
+node :: Parser Mess
+node = VNode <$> tchunks <*> sep <*> messNumber
+
+tchunks :: Parser [Text]
+tchunks = (pack <$> many1 (letter <|> digit)) `sepBy` char '.'
+
+sep :: Parser VSep
+sep = choice [ VColon  <$ char ':'
+             , VHyphen <$ char '-'
+             , VPlus   <$ char '+'
+             , VUnder  <$ char '_' ]
+
+sepCh :: VSep -> Char
+sepCh VColon  = ':'
+sepCh VHyphen = '-'
+sepCh VPlus   = '+'
+sepCh VUnder  = '_'
+
+-- | Convert any parsed Versioning type to its textual representation.
+prettyV :: Versioning -> Text
+prettyV (Ideal sv)  = prettySemVer sv
+prettyV (General v) = prettyVer v
+prettyV (Complex m) = prettyMess m
+
+-- | Convert a `SemVer` back to its textual representation.
+prettySemVer :: SemVer -> Text
+prettySemVer (SemVer ma mi pa pr me) = mconcat $ ver <> pr' <> me'
+  where ver = intersperse "." [ showt ma, showt mi, showt pa ]
+        pr' = foldable [] ("-" :) $ intersperse "." (chunksAsT pr)
+        me' = foldable [] ("+" :) $ intersperse "." (chunksAsT me)
+
+-- | Convert a `Version` back to its textual representation.
+prettyVer :: Version -> Text
+prettyVer (Version cs pr) = mconcat $ ver <> pr'
+  where ver = intersperse "." $ chunksAsT cs
+        pr' = foldable [] ("-" :) $ intersperse "." (chunksAsT pr)
+
+-- | Convert a `Mess` back to its textual representation.
+prettyMess :: Mess -> Text
+prettyMess (VLeaf t)     = mconcat $ intersperse "." t
+prettyMess (VNode t s v) = snoc t' (sepCh s) <> prettyMess v
+  where t' = mconcat $ intersperse "." t
+
+chunksAsT :: [VChunk] -> [Text]
+chunksAsT = map (mconcat . map f)
+  where f (Digits i) = showt i
+        f (Str s)    = s
+
+-- | Analogous to `maybe` and `either`. If a given Foldable is empty,
+-- a default value is returned. Else, a function is applied to that Foldable.
+foldable :: Foldable f => f b -> (f a -> f b) -> f a -> f b
+foldable d g f | null f    = d
+               | otherwise = g f
+
+-- | Flip an Ordering.
+opposite :: Ordering -> Ordering
+opposite EQ = EQ
+opposite LT = GT
+opposite GT = LT
diff --git a/LICENSE b/LICENSE
new file mode 100644
--- /dev/null
+++ b/LICENSE
@@ -0,0 +1,30 @@
+Copyright (c) 2015, Colin Woodbury
+
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+
+    * Neither the name of Colin Woodbury nor the names of other
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/Setup.hs b/Setup.hs
new file mode 100644
--- /dev/null
+++ b/Setup.hs
@@ -0,0 +1,2 @@
+import Distribution.Simple
+main = defaultMain
diff --git a/test/Test.hs b/test/Test.hs
new file mode 100644
--- /dev/null
+++ b/test/Test.hs
@@ -0,0 +1,160 @@
+{-# LANGUAGE OverloadedStrings #-}
+
+module Test where
+
+import Data.Either
+import Data.Monoid ((<>))
+import Data.Text (Text,unpack)
+import Data.Versions
+import Test.Tasty
+import Test.Tasty.HUnit
+
+---
+
+-- | These don't need to parse as a SemVer.
+goodVers :: [Text]
+goodVers = [ "1", "1.2", "1.58.0-3",  "44.0.2403.157-1"
+           , "0.25-2",  "8.u51-1", "21-2", "7.1p1-1", "20150826-1"
+           ]
+
+messes :: [Text]
+messes = [ "10.2+0.93+1-1", "003.03-3", "002.000-7", "1:0.10.16-3"
+         , "20.26.1_0-2"
+         ]
+
+messComps :: [Text]
+messComps = [ "10.2+0.93+1-1", "10.2+0.93+1-2", "10.2+0.93+2-1"
+            , "10.2+0.94+1-1", "10.3+0.93+1-1", "11.2+0.93+1-1", "12"
+            ]
+
+badSemVs :: [Text]
+badSemVs = [ "1", "1.2", "1.2.3+a1b2bc3.1-alpha.2", "a.b.c", "1.01.1"
+           , "1.2.3+a1b!2c3.1"
+           ]
+
+goodSemVs :: [Text]
+goodSemVs = [ "0.1.0", "1.2.3", "1.2.3-1", "1.2.3-alpha", "1.2.3-alpha.2"
+            , "1.2.3+a1b2c3.1", "1.2.3-alpha.2+a1b2c3.1"
+            ]
+
+-- | The exact example from `http://semver.org`
+semverOrd :: [Text]
+semverOrd = [ "1.0.0-alpha", "1.0.0-alpha.1", "1.0.0-alpha.beta"
+            , "1.0.0-beta", "1.0.0-beta.2", "1.0.0-beta.11", "1.0.0-rc.1"
+            , "1.0.0"
+            ]
+
+-- | Cabal makes this distinction: 0.2 < 0.2.0 < 0.2.0.0
+-- Apparently there are only 5 packages on Hackage that actually
+-- make this necessary, meaning `cabal` can't be simplified to ignore it.
+-- Logically, these are the same package, but for those 5 packages, they
+-- aren't.
+cabalOrd :: [Text]
+cabalOrd = [ "0.2", "0.2.0", "0.2.0.0" ]
+
+versionOrd :: [Text]
+versionOrd = [ "0.9.9.9", "1.0.0.0", "1.0.0.1", "2" ]
+
+suite :: TestTree
+suite = testGroup "Unit Tests"
+  [ testGroup "(Ideal) Semantic Versioning"
+    [ testGroup "Bad Versions (shouldn't parse)" $
+      map (\s -> testCase (unpack s) $ assert $ isLeft $ semver s) badSemVs
+    , testGroup "Good Versions (should parse)" $
+      map (\s -> testCase (unpack s) $ isomorphSV s) goodSemVs
+    , testGroup "Comparisons" $
+      testCase "1.2.3-alpha.2 == 1.2.3-alpha.2+a1b2c3.1"
+      (assert $ semver "1.2.3-alpha.2" == semver "1.2.3-alpha.2+a1b2c3.1") :
+      map (\(a,b) -> testCase (unpack $ a <> " < " <> b) $ comp semver a b)
+      (zip semverOrd $ tail semverOrd)
+    ]
+  , testGroup "(General) Versions"
+    [ testGroup "Good Versions" $
+      map (\s -> testCase (unpack s) $ isomorphV s) goodVers
+    , testGroup "Comparisons" $
+      map (\(a,b) -> testCase (unpack $ a <> " < " <> b) $ comp version a b) $
+      zip cabalOrd (tail cabalOrd) <> zip versionOrd (tail versionOrd)
+    ]
+  , testGroup "(Complex) Mess"
+    [ testGroup "Good Versions" $
+      map (\s -> testCase (unpack s) $ isomorphM s) messes
+    , testGroup "Comparisons" $
+      map (\(a,b) -> testCase (unpack $ a <> " < " <> b) $ comp mess a b) $
+      zip messComps (tail messComps)
+    ]
+  , testGroup "Mixed Versioning" $
+    [ testGroup "Identification" $
+      [ testCase "1.2.3 is SemVer" $ check $ isSemVer <$> parseV "1.2.3"
+      , testCase "1.2.3-1 is SemVer" $ check $ isSemVer <$> parseV "1.2.3-1"
+      , testCase "1.2.3-1+1 is SemVer" $ check $ isSemVer <$> parseV "1.2.3-1+1"
+      , testCase "1.2.3r1 is Version" $ check $ isVersion <$> parseV "1.2.3r1"
+      , testCase "0.25-2 is Version" $ check $ isVersion <$> parseV "0.25-2" 
+      , testCase "1.2.3+1-1 is Mess" $ check $ isMess <$> parseV "1.2.3+1-1"
+      , testCase "1:1.2.3-1 is Mess" $ check $ isMess <$> parseV "1:1.2.3-1"
+      , testCase "000.007-1 is Mess" $ check $ isMess <$> parseV "000.007-1"
+      , testCase "20.26.1_0-2 is Mess" $ check $ isMess <$> parseV "20.26.1_0-2"
+      ]
+    , testGroup "Isomorphisms" $
+      map (\s -> testCase (unpack s) $ isomorph s) $ goodSemVs ++ goodVers ++ messes
+    , testGroup "Comparisons" $
+      [ testCase "1.2.2r1-1 < 1.2.3-1"   $ comp parseV "1.2.2r1-1" "1.2.3-1"
+      , testCase "1.2.3-1   < 1.2.4r1-1" $ comp parseV "1.2.3-1" "1.2.4r1-1"
+      , testCase "1.2.3-1   < 2+0007-1"  $ comp parseV "1.2.3-1" "2+0007-1"
+      , testCase "1.2.3r1-1 < 2+0007-1"  $ comp parseV "1.2.3r1-1" "2+0007-1"
+      ]
+    ]
+  ]
+
+-- | Does pretty-printing return a Versioning to its original form?
+isomorph :: Text -> Assertion
+isomorph t = Right t @=? (prettyV <$> parseV t)
+
+-- | Does pretty-printing return a Version to its original form?
+isomorphV :: Text -> Assertion
+isomorphV t = Right t @=? (prettyVer <$> version t)
+
+-- | Does pretty-printing return a SemVer to its original form?
+isomorphSV :: Text -> Assertion
+isomorphSV t = Right t @=? (prettySemVer <$> semver t)
+
+isomorphM :: Text -> Assertion
+isomorphM t =  Right t @=? (prettyMess <$> mess t)
+
+comp :: Ord b => (Text -> Either a b) -> Text -> Text -> Assertion
+comp f a b = check $ (<) <$> f a <*> f b
+
+check :: Either a Bool -> Assertion
+check = assert . either (const False) id
+
+isSemVer :: Versioning -> Bool
+isSemVer (Ideal _) = True
+isSemVer _ = False
+
+isVersion :: Versioning -> Bool
+isVersion (General _) = True
+isVersion _ = False
+
+isMess :: Versioning -> Bool
+isMess (Complex _) = True
+isMess _ = False
+
+
+{-}
+-- Need to submit patch for these, as well as Maybe instance.
+assertRight :: String -> Either a b -> Assertion
+assertRight _ (Right _)  = return ()
+assertRight msg (Left _) = assertFailure msg
+
+instance Assertable (Either a b) where
+  assert = assertRight ""
+
+assertMaybe :: String -> Maybe a -> Assertion
+assertMaybe _ (Just _)  = return ()
+assertMaybe msg Nothing = assertFailure msg
+
+instance Assertable (Maybe a) where
+  assert = assertMaybe ""
+-}
+
+main :: IO ()
+main = defaultMain suite
diff --git a/versions.cabal b/versions.cabal
new file mode 100644
--- /dev/null
+++ b/versions.cabal
@@ -0,0 +1,65 @@
+name:                versions
+version:             1.0.0
+synopsis:            Types and parsers for software version numbers.
+description:         A library for parsing and comparing software version numbers.
+                     .
+                     We like to give version numbers to our software in a myriad of different
+                     ways. Some ways follow strict guidelines for incrementing and comparison.
+                     Some follow conventional wisdom and are generally self-consistent.
+                     Some are just plain asinine. This library provides a means of parsing
+                     and comparing /any/ style of versioning, be it a nice Semantic Version
+                     like this:
+                     .
+                     > 1.2.3-r1+git123
+                     .
+                     ...or a monstrosity like this:
+                     .
+                     > 2:10.2+0.0093r3+1-1
+                     .
+                     Please switch to <http://semver.org Semantic Versioning> if you
+                     aren't currently using it. It provides consistency in version
+                     incrementing and has the best constraints on comparisons.
+
+license:             BSD3
+license-file:        LICENSE
+author:              Colin Woodbury
+maintainer:          colingw@gmail.com
+-- copyright:           
+category:            Data
+build-type:          Simple
+-- extra-source-files:  
+cabal-version:       >=1.10
+
+source-repository head
+  type:     git
+  location: git://github.com/fosskers/haskell-versions.git
+
+library
+  exposed-modules:     Data.Versions
+  -- other-modules:       
+  other-extensions:    OverloadedStrings
+  build-depends:       base >=4.8 && <4.9
+                     , parsec >=3.1 && <3.2
+                     , semigroups >= 0.16.2.2
+                     , text >=1.2 && <1.3
+                     , text-show >= 2
+  -- hs-source-dirs:      
+  default-language:    Haskell2010
+
+test-suite versions-test
+  type:                exitcode-stdio-1.0
+  other-extensions:    OverloadedStrings
+
+  build-depends:       base >=4.8 && <4.9
+                     , either >= 4.4.1
+                     , extra >= 1.4.1
+                     , semigroups >= 0.16.2.2
+                     , tasty >= 0.10.1.2
+                     , tasty-hunit >= 0.9.2
+                     , text >=1.2 && <1.3
+                     , text-show >= 2
+                     , versions
+
+  hs-source-dirs:      test
+  main-is:             Test.hs
+  default-language:    Haskell2010
