Search code examples
haskellhaskell-persistent

Remove underscore from fields with generated lenses in Persistent


Let's suppose that I have a persistent type and want to project some value from this type:

share [mkPersist sqlSettings, mkMigrate "migrateAll"] [persistLowerCase|
    User
        name Text
        email Text
|]
...
getName :: Entity User -> Text
getName (Entity uid vals) = userName vals

The problem is, if I generate lenses for said type, using mkPersist sqlSettings {mpsGenerateLenses = True}, I'll need to add a underscore in the beginning of each projection function or use the lenses getter:

getName :: Entity User -> Text
getName (Entity uid vals) = _userName vals

getName' :: Entity User -> Text
getName (Entity uid vals) = vals ^. userName
  • Firstly, how can I revert that to the default, userName vals, and add the underscore to use the lenses getter, vals ^. _userName?
  • Secondly, why is this this way and not the other way around?

Solution

  • Firstly, how can I revert that to the default, userName vals, and add the underscore to use the lenses getter, vals ^. _userName?

    Database.Persist.TH does not offer that option (to see what it might look like if it existed, cf. Control.Lens.TH), so, assuming that you won't fork the library over this, there doesn't seem to be a way. (By the way, looking for mpsGenerateLenses in the source will show exactly where the underscores are added.)

    Secondly, why is this this way and not the other way around?

    Presumably because the library assumes that if you generate the lenses you will use them everywhere instead of the record accessors/labels, including for getting the value of the field. The only cosmetic suggestion I have is that, if the change of writing order from _userName vals to vals ^. userName bothers you, you might prefer using view rather than (^.), as in view userName vals.