Search code examples
haskellyesodtemplate-haskell

Can template-haskell be used to generate quasi-quotes?


A project that I'm currently working on makes extensive use of persistent. Instead of persistent's quasi-quoted syntax to specify models, I would like to use json. Right now, I use a script to generate the quasiquote which persistent expects using simple-templates. That adds a rather awkward step in the workflow. Can this be avoided using template-haskell?

This is currently generated by the script :

-- File : ProjSpecific.Models

share [mkPersist sqlSettings, mkMigrate "migrateAll"]
[persistLowerCase|
Person
    name String
    age Int Maybe
    deriving Show
BlogPost
    title String
    authorId PersonId
    deriving Show
|]

This is how I would ideally like to do it :

-- File : ProjSpecific.Config

import Data.Aeson.QQ
import Data.Aeson (Value)

models :: Value
models = [aesonQQ| {some json encoding of above models} |]

And

-- File : ProjSpecific.Models

complie time logic to generate the persistent models

Any ideas on how this can be done or is there a better way to accompilsh what I'm trying to do?


Solution

  • Yes, it should be relatively painless. You'd essentially want to use the quoteExp field from persistLowerCase, which will give you a function of type String -> Q Exp. Use your preprocessor to convert JSON into the expected syntax, and then pass it to the function.