haskell-opaleye icon indicating copy to clipboard operation
haskell-opaleye copied to clipboard

Mention in the docs that it's awkward to have to cast to nullable to use JSON operators

Open tomjaguarpaw opened this issue 6 years ago • 4 comments

The JSON operators basically take nullable JSON things. This is awkward if you have a non-nullable one. We should at least mention this in the docs.

The proper fix is here: https://github.com/tomjaguarpaw/haskell-opaleye/issues/97

A hacky fix is here: https://github.com/tomjaguarpaw/haskell-opaleye/issues/350#issuecomment-343726689

tomjaguarpaw avatar Nov 12 '17 10:11 tomjaguarpaw

@tomjaguarpaw can you please assign this to Kahlil? He's struggled quite a lot with the Opaleye JSON operators and should be in a position to write better docs to help other first-time users.

saurabhnanda avatar Nov 12 '17 10:11 saurabhnanda

@kahlil29 is welcome to work on this, though for some reason I can't formally assign him in the UI.

tomjaguarpaw avatar Nov 12 '17 10:11 tomjaguarpaw

@tomjaguarpaw @kahlil29 was about to pick this up, but we just had an offline discussion about why do JSON fields need to be nullable for the operators to work? What's the rationale for having this in the first place?

saurabhnanda avatar Nov 15 '17 07:11 saurabhnanda

Look at the Postgres operator ->, for example. When we translate it to Opaleye we want it to be useable at all of these types

(.->) :: Column           PGJson   -> Column k -> Column (Nullable PGJSon)
(.->) :: Column (Nullable PGJson)  -> Column k -> Column (Nullable PGJSon)
(.->) :: Column           PGJsonb  -> Column k -> Column (Nullable PGJSonb)
(.->) :: Column (Nullable PGJsonb) -> Column k -> Column (Nullable PGJSonb)

The approach we currently take is a bit of a compromise. We define

class PGIsJson a

instance PGIsJson T.PGJson
instance PGIsJson T.PGJsonb

and implement

(.->) :: (PGIsJson a, PGJsonIndex k)
      => Column (C.Nullable a) -- ^
      -> Column k -- ^ key or index
      -> Column (C.Nullable a)

This only gets us (.->) at two of the four types we wanted but it's OK because for the other two we can just use fromNullable directly.

tomjaguarpaw avatar Nov 16 '17 11:11 tomjaguarpaw