TH: quote both an imported name and its computed value
This is a follow-up of the discussion on haskell-cafe: https://mail.haskell.org/pipermail/haskell-cafe/2021-February/133368.html
I have the following kind of template haskell code:
module Bar where
bar :: String
bar = "whatever"
module Foo where
foo :: String -> Name -> Q [Dec]
foo str name = ...
module FooBar where
import Foo
import Bar
foo bar 'bar
It works great as in foo
I can use both bar's Name
and bar's value
computed at compile time.
But it's unsafe for my purpose because a user could call foo "fakeBarValue" 'bar
.
I would like a way to quote both the name and the value of an import into an unforgeable value (by the user, TH can obviously):
module TH.Internal
( Named -- constructor not exported
, namedThing
, namedName
)
where
data Named a = Named { namedThing :: a, namedName :: Name }
module Foo where
foo :: Named String -> Q [Dec]
foo n = ...
module FooBar where
import Foo
import Bar
foo '''bar -- new kind of quote?
Or perhaps an alternative way would be to lift the stage restriction ("‘name’ is used in a top-level splice, quasi-quote, or annotation, and must be imported, not defined locally") for imported names? It would allow:
module Foo (foo) where
foo :: ImportedName -> Q [Dec]
foo name = ... $(varE name)...
module FooBar where
import Foo
import Bar
foo 'bar