I have a medium-sized codebase (about 25K LOC) with around 200 different data types, and I want to find all the types which do not have a ToJSON
instance. Curious if anyone has ideas for an automated way to accomplish that — perhaps using the GHC API somehow? Because of things like standalone deriving, orphan instances, etc., a simple syntactic analysis is probably not going to cut it.
You might be able to put something together using hiedb
(which produces a SQLite database). The result of .hie
files would definitely be my choice for the source of this information.
I’ve managed to install hiedb
and index all the relevant .hie
files into a database. I can use the hiedb
tool to list the source locations of all the references to ToJSON
, or find the definition of any type; I also figured out how to directly query a list of all the defined data types from the database. I haven’t yet figured out how to extract information about type class instances, but I’ll keep playing with it.
Do report back to us, this sounds like a great use case
There exists the function reifyInstances :: Name -> [Type] -> Q [InstanceDec]
(Language.Haskell.TH) which can return all instances of a class which are in scope.
You could use it to view all FromJSON
instances in your project if you run it in a module which imports all other modules. However, it does not seem like you can get datatypes which do not satisfy an instance with this method. Maybe you can combine this with the hiedb
approach; query all defined data types with hiedb
and then subtract the ones found with reifyInstances
.
GHCi gives you all instances of a class via :i
. Maybe that’s a starting point too.
A dumb solution would be to generate a source file that imports all the types, and then use toJSON
on an undefined
of each type; try to compile that source file, and the error messages will tell you which types don’t have JSON instances.