[Haskell-cafe] Using Haskell types in a database

Nikita Karetnikov nikita at karetnikov.org
Tue Feb 10 14:29:55 UTC 2015

Suppose I need to represent a user in a database.  I could make a table
like this one (using Yesod's config/models syntax):

  name        Text
  email       Text     Maybe
  is_verified Bool     default=false
  last_login  UTCTime  default=now()

Instead, it would be better to do the following, so I couldn't swap name
and email by accident or feed a wrong value to is_verified and

  name         UserName
  email        UserEmail v   Maybe
  last_login   UserLastLogin


newtype UserName      = UserName Text deriving (Show, Read)
derivePersistField "UserName"
newtype UserLastLogin = UserLastLogin UTCTime deriving (Show, Read)
derivePersistField "UserLastLogin"

data Verified
data Unverified
newtype UserEmail v = UserEmail Text deriving (Show, Read)
derivePersistField "UserEmail"

(So I could define functions like

sendAnnouncement :: UserEmail Verified   -> IO ()
sendVerification :: UserEmail Unverified -> IO ())

The Haskell part is not new and has been successfully used in the large
(see http://code.haskell.org/~dons/talks/dons-google-2015-01-27.pdf,
pp. 17--21), but I wonder whether it's reasonable in the database layer.

The first table will be mapped to this in PostgreSQL:

  name        character varying        not null
  email       character varying
  is_verified boolean                  not null default false
  last_login  timestamp with time zone not null default now()

while the second will use character varying for everything.

The only downsides of the latter approach I can think of:

1. You can no longer rely on the database to ensure (basic) type safety,
   so everything needs to be done in the Haskell layer.  Otherwise, you
   will get runtime errors.

2. I haven't benchmarked this, but I assume that comparing, say,
   booleans should be faster than comparing varchars.

So, is it worth it in practice?  Do I need to worry about these issues?
And are there any other problems?
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 818 bytes
Desc: not available
URL: <http://www.haskell.org/pipermail/haskell-cafe/attachments/20150210/85d8fafc/attachment.sig>

More information about the Haskell-Cafe mailing list