I was surprised to find out the expression quasiquoter [| |]
accepts expressions that don’t typecheck, see the ghci interaction below :
λ> runQ [| \x -> head x : head x |]
LamE [VarP x_20] (InfixE (Just (AppE (VarE GHC.List.head) (VarE x_20))) (ConE GHC.Types.:) (Just (AppE (VarE GHC.List.head) (VarE x_20))))
Is there a way to restrict quasiquoters to erroring out when their argument doesn’t typecheck, or to get an AST from a later compiler stage, after typechecking?
My aim is : given the AST of a well-typed expression, produce new top-level declarations at compile time, e.g. Q [Dec]
. Is this possible?