hasql-check 0.5.0.0 → 0.5.1.0
raw patch · 8 files changed
+1197/−319 lines, 8 filesPVP ok
version bump matches the API change (PVP)
API changes (from Hackage documentation)
+ Hasql.Check: parseForkStmt :: Text -> Either String PreparableStmt
+ Hasql.Check.Inferred: Slots :: Params p -> Slots (ps :: [Symbol]) (ls :: [[Symbol]]) (hs :: [Type]) p
+ Hasql.Check.Inferred: Target :: Row r -> Target (cs :: [Symbol]) (ls :: [[Symbol]]) (hs :: [Type]) r
+ Hasql.Check.Inferred: [slotsParams] :: Slots (ps :: [Symbol]) (ls :: [[Symbol]]) (hs :: [Type]) p -> Params p
+ Hasql.Check.Inferred: [targetRow] :: Target (cs :: [Symbol]) (ls :: [[Symbol]]) (hs :: [Type]) r -> Row r
+ Hasql.Check.Inferred: class HaskellColumns (hs :: [Type])
+ Hasql.Check.Inferred: class HaskellParams (hs :: [Type])
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j, k)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j, k)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j, k, l)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j, k, l)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j, k, l, m)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j, k, l, m)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q, Hasql.Check.Inferred.Column r) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q, Hasql.Check.Inferred.Column r) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q, Hasql.Check.Inferred.Column r, Hasql.Check.Inferred.Column s) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q, Hasql.Check.Inferred.Column r, Hasql.Check.Inferred.Column s) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q, Hasql.Check.Inferred.Column r, Hasql.Check.Inferred.Column s, Hasql.Check.Inferred.Column t) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q, Hasql.Check.Inferred.Column r, Hasql.Check.Inferred.Column s, Hasql.Check.Inferred.Column t) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q, Hasql.Check.Inferred.Column r, Hasql.Check.Inferred.Column s, Hasql.Check.Inferred.Column t, Hasql.Check.Inferred.Column u) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q, Hasql.Check.Inferred.Column r, Hasql.Check.Inferred.Column s, Hasql.Check.Inferred.Column t, Hasql.Check.Inferred.Column u) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q, Hasql.Check.Inferred.Column r, Hasql.Check.Inferred.Column s, Hasql.Check.Inferred.Column t, Hasql.Check.Inferred.Column u, Hasql.Check.Inferred.Column v) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q, Hasql.Check.Inferred.Column r, Hasql.Check.Inferred.Column s, Hasql.Check.Inferred.Column t, Hasql.Check.Inferred.Column u, Hasql.Check.Inferred.Column v) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q, Hasql.Check.Inferred.Column r, Hasql.Check.Inferred.Column s, Hasql.Check.Inferred.Column t, Hasql.Check.Inferred.Column u, Hasql.Check.Inferred.Column v, Hasql.Check.Inferred.Column w) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q, Hasql.Check.Inferred.Column r, Hasql.Check.Inferred.Column s, Hasql.Check.Inferred.Column t, Hasql.Check.Inferred.Column u, Hasql.Check.Inferred.Column v, Hasql.Check.Inferred.Column w) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q, Hasql.Check.Inferred.Column r, Hasql.Check.Inferred.Column s, Hasql.Check.Inferred.Column t, Hasql.Check.Inferred.Column u, Hasql.Check.Inferred.Column v, Hasql.Check.Inferred.Column w, Hasql.Check.Inferred.Column x) => Hasql.Check.Inferred.Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x)
+ Hasql.Check.Inferred: instance (Hasql.Check.Inferred.Column a, Hasql.Check.Inferred.Column b, Hasql.Check.Inferred.Column c, Hasql.Check.Inferred.Column d, Hasql.Check.Inferred.Column e, Hasql.Check.Inferred.Column f, Hasql.Check.Inferred.Column g, Hasql.Check.Inferred.Column h, Hasql.Check.Inferred.Column i, Hasql.Check.Inferred.Column j, Hasql.Check.Inferred.Column k, Hasql.Check.Inferred.Column l, Hasql.Check.Inferred.Column m, Hasql.Check.Inferred.Column n, Hasql.Check.Inferred.Column o, Hasql.Check.Inferred.Column p, Hasql.Check.Inferred.Column q, Hasql.Check.Inferred.Column r, Hasql.Check.Inferred.Column s, Hasql.Check.Inferred.Column t, Hasql.Check.Inferred.Column u, Hasql.Check.Inferred.Column v, Hasql.Check.Inferred.Column w, Hasql.Check.Inferred.Column x) => Hasql.Check.Inferred.Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x)
+ Hasql.Check.Inferred: instance Hasql.Check.Inferred.HaskellColumns hs
+ Hasql.Check.Inferred: instance Hasql.Check.Inferred.HaskellParams hs
+ Hasql.Check.Inferred: newtype Slots (ps :: [Symbol]) (ls :: [[Symbol]]) (hs :: [Type]) p
+ Hasql.Check.Inferred: newtype Target (cs :: [Symbol]) (ls :: [[Symbol]]) (hs :: [Type]) r
+ Hasql.Check.Inferred: resultlessWith :: forall p (ps :: [Symbol]) (pl :: [[Symbol]]) (ph :: [Type]). (PostgresParams ps, PostgresParamLabels pl, HaskellParams ph) => Template -> Slots ps pl ph p -> Statement p ()
+ Hasql.Check.Inferred: rowsAffected :: forall p (ps :: [Symbol]) (pl :: [[Symbol]]). (Params p, ps ~ PgParamTypes p, PostgresParams ps, pl ~ PgParamLabels p, PostgresParamLabels pl) => Template -> Statement p Int64
+ Hasql.Check.Inferred: rowsAffectedWith :: forall p (ps :: [Symbol]) (pl :: [[Symbol]]) (ph :: [Type]). (PostgresParams ps, PostgresParamLabels pl, HaskellParams ph) => Template -> Slots ps pl ph p -> Statement p Int64
+ Hasql.Check.Inferred: slotsAp :: forall (ps :: [Symbol]) (ls :: [[Symbol]]) (hs :: [Type]) p (qs :: [Symbol]) (ms :: [[Symbol]]) (is :: [Type]). Slots ps ls hs p -> Slots qs ms is p -> Slots (Append ps qs) (Append ls ms) (Append hs is) p
+ Hasql.Check.Inferred: slotsNone :: Slots ('[] :: [Symbol]) ('[] :: [[Symbol]]) ('[] :: [Type]) p
+ Hasql.Check.Inferred: slotsOne :: Column a => (p -> a) -> Slots '[PgColumnType a] '[PgColumnLabels a] '[a] p
+ Hasql.Check.Inferred: statementRow :: forall p r a (ps :: [Symbol]) (cs :: [Symbol]) (pl :: [[Symbol]]) (cl :: [[Symbol]]) (ph :: [Type]). (Row r, cs ~ PgColumnTypes r, cl ~ PgColumnLabelLists r, PostgresParams ps, PostgresColumns cs, PostgresParamLabels pl, PostgresColumnLabels cl, HaskellParams ph) => Template -> Slots ps pl ph p -> (Row r -> Result a) -> Statement p a
+ Hasql.Check.Inferred: statementWith :: forall p r a (ps :: [Symbol]) (cs :: [Symbol]) (pl :: [[Symbol]]) (cl :: [[Symbol]]) (ph :: [Type]) (ch :: [Type]). (PostgresParams ps, PostgresColumns cs, PostgresParamLabels pl, PostgresColumnLabels cl, HaskellParams ph, HaskellColumns ch) => Template -> Slots ps pl ph p -> Target cs cl ch r -> (Row r -> Result a) -> Statement p a
+ Hasql.Check.Inferred: targetAp :: forall (cs :: [Symbol]) (ls :: [[Symbol]]) (hs :: [Type]) a b (ds :: [Symbol]) (ms :: [[Symbol]]) (is :: [Type]). Target cs ls hs (a -> b) -> Target ds ms is a -> Target (Append cs ds) (Append ls ms) (Append hs is) b
+ Hasql.Check.Inferred: targetColumn :: Column a => Target '[PgColumnType a] '[PgColumnLabels a] '[a] a
+ Hasql.Check.Inferred: targetPure :: r -> Target ('[] :: [Symbol]) ('[] :: [[Symbol]]) ('[] :: [Type]) r
+ Hasql.Check.Inferred.TH: Parsed :: Template -> [Slot] -> Int -> [Int] -> Maybe [Tgt] -> Parsed
+ Hasql.Check.Inferred.TH: Slot :: Int -> Maybe Text -> Slot
+ Hasql.Check.Inferred.TH: TgtApply :: Text -> [Tgt] -> Tgt
+ Hasql.Check.Inferred.TH: TgtColumn :: Tgt
+ Hasql.Check.Inferred.TH: TgtRecord :: Text -> [(Text, Tgt)] -> Tgt
+ Hasql.Check.Inferred.TH: [parsedArity] :: Parsed -> Int
+ Hasql.Check.Inferred.TH: [parsedSlots] :: Parsed -> [Slot]
+ Hasql.Check.Inferred.TH: [parsedTargets] :: Parsed -> Maybe [Tgt]
+ Hasql.Check.Inferred.TH: [parsedTemplate] :: Parsed -> Template
+ Hasql.Check.Inferred.TH: [parsedUsed] :: Parsed -> [Int]
+ Hasql.Check.Inferred.TH: data Parsed
+ Hasql.Check.Inferred.TH: data Slot
+ Hasql.Check.Inferred.TH: data Tgt
+ Hasql.Check.Inferred.TH: instance GHC.Classes.Eq Hasql.Check.Inferred.TH.Parsed
+ Hasql.Check.Inferred.TH: instance GHC.Classes.Eq Hasql.Check.Inferred.TH.Slot
+ Hasql.Check.Inferred.TH: instance GHC.Classes.Eq Hasql.Check.Inferred.TH.Tgt
+ Hasql.Check.Inferred.TH: instance GHC.Internal.Show.Show Hasql.Check.Inferred.TH.Parsed
+ Hasql.Check.Inferred.TH: instance GHC.Internal.Show.Show Hasql.Check.Inferred.TH.Slot
+ Hasql.Check.Inferred.TH: instance GHC.Internal.Show.Show Hasql.Check.Inferred.TH.Tgt
+ Hasql.Check.Inferred.TH: parsed :: Text -> Either String Parsed
+ Hasql.Check.Inferred.TH: rowsAffectedStatement :: QuasiQuoter
Files
- ChangeLog.md +23/−0
- hasql-check.cabal +7/−1
- src/Hasql/Check.hs +27/−23
- src/Hasql/Check/Inferred.hs +655/−154
- src/Hasql/Check/Inferred/Quote.hs +60/−59
- src/Hasql/Check/Inferred/TH.hs +257/−40
- test/Inferred/Shapes.hs +144/−0
- test/Main.hs +24/−42
ChangeLog.md view
@@ -1,5 +1,28 @@ # Changelog +## 0.5.1.0++The quoters of `Hasql.Check.Inferred.TH` now take the Haskell targets and+`$1.$field` param fields of the `kronor-syntax` flag: the quoter builds the+row decoder and the parameter encoder from them, and a record's columns are+read at the type of the field each one names, so a statement may write the+fields in any order. Add `rowsAffectedStatement`, and widen the tuple+instances from eight components to twenty-four.++`Target` and `Slots` carry the Postgres and the Haskell types at the type+level, as `PostgresParams`, `PostgresColumns`, `HaskellParams` and+`HaskellColumns`, so `hasql-check-hie` finds them in the `.hie` files.++`--inferred` annotated the statement as written rather than as the quoter+sends it, so a statement that writes its placeholders out of order, such as+`set name = $2 where id = $1`, had its parameters' types paired with the+wrong ones and was rejected. It now lowers the statement first, and reports+an unused parameter by the number the statement was written with.++Known gap: a param field reaches its type through `HasField`, whose+`PgColumnType` stays stuck in the recorded type, so such a statement is+reported as having no concrete type rather than being checked.+ ## 0.5.0.0 Add `Hasql.Check.Inferred.TH`: quoters for statements without annotations,
hasql-check.cabal view
@@ -1,6 +1,6 @@ cabal-version: 3.0 name: hasql-check-version: 0.5.0.0+version: 0.5.1.0 synopsis: Check hasql-th statements against a live PostgreSQL schema description: Finds the hasql-th quasiquotes in Haskell source files and PREPAREs each@@ -223,13 +223,19 @@ test-suite hasql-check-test type: exitcode-stdio-1.0 main-is: Main.hs+ other-modules: Inferred.Shapes hs-source-dirs: test default-language: GHC2021 default-extensions: BlockArguments DataKinds+ DerivingVia LambdaCase+ OverloadedRecordDot OverloadedStrings+ QuasiQuotes+ TemplateHaskell+ UndecidableInstances ghc-options: -Wall -threaded -rtsopts -with-rtsopts=-N
src/Hasql/Check.hs view
@@ -1,13 +1,14 @@ {-# LANGUAGE CPP #-} --- |--- Module : Hasql.Check--- Copyright : (c) 2022 Kronor.io------ License : BSD-3-Clause--- Maintainer : lorenzo@kronor.io--- Stability : experimental--- Portability : GHC+{- |+Module : Hasql.Check+Copyright : (c) 2022 Kronor.io++License : BSD-3-Clause+Maintainer : lorenzo@kronor.io+Stability : experimental+Portability : GHC+-} module Hasql.Check where import Data.ByteString (ByteString)@@ -18,30 +19,35 @@ import Pqi qualified import Prelude ---- | Turn the SQL text inside a quasiquote into the SQL the splice actually--- sends to Postgres, mirroring @Hasql.TH.expPreparableStmtAstParser@ composed--- with @Hasql.TH.Extraction.Exp.sql@ line for line. Rendering at 'mempty'--- drops the nullability markers.+{- | Turn the SQL text inside a quasiquote into the SQL the splice actually+sends to Postgres, mirroring @Hasql.TH.expPreparableStmtAstParser@ composed+with @Hasql.TH.Extraction.Exp.sql@ line for line. Rendering at 'mempty'+drops the nullability markers.+-} renderSql :: Text -> Either String ByteString renderSql sql = renderStmt <$> parseStmt sql - -- | The statement in a quasiquote, as the splice would render it. parseStmt :: Text -> Either String Ast.PreparableStmt parseStmt sql = either (Left . Text.unpack) (Right . lowerAst) (Ast.parse quoterSettings sql) +{- | A statement in plain SQL, as Postgres reads it, whatever syntax this+build takes in hasql-th's quotes: for the quoters of+"Hasql.Check.Inferred.TH", and the annotated statements that stand for+theirs, which hasql-th's nullability markers may annotate. --- | A statement in plain SQL, as Postgres reads it, whatever syntax this--- build takes in hasql-th's quotes: for the quoters of--- "Hasql.Check.Inferred.TH", and the annotated statements that stand for--- theirs, which hasql-th's nullability markers may annotate.------ Not lowered: Kronor's fork numbers the placeholders afresh as it lowers--- its parameter fields, which would turn a lone @$2@ into @$1@.+Not lowered: Kronor's fork numbers the placeholders afresh as it lowers+its parameter fields, which would turn a lone @$2@ into @$1@.+-} parsePlainStmt :: Bool -> Text -> Either String Ast.PreparableStmt parsePlainStmt markers sql = either (Left . Text.unpack) Right (Ast.parse (Ast.nullabilityMarkers markers) sql) +{- | A statement in whatever syntax this build's quotes take, left exactly as+parsed: the quoters of "Hasql.Check.Inferred.TH" read Kronor's Haskell+targets off it, and lower it themselves.+-}+parseForkStmt :: Text -> Either String Ast.PreparableStmt+parseForkStmt sql = either (Left . Text.unpack) Right (Ast.parse quoterSettings sql) renderStmt :: Ast.PreparableStmt -> ByteString renderStmt = Text.encodeUtf8 . Ast.toText mempty@@ -81,11 +87,9 @@ #endif - prepare :: Pqi.Connection -> Text -> Text -> IO (Either String ()) prepare conn stmtName unParsedStmt = either (pure . Left) (prepareStmt conn (Text.encodeUtf8 stmtName)) (parseStmt unParsedStmt)- -- | Prepare a statement under a name, returning the server's error if it fails. prepareStmt :: Pqi.Connection -> ByteString -> Ast.PreparableStmt -> IO (Either String ())
src/Hasql/Check/Inferred.hs view
@@ -5,28 +5,29 @@ -- statement is used, which is what puts them in the .hie files. {-# OPTIONS_GHC -Wno-redundant-constraints #-} --- |--- Module : Hasql.Check.Inferred--- Copyright : (c) 2026 Kronor.io------ License : BSD-3-Clause--- Maintainer : lorenzo@kronor.io--- Stability : experimental--- Portability : GHC------ Statements whose encoders and decoders are chosen by the Haskell types they--- are used with, for the quoters in "Hasql.Check.Inferred.TH".------ Each Haskell type stands for one Postgres type, named at the type level by--- 'PgType', and the statement sends the annotations hasql-th would ask for:--- @select email from customer@ used as a @Statement Int64 Text@ is sent as--- @select (email)::text from customer@. A @varchar@ column is then read as--- 'Text', and an @int4@ one as 'Int64', where an exact decoder would fail.------ Because the names are types, GHC works them out where a statement is used,--- and records them in its @.hie@ files, where @hasql-check-hie@ reads them:--- a @newtype@ deriving 'Value' is checked as the type it wraps, with no list--- of types to keep in step.+{- |+Module : Hasql.Check.Inferred+Copyright : (c) 2026 Kronor.io++License : BSD-3-Clause+Maintainer : lorenzo@kronor.io+Stability : experimental+Portability : GHC++Statements whose encoders and decoders are chosen by the Haskell types they+are used with, for the quoters in "Hasql.Check.Inferred.TH".++Each Haskell type stands for one Postgres type, named at the type level by+'PgType', and the statement sends the annotations hasql-th would ask for:+@select email from customer@ used as a @Statement Int64 Text@ is sent as+@select (email)::text from customer@. A @varchar@ column is then read as+'Text', and an @int4@ one as 'Int64', where an exact decoder would fail.++Because the names are types, GHC works them out where a statement is used,+and records them in its @.hie@ files, where @hasql-check-hie@ reads them:+a @newtype@ deriving 'Value' is checked as the type it wraps, with no list+of types to keep in step.+-} module Hasql.Check.Inferred ( -- * Types Value (..),@@ -52,12 +53,29 @@ PostgresParams, PostgresColumns, + -- * Targets and slots, for the quoters' own statements+ Target (..),+ HaskellColumns,+ HaskellParams,+ targetPure,+ targetColumn,+ targetAp,+ Slots (..),+ slotsNone,+ slotsOne,+ slotsAp,+ -- * Statements Template (..), Wrapped (..), Piece (..), statement,+ statementWith,+ statementRow, resultless,+ resultlessWith,+ rowsAffected,+ rowsAffectedWith, render, ) where @@ -84,151 +102,131 @@ import PostgresqlSyntax qualified as Ast import Prelude +{- | A Haskell type, and the Postgres type it is sent and read as. --- | A Haskell type, and the Postgres type it is sent and read as.------ A @newtype@ can derive the instance of the type it wraps:------ > newtype Email = Email Text--- > deriving newtype (Value)+A @newtype@ can derive the instance of the type it wraps:++> newtype Email = Email Text+> deriving newtype (Value)+-} class Value a where- -- | The Postgres type's name, as an annotation would give it: @"int8"@,- -- @"public.payment_state"@.+ {- | The Postgres type's name, as an annotation would give it: @"int8"@,+ @"public.payment_state"@.+ -} type PgType a :: Symbol - -- | The labels of the Postgres enum it is, if it is one, for the checker. type PgLabels a :: [Symbol] - type PgLabels a = '[] - encodeValue :: E.Value a decodeValue :: D.Value a - -- | The name of a type's Postgres type.-typeName :: forall a. KnownSymbol (PgType a) => Text+typeName :: forall a. (KnownSymbol (PgType a)) => Text typeName = Text.pack (symbolVal (Proxy @(PgType a))) - instance Value Bool where type PgType Bool = "bool" encodeValue = E.bool decodeValue = D.bool - instance Value Int16 where type PgType Int16 = "int2" encodeValue = E.int2 decodeValue = D.int2 - instance Value Int32 where type PgType Int32 = "int4" encodeValue = E.int4 decodeValue = D.int4 - instance Value Int64 where type PgType Int64 = "int8" encodeValue = E.int8 decodeValue = D.int8 - instance Value Float where type PgType Float = "float4" encodeValue = E.float4 decodeValue = D.float4 - instance Value Double where type PgType Double = "float8" encodeValue = E.float8 decodeValue = D.float8 - instance Value Scientific where type PgType Scientific = "numeric" encodeValue = E.numeric decodeValue = D.numeric - instance Value Text where type PgType Text = "text" encodeValue = E.text decodeValue = D.text - instance Value ByteString where type PgType ByteString = "bytea" encodeValue = E.bytea decodeValue = D.bytea - instance Value UUID where type PgType UUID = "uuid" encodeValue = E.uuid decodeValue = D.uuid - instance Value Day where type PgType Day = "date" encodeValue = E.date decodeValue = D.date - instance Value LocalTime where type PgType LocalTime = "timestamp" encodeValue = E.timestamp decodeValue = D.timestamp - instance Value UTCTime where type PgType UTCTime = "timestamptz" encodeValue = E.timestamptz decodeValue = D.timestamptz - instance Value TimeOfDay where type PgType TimeOfDay = "time" encodeValue = E.time decodeValue = D.time - instance Value Aeson.Value where type PgType Aeson.Value = "jsonb" encodeValue = E.jsonb decodeValue = D.jsonb +{- | A type sent and read as the one it wraps, under the name of a Postgres+domain over it, so that Postgres checks the domain's constraints: --- | A type sent and read as the one it wraps, under the name of a Postgres--- domain over it, so that Postgres checks the domain's constraints:------ > newtype Cents = Cents Int64--- > deriving (Value) via Domain "cents" Int64+> newtype Cents = Cents Int64+> deriving (Value) via Domain "cents" Int64+-} newtype Domain (name :: Symbol) a = Domain a --instance Value a => Value (Domain name a) where+instance (Value a) => Value (Domain name a) where type PgType (Domain name a) = name type PgLabels (Domain name a) = PgLabels a encodeValue = (\(Domain a) -> a) >$< encodeValue decodeValue = Domain <$> decodeValue +{- | A Haskell enumeration sent and read as a Postgres enum, by the enum's+name: each constructor, which takes no fields, as the label of the same+name. --- | A Haskell enumeration sent and read as a Postgres enum, by the enum's--- name: each constructor, which takes no fields, as the label of the same--- name.------ > data PaymentState = PENDING | PAID--- > deriving stock (Generic)--- > deriving (Value) via PgEnum "payment_state" PaymentState------ The checker compares the labels with the enum's in the database.-newtype PgEnum (name :: Symbol) a = PgEnum a+> data PaymentState = PENDING | PAID+> deriving stock (Generic)+> deriving (Value) via PgEnum "payment_state" PaymentState +The checker compares the labels with the enum's in the database.+-}+newtype PgEnum (name :: Symbol) a = PgEnum a instance (KnownSymbol name, Generic a, GEnum (Rep a)) => Value (PgEnum name a) where type PgType (PgEnum name a) = name@@ -236,11 +234,11 @@ encodeValue = uncurry E.enum (qualifiedName (Text.pack (symbolVal (Proxy @name)))) (\(PgEnum a) -> glabel (from a)) decodeValue = uncurry D.enum (qualifiedName (Text.pack (symbolVal (Proxy @name)))) (\t -> PgEnum . to <$> lookup t gvalues) ---- | A type's schema, if its name has one, and its own name, as the--- identifiers they are: the name is SQL, as a cast takes it, so a quoted--- part is taken as it is and an unquoted one in lower case, as Postgres--- takes them.+{- | A type's schema, if its name has one, and its own name, as the+identifiers they are: the name is SQL, as a cast takes it, so a quoted+part is taken as it is and an unquoted one in lower case, as Postgres+takes them.+-} qualifiedName :: Text -> (Maybe Text, Text) qualifiedName n = case Ast.parse mempty n of Right (Ast.Typename _ (Ast.GenericTypeSimpleTypename (Ast.GenericType i attrs _)) _ _) ->@@ -257,106 +255,90 @@ Ast.QuotedIdent t -> t Ast.UnquotedIdent t -> t - -- | The constructors of an enumeration, by name. class GEnum f where gvalues :: [(Text, f p)] glabel :: f p -> Text --instance GEnum f => GEnum (D1 m f) where+instance (GEnum f) => GEnum (D1 m f) where gvalues = [(l, M1 x) | (l, x) <- gvalues] glabel (M1 x) = glabel x - instance (GEnum f, GEnum g) => GEnum (f :+: g) where gvalues = [(l, L1 x) | (l, x) <- gvalues] <> [(l, R1 x) | (l, x) <- gvalues] glabel = \case L1 x -> glabel x R1 x -> glabel x --instance KnownSymbol label => GEnum (C1 ('MetaCons label fixity strict) U1) where+instance (KnownSymbol label) => GEnum (C1 ('MetaCons label fixity strict) U1) where gvalues = [(Text.pack (symbolVal (Proxy @label)), M1 U1)] glabel _ = Text.pack (symbolVal (Proxy @label)) - -- | An enumeration's constructor names. type family ConstructorNames (f :: Type -> Type) :: [Symbol] where ConstructorNames (D1 m f) = ConstructorNames f ConstructorNames (f :+: g) = Append (ConstructorNames f) (ConstructorNames g) ConstructorNames (C1 ('MetaCons label fixity strict) U1) = '[label] - type family Append (xs :: [k]) (ys :: [k]) :: [k] where Append '[] ys = ys Append (x ': xs) ys = x ': Append xs ys ---- | A one-dimensional array, whose elements may be NULL when they are--- 'Maybe's: a @Vector Int64@ is an @int8[]@.-instance Column a => Value (Vector a) where+{- | A one-dimensional array, whose elements may be NULL when they are+'Maybe's: a @Vector Int64@ is an @int8[]@.+-}+instance (Column a) => Value (Vector a) where type PgType (Vector a) = AppendSymbol (PgColumnType a) "[]" type PgLabels (Vector a) = PgColumnLabels a encodeValue = E.foldableArray encodeColumn decodeValue = D.vectorArray decodeColumn ---- | A one-dimensional array, as a list. A 'String' is not one: 'Char' has no--- Postgres type; use 'Text'.-instance Column a => Value [a] where+{- | A one-dimensional array, as a list. A 'String' is not one: 'Char' has no+Postgres type; use 'Text'.+-}+instance (Column a) => Value [a] where type PgType [a] = AppendSymbol (PgColumnType a) "[]" type PgLabels [a] = PgColumnLabels a encodeValue = E.foldableArray encodeColumn decodeValue = D.listArray decodeColumn - -- | A column or parameter, which may be NULL when it is a 'Maybe'. class Column a where encodeColumn :: E.NullableOrNot E.Value a decodeColumn :: D.NullableOrNot D.Value a --instance {-# OVERLAPPABLE #-} Value a => Column a where+instance {-# OVERLAPPABLE #-} (Value a) => Column a where encodeColumn = E.nonNullable encodeValue decodeColumn = D.nonNullable decodeValue --instance Value a => Column (Maybe a) where+instance (Value a) => Column (Maybe a) where encodeColumn = E.nullable encodeValue decodeColumn = D.nullable decodeValue - -- | A column's enum labels, if it is one. type family PgColumnLabels (a :: Type) :: [Symbol] where PgColumnLabels (Maybe a) = PgLabels a PgColumnLabels a = PgLabels a - -- | A column's Postgres type. type family PgColumnType (a :: Type) :: Symbol where PgColumnType (Maybe a) = PgType a PgColumnType a = PgType a - -- | A statement's parameters: none, one, or a tuple of them. class Params a where params :: E.Params a - instance Params () where params = E.noParams --instance {-# OVERLAPPABLE #-} Column a => Params a where+instance {-# OVERLAPPABLE #-} (Column a) => Params a where params = E.param encodeColumn - instance (Column a, Column b) => Params (a, b) where params =- (fst >$< E.param encodeColumn)- <> (snd >$< E.param encodeColumn)-+ ((\(x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x) -> x) >$< E.param encodeColumn) instance (Column a, Column b, Column c) => Params (a, b, c) where params =@@ -364,7 +346,6 @@ <> ((\(_, x, _) -> x) >$< E.param encodeColumn) <> ((\(_, _, x) -> x) >$< E.param encodeColumn) - instance (Column a, Column b, Column c, Column d) => Params (a, b, c, d) where params = ((\(x, _, _, _) -> x) >$< E.param encodeColumn)@@ -372,7 +353,6 @@ <> ((\(_, _, x, _) -> x) >$< E.param encodeColumn) <> ((\(_, _, _, x) -> x) >$< E.param encodeColumn) - instance (Column a, Column b, Column c, Column d, Column e) => Params (a, b, c, d, e) where params = ((\(x, _, _, _, _) -> x) >$< E.param encodeColumn)@@ -381,7 +361,6 @@ <> ((\(_, _, _, x, _) -> x) >$< E.param encodeColumn) <> ((\(_, _, _, _, x) -> x) >$< E.param encodeColumn) - instance (Column a, Column b, Column c, Column d, Column e, Column f) => Params (a, b, c, d, e, f) where params = ((\(x, _, _, _, _, _) -> x) >$< E.param encodeColumn)@@ -391,7 +370,6 @@ <> ((\(_, _, _, _, x, _) -> x) >$< E.param encodeColumn) <> ((\(_, _, _, _, _, x) -> x) >$< E.param encodeColumn) - instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g) => Params (a, b, c, d, e, f, g) where params = ((\(x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)@@ -402,7 +380,6 @@ <> ((\(_, _, _, _, _, x, _) -> x) >$< E.param encodeColumn) <> ((\(_, _, _, _, _, _, x) -> x) >$< E.param encodeColumn) - instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h) => Params (a, b, c, d, e, f, g, h) where params = ((\(x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)@@ -414,7 +391,318 @@ <> ((\(_, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn) <> ((\(_, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn) +instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i) => Params (a, b, c, d, e, f, g, h, i) where+ params =+ ((\(x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn) +instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j) => Params (a, b, c, d, e, f, g, h, i, j) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k) => Params (a, b, c, d, e, f, g, h, i, j, k) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l) => Params (a, b, c, d, e, f, g, h, i, j, k, l) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m) => Params (a, b, c, d, e, f, g, h, i, j, k, l, m) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n) => Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o) => Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p) => Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q) => Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q, Column r) => Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q, Column r, Column s) => Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q, Column r, Column s, Column t) => Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q, Column r, Column s, Column t, Column u) => Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q, Column r, Column s, Column t, Column u, Column v) => Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q, Column r, Column s, Column t, Column u, Column v, Column w) => Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q, Column r, Column s, Column t, Column u, Column v, Column w, Column x) => Params (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x) where+ params =+ ((\(x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x, _) -> x) >$< E.param encodeColumn)+ <> ((\(_, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, _, x) -> x) >$< E.param encodeColumn)+ -- | The Postgres types of a statement's parameters. type family PgParamTypes (p :: Type) :: [Symbol] where PgParamTypes () = '[]@@ -425,9 +713,24 @@ PgParamTypes (a, b, c, d, e, f) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f] PgParamTypes (a, b, c, d, e, f, g) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g] PgParamTypes (a, b, c, d, e, f, g, h) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h]+ PgParamTypes (a, b, c, d, e, f, g, h, i) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j, k) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j, k, l) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j, k, l, m) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q, PgColumnType r]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q, PgColumnType r, PgColumnType s]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q, PgColumnType r, PgColumnType s, PgColumnType t]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q, PgColumnType r, PgColumnType s, PgColumnType t, PgColumnType u]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q, PgColumnType r, PgColumnType s, PgColumnType t, PgColumnType u, PgColumnType v]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q, PgColumnType r, PgColumnType s, PgColumnType t, PgColumnType u, PgColumnType v, PgColumnType w]+ PgParamTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q, PgColumnType r, PgColumnType s, PgColumnType t, PgColumnType u, PgColumnType v, PgColumnType w, PgColumnType x] PgParamTypes a = '[PgColumnType a] - -- | The enum labels of a statement's parameters, one list each. type family PgParamLabels (p :: Type) :: [[Symbol]] where PgParamLabels () = '[]@@ -438,46 +741,100 @@ PgParamLabels (a, b, c, d, e, f) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f] PgParamLabels (a, b, c, d, e, f, g) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g] PgParamLabels (a, b, c, d, e, f, g, h) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h]+ PgParamLabels (a, b, c, d, e, f, g, h, i) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j, k) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j, k, l) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j, k, l, m) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j, k, l, m, n) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q, PgColumnLabels r]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q, PgColumnLabels r, PgColumnLabels s]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q, PgColumnLabels r, PgColumnLabels s, PgColumnLabels t]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q, PgColumnLabels r, PgColumnLabels s, PgColumnLabels t, PgColumnLabels u]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q, PgColumnLabels r, PgColumnLabels s, PgColumnLabels t, PgColumnLabels u, PgColumnLabels v]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q, PgColumnLabels r, PgColumnLabels s, PgColumnLabels t, PgColumnLabels u, PgColumnLabels v, PgColumnLabels w]+ PgParamLabels (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q, PgColumnLabels r, PgColumnLabels s, PgColumnLabels t, PgColumnLabels u, PgColumnLabels v, PgColumnLabels w, PgColumnLabels x] PgParamLabels a = '[PgColumnLabels a] - -- | A result row: one column, or a tuple of them. class Row a where row :: D.Row a --instance {-# OVERLAPPABLE #-} Column a => Row a where+instance {-# OVERLAPPABLE #-} (Column a) => Row a where row = D.column decodeColumn - instance (Column a, Column b) => Row (a, b) where row = (,) <$> D.column decodeColumn <*> D.column decodeColumn - instance (Column a, Column b, Column c) => Row (a, b, c) where row = (,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn - instance (Column a, Column b, Column c, Column d) => Row (a, b, c, d) where row = (,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn - instance (Column a, Column b, Column c, Column d, Column e) => Row (a, b, c, d, e) where row = (,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn - instance (Column a, Column b, Column c, Column d, Column e, Column f) => Row (a, b, c, d, e, f) where row = (,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn - instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g) => Row (a, b, c, d, e, f, g) where row = (,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn - instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h) => Row (a, b, c, d, e, f, g, h) where row = (,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn +instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i) => Row (a, b, c, d, e, f, g, h, i) where+ row = (,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn +instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j) => Row (a, b, c, d, e, f, g, h, i, j) where+ row = (,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k) => Row (a, b, c, d, e, f, g, h, i, j, k) where+ row = (,,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l) => Row (a, b, c, d, e, f, g, h, i, j, k, l) where+ row = (,,,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m) => Row (a, b, c, d, e, f, g, h, i, j, k, l, m) where+ row = (,,,,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n) => Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n) where+ row = (,,,,,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o) => Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o) where+ row = (,,,,,,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p) => Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p) where+ row = (,,,,,,,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q) => Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q) where+ row = (,,,,,,,,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q, Column r) => Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r) where+ row = (,,,,,,,,,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q, Column r, Column s) => Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s) where+ row = (,,,,,,,,,,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q, Column r, Column s, Column t) => Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t) where+ row = (,,,,,,,,,,,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q, Column r, Column s, Column t, Column u) => Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u) where+ row = (,,,,,,,,,,,,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q, Column r, Column s, Column t, Column u, Column v) => Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v) where+ row = (,,,,,,,,,,,,,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q, Column r, Column s, Column t, Column u, Column v, Column w) => Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w) where+ row = (,,,,,,,,,,,,,,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn++instance (Column a, Column b, Column c, Column d, Column e, Column f, Column g, Column h, Column i, Column j, Column k, Column l, Column m, Column n, Column o, Column p, Column q, Column r, Column s, Column t, Column u, Column v, Column w, Column x) => Row (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x) where+ row = (,,,,,,,,,,,,,,,,,,,,,,,) <$> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn <*> D.column decodeColumn+ -- | The Postgres types of a statement's result columns. type family PgColumnTypes (r :: Type) :: [Symbol] where PgColumnTypes (a, b) = '[PgColumnType a, PgColumnType b]@@ -487,9 +844,24 @@ PgColumnTypes (a, b, c, d, e, f) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f] PgColumnTypes (a, b, c, d, e, f, g) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g] PgColumnTypes (a, b, c, d, e, f, g, h) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h]+ PgColumnTypes (a, b, c, d, e, f, g, h, i) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j, k) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j, k, l) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j, k, l, m) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q, PgColumnType r]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q, PgColumnType r, PgColumnType s]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q, PgColumnType r, PgColumnType s, PgColumnType t]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q, PgColumnType r, PgColumnType s, PgColumnType t, PgColumnType u]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q, PgColumnType r, PgColumnType s, PgColumnType t, PgColumnType u, PgColumnType v]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q, PgColumnType r, PgColumnType s, PgColumnType t, PgColumnType u, PgColumnType v, PgColumnType w]+ PgColumnTypes (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x) = '[PgColumnType a, PgColumnType b, PgColumnType c, PgColumnType d, PgColumnType e, PgColumnType f, PgColumnType g, PgColumnType h, PgColumnType i, PgColumnType j, PgColumnType k, PgColumnType l, PgColumnType m, PgColumnType n, PgColumnType o, PgColumnType p, PgColumnType q, PgColumnType r, PgColumnType s, PgColumnType t, PgColumnType u, PgColumnType v, PgColumnType w, PgColumnType x] PgColumnTypes a = '[PgColumnType a] - -- | The enum labels of a statement's result columns, one list each. type family PgColumnLabelLists (r :: Type) :: [[Symbol]] where PgColumnLabelLists (a, b) = '[PgColumnLabels a, PgColumnLabels b]@@ -499,65 +871,86 @@ PgColumnLabelLists (a, b, c, d, e, f) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f] PgColumnLabelLists (a, b, c, d, e, f, g) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g] PgColumnLabelLists (a, b, c, d, e, f, g, h) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j, k) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j, k, l) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j, k, l, m) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j, k, l, m, n) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q, PgColumnLabels r]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q, PgColumnLabels r, PgColumnLabels s]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q, PgColumnLabels r, PgColumnLabels s, PgColumnLabels t]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q, PgColumnLabels r, PgColumnLabels s, PgColumnLabels t, PgColumnLabels u]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q, PgColumnLabels r, PgColumnLabels s, PgColumnLabels t, PgColumnLabels u, PgColumnLabels v]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q, PgColumnLabels r, PgColumnLabels s, PgColumnLabels t, PgColumnLabels u, PgColumnLabels v, PgColumnLabels w]+ PgColumnLabelLists (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x) = '[PgColumnLabels a, PgColumnLabels b, PgColumnLabels c, PgColumnLabels d, PgColumnLabels e, PgColumnLabels f, PgColumnLabels g, PgColumnLabels h, PgColumnLabels i, PgColumnLabels j, PgColumnLabels k, PgColumnLabels l, PgColumnLabels m, PgColumnLabels n, PgColumnLabels o, PgColumnLabels p, PgColumnLabels q, PgColumnLabels r, PgColumnLabels s, PgColumnLabels t, PgColumnLabels u, PgColumnLabels v, PgColumnLabels w, PgColumnLabels x] PgColumnLabelLists a = '[PgColumnLabels a] - -- | Type-level names, as text. class KnownSymbols (ss :: [Symbol]) where symbolTexts :: [Text] - instance KnownSymbols '[] where symbolTexts = [] - instance (KnownSymbol s, KnownSymbols ss) => KnownSymbols (s ': ss) where symbolTexts = Text.pack (symbolVal (Proxy @s)) : symbolTexts @ss ---- | The Postgres types of a statement's parameters, as GHC worked them out--- where it is used. A class of its own, rather than 'KnownSymbols' itself,--- so that @hasql-check-hie@ finds the whole list in a @.hie@ file, and not--- only the tails 'KnownSymbols' is built from.-class KnownSymbols ps => PostgresParams ps+{- | The Postgres types of a statement's parameters, as GHC worked them out+where it is used. A class of its own, rather than 'KnownSymbols' itself,+so that @hasql-check-hie@ finds the whole list in a @.hie@ file, and not+only the tails 'KnownSymbols' is built from.+-}+class (KnownSymbols ps) => PostgresParams ps +instance (KnownSymbols ps) => PostgresParams ps -instance KnownSymbols ps => PostgresParams ps+{- | The Haskell types a statement's parameters are sent from, for+@hasql-check-hie@ to find; see 'PostgresParams'.+-}+class HaskellParams (hs :: [Type]) +instance HaskellParams hs --- | The Postgres types of a statement's result columns; see 'PostgresParams'.-class KnownSymbols cs => PostgresColumns cs+{- | The Haskell types a statement's result columns are read as; see+'PostgresParams'.+-}+class HaskellColumns (hs :: [Type]) +instance HaskellColumns hs -instance KnownSymbols cs => PostgresColumns cs+-- | The Postgres types of a statement's result columns; see 'PostgresParams'.+class (KnownSymbols cs) => PostgresColumns cs +instance (KnownSymbols cs) => PostgresColumns cs --- | The enum labels of a statement's parameters, as GHC worked them out where--- it is used, for @hasql-check-hie@ to find; see 'PostgresParams'.+{- | The enum labels of a statement's parameters, as GHC worked them out where+it is used, for @hasql-check-hie@ to find; see 'PostgresParams'.+-} class PostgresParamLabels (ls :: [[Symbol]]) - instance PostgresParamLabels ls - -- | The enum labels of a statement's result columns; see 'PostgresParams'. class PostgresColumnLabels (ls :: [[Symbol]]) - instance PostgresColumnLabels ls +{- | A statement's text, as the quoter cut it. --- | A statement's text, as the quoter cut it.------ Its result columns are cast in a projection around it,------ > WITH <its own WITH list,> r (c1, c2) AS (<the statement>) SELECT c1 :: int8, c2 :: text FROM r------ rather than where they are selected, so that the statement means what it--- did: a cast column is another expression to DISTINCT ON, ORDER BY and--- GROUP BY, and no longer the primary key other columns depend on. The--- statement's own WITH list goes first, since one with a data-modifying--- statement must stay at the top.+Its result columns are cast in a projection around it,++> WITH <its own WITH list,> r (c1, c2) AS (<the statement>) SELECT c1 :: int8, c2 :: text FROM r++rather than where they are selected, so that the statement means what it+did: a cast column is another expression to DISTINCT ON, ORDER BY and+GROUP BY, and no longer the primary key other columns depend on. The+statement's own WITH list goes first, since one with a data-modifying+statement must stay at the top.+-} data Template = Template { whole :: [Piece] -- ^ The statement, for one returning no rows.@@ -566,7 +959,6 @@ } deriving stock (Eq, Show, Lift) - data Wrapped = Wrapped { with :: Maybe [Piece] -- ^ Its own WITH list, with the WITH.@@ -577,7 +969,6 @@ } deriving stock (Eq, Show, Lift) - -- | Some SQL, or the place of a parameter's annotation. data Piece = Sql Text@@ -585,9 +976,9 @@ ParamType Int deriving stock (Eq, Show, Lift) ---- | The statement's text, given the Postgres types of its parameters and--- result columns.+{- | The statement's text, given the Postgres types of its parameters and+result columns.+-} render :: [Text] -> [Text] -> Template -> Text render paramTypes' columnTypes' t = case (columnTypes', t.wrapped) of (_ : _, Just w) ->@@ -612,7 +1003,110 @@ ty : _ | n >= 1 -> " :: " <> ty _ -> "" +{- | A row decoder the quoter built out of a statement's target list, carrying+the Postgres types and enum labels its columns are read as. Kronor's+Haskell targets need it: only the statement knows the row's shape, and the+column types are the constructor's fields'.+-}+newtype Target (cs :: [Symbol]) (ls :: [[Symbol]]) (hs :: [Type]) r = Target {targetRow :: D.Row r} +-- | A target that reads no columns: a constructor, before its arguments.+targetPure :: r -> Target '[] '[] '[] r+targetPure = Target . pure++-- | One column, read as whatever Haskell reads it as.+targetColumn :: forall a. (Column a) => Target '[PgColumnType a] '[PgColumnLabels a] '[a] a+targetColumn = Target (D.column decodeColumn)++-- | A constructor applied to one more column, appending its type.+targetAp :: Target cs ls hs (a -> b) -> Target ds ms is a -> Target (Append cs ds) (Append ls ms) (Append hs is) b+targetAp (Target f) (Target x) = Target (f <*> x)++{- | A parameter encoder the quoter built out of a statement's placeholders,+carrying the Postgres types they are sent as. Kronor's @$1.$field@ param+fields need it: each sends a field of a parameter, not the whole of it.+-}+newtype Slots (ps :: [Symbol]) (ls :: [[Symbol]]) (hs :: [Type]) p = Slots {slotsParams :: E.Params p}++-- | No parameters.+slotsNone :: Slots '[] '[] '[] p+slotsNone = Slots mempty++-- | One parameter slot, sending what the projection picks out.+slotsOne :: forall a p. (Column a) => (p -> a) -> Slots '[PgColumnType a] '[PgColumnLabels a] '[a] p+slotsOne f = Slots (f >$< E.param encodeColumn)++-- | One more slot, appending its type.+slotsAp :: Slots ps ls hs p -> Slots qs ms is p -> Slots (Append ps qs) (Append ls ms) (Append hs is) p+slotsAp (Slots a) (Slots b) = Slots (a <> b)++{- | A statement returning rows, whose decoder and encoder the quoter built+because the statement's own syntax decides them.+-}+statementWith ::+ forall p r a ps cs pl cl ph ch.+ ( PostgresParams ps+ , PostgresColumns cs+ , PostgresParamLabels pl+ , PostgresColumnLabels cl+ , HaskellParams ph+ , HaskellColumns ch+ ) =>+ Template ->+ Slots ps pl ph p ->+ Target cs cl ch r ->+ (D.Row r -> D.Result a) ->+ Statement p a+statementWith template slots target result =+ Statement.preparable+ (render (symbolTexts @ps) (symbolTexts @cs) template)+ (slotsParams slots)+ (result (targetRow target))++{- | A statement whose encoder the quoter built, but whose row the Haskell+type decides: a target list the quoter cannot count, such as a @*@.+-}+statementRow ::+ forall p r a ps cs pl cl ph.+ ( Row r+ , cs ~ PgColumnTypes r+ , cl ~ PgColumnLabelLists r+ , PostgresParams ps+ , PostgresColumns cs+ , PostgresParamLabels pl+ , PostgresColumnLabels cl+ , HaskellParams ph+ ) =>+ Template ->+ Slots ps pl ph p ->+ (D.Row r -> D.Result a) ->+ Statement p a+statementRow template slots result =+ Statement.preparable+ (render (symbolTexts @ps) (symbolTexts @cs) template)+ (slotsParams slots)+ (result row)++-- | A statement returning no rows, whose encoder the quoter built.+resultlessWith ::+ forall p ps pl ph.+ (PostgresParams ps, PostgresParamLabels pl, HaskellParams ph) =>+ Template ->+ Slots ps pl ph p ->+ Statement p ()+resultlessWith template slots =+ Statement.preparable (render (symbolTexts @ps) [] template) (slotsParams slots) D.noResult++-- | A statement counting the rows it affected, whose encoder the quoter built.+rowsAffectedWith ::+ forall p ps pl ph.+ (PostgresParams ps, PostgresParamLabels pl, HaskellParams ph) =>+ Template ->+ Slots ps pl ph p ->+ Statement p Int64+rowsAffectedWith template slots =+ Statement.preparable (render (symbolTexts @ps) [] template) (slotsParams slots) D.rowsAffected+ -- | A statement returning rows, given what to make of them. statement :: forall p r a ps cs pl cl.@@ -633,6 +1127,13 @@ statement template result = Statement.preparable (render (symbolTexts @ps) (symbolTexts @cs) template) params (result row) +-- | A statement whose result is the number of rows it affected.+rowsAffected ::+ forall p ps pl.+ (Params p, ps ~ PgParamTypes p, PostgresParams ps, pl ~ PgParamLabels p, PostgresParamLabels pl) =>+ Template ->+ Statement p Int64+rowsAffected template = Statement.preparable (render (symbolTexts @ps) [] template) params D.rowsAffected -- | A statement returning no rows. resultless ::
src/Hasql/Check/Inferred/Quote.hs view
@@ -1,18 +1,19 @@--- |--- Module : Hasql.Check.Inferred.Quote--- Copyright : (c) 2026 Kronor.io------ License : BSD-3-Clause--- Maintainer : lorenzo@kronor.io--- Stability : experimental--- Portability : GHC------ Quotes of "Hasql.Check.Inferred.TH", with the Haskell types GHC used them--- at, as @hasql-check-hie@ writes them: one JSON object a line.------ Each is checked as the hasql-th quote it stands for - the same SQL, with--- the annotations the Haskell types give it - so that every check of an--- annotated quote applies to it too.+{- |+Module : Hasql.Check.Inferred.Quote+Copyright : (c) 2026 Kronor.io++License : BSD-3-Clause+Maintainer : lorenzo@kronor.io+Stability : experimental+Portability : GHC++Quotes of "Hasql.Check.Inferred.TH", with the Haskell types GHC used them+at, as @hasql-check-hie@ writes them: one JSON object a line.++Each is checked as the hasql-th quote it stands for - the same SQL, with+the annotations the Haskell types give it - so that every check of an+annotated quote applies to it too.+-} module Hasql.Check.Inferred.Quote ( Inferred (..), Column (..),@@ -33,11 +34,11 @@ import Data.Text qualified as Text import Data.Text.Encoding qualified as Text import Data.Word (Word32)-import Hasql.Check (parsePlainStmt, quoterSettings, renderStmt)+import Hasql.Check (parsePlainStmt, parseStmt, quoterSettings, renderStmt) import Hasql.Check.Annotate (annotate, typename, untypedLiterals) import Hasql.Check.Finding (Finding (..), statementHash)-import Hasql.Check.Inferred (Piece (..), Template (..), render)-import Hasql.Check.Inferred.TH (template)+import Hasql.Check.Inferred (Template (..), render)+import Hasql.Check.Inferred.TH (Parsed (..), parsed) import Hasql.Check.Nullability (Catalogue, query) import Hasql.Check.Nullability qualified as Nullability import Hasql.Check.Types qualified as Types@@ -46,7 +47,6 @@ import Text.Read (readMaybe) import Prelude - data Inferred = Inferred { file :: FilePath , line :: Int@@ -58,9 +58,9 @@ -- ^ Nothing for a statement that returns no rows. } ---- | A parameter or result column: the qualified name of its Haskell type,--- its Postgres type, and whether it is a 'Maybe'.+{- | A parameter or result column: the qualified name of its Haskell type,+its Postgres type, and whether it is a 'Maybe'.+-} data Column = Column { haskellType :: Text , postgres :: Text@@ -70,7 +70,6 @@ , nullable :: Bool } - instance Aeson.FromJSON Inferred where parseJSON = Aeson.withObject "quote" \o -> Inferred@@ -82,15 +81,14 @@ <*> o .: "params" <*> o .:? "row" - instance Aeson.FromJSON Column where parseJSON = Aeson.withObject "column" \o -> Column <$> o .: "type" <*> o .: "postgres" <*> (o .:? "labels" .!= []) <*> o .: "nullable" ---- | Everything checking an inferred statement finds: why it fails, or the--- warnings asked for - nullability, narrowing - in terms of its Haskell--- types, and its fingerprint for baselines: the SQL it sends, so that--- reading a column as another type is another statement.+{- | Everything checking an inferred statement finds: why it fails, or the+warnings asked for - nullability, narrowing - in terms of its Haskell+types, and its fingerprint for baselines: the SQL it sends, so that+reading a column as another type is another statement.+-} checkInferred :: Pqi.Connection -> Maybe Catalogue -> Bool -> Bool -> Inferred -> IO (Either String ([Finding], Text)) checkInferred conn catalogue nullable narrowing q = checkSent conn q >>= \case@@ -111,9 +109,9 @@ let fingerprint = either (const (statementHash (renderStmt ast))) (statementHash . Text.encodeUtf8) (sent q) pure (Right ([f{message = inHaskellTerms f.message} | f <- found], fingerprint)) ---- | A finding about an inferred quote, in terms of its Haskell types rather--- than the annotations they stand for.+{- | A finding about an inferred quote, in terms of its Haskell types rather+than the annotations they stand for.+-} inHaskellTerms :: String -> String inHaskellTerms m = Text.unpack@@ -123,7 +121,6 @@ where t = Text.pack m - -- | Quotes, one JSON object a line. readInferred :: ByteString -> Either String [Inferred] readInferred contents =@@ -131,54 +128,56 @@ (\(n, l) -> either (\e -> Left ("line " <> show n <> ": " <> e)) Right (Aeson.eitherDecodeStrict l)) [(n, l) | (n :: Int, l) <- zip [1 ..] (ByteString.Char8.lines contents), not (ByteString.Char8.null l)] ---- | The statement with its parameters annotated, as a hasql-th quote: its--- result columns are cast around it, which the warnings see through--- 'columns'.+{- | The statement with its parameters annotated, as a hasql-th quote: its+result columns are cast around it, which the warnings see through+'columns'.+-} annotated :: Inferred -> Either String Text annotated q = do- stmt <- parsePlainStmt False q.sql+ -- Lowered, as the quoter sends it: the types come one per placeholder in+ -- that order, which is not the order the statement writes them in when it+ -- uses a parameter more than once, out of order, or by field.+ stmt <- parseStmt q.sql params <- traverse (\c -> typename c.postgres c.nullable) q.params let param n = case drop (n - 1) params of t : _ | n >= 1 -> Just t _ -> Nothing pure (Ast.toText quoterSettings (annotate param stmt)) - -- | The statement as the quoter sends it, casts and all. sent :: Inferred -> Either String Text sent q = do- t <- template q.sql+ t <- parsedTemplate <$> parsed q.sql params <- traverse postgresType q.params row <- traverse (traverse postgresType) q.row pure (render (map fst params) (maybe [] (map fst) row) t) ---- | The Postgres type each result column is read as, and whether it may be--- NULL.+{- | The Postgres type each result column is read as, and whether it may be+NULL.+-} columns :: Inferred -> Maybe [(Text, Bool)] columns q = either (const Nothing) Just . traverse postgresType =<< q.row - postgresType :: Column -> Either String (Text, Bool) postgresType c = Right (c.postgres, c.nullable) +{- | Whether the statement, as the quoter sends it, prepares; whether it+takes as many parameters as the Haskell type sends, and returns as many+columns as it reads, each of a type it can be read as. Prepared, as hasql+prepares it, with the parameters' types, which Postgres could not tell for+a parameter the statement does not use. --- | Whether the statement, as the quoter sends it, prepares; whether it--- takes as many parameters as the Haskell type sends, and returns as many--- columns as it reads, each of a type it can be read as. Prepared, as hasql--- prepares it, with the parameters' types, which Postgres could not tell for--- a parameter the statement does not use.------ A result column is cast to the type it is read as, and Postgres casts--- anything it can convert, even text to a number, which fails at runtime for--- text that is not one. So the column must have that type already, or one--- Postgres converts to it without being told to: implicitly, or on--- assignment.+A result column is cast to the type it is read as, and Postgres casts+anything it can convert, even text to a number, which fails at runtime for+text that is not one. So the column must have that type already, or one+Postgres converts to it without being told to: implicitly, or on+assignment.+-} checkSent :: Pqi.Connection -> Inferred -> IO [String]-checkSent conn q = case (,,) <$> template q.sql <*> traverse postgresType q.params <*> traverse (traverse postgresType) q.row of+checkSent conn q = case (,,) <$> parsed q.sql <*> traverse postgresType q.params <*> traverse (traverse postgresType) q.row of Left err -> pure [err]- Right (t, params, row) -> do+ Right (p, params, row) -> do+ let t = p.parsedTemplate oids <- traverse (oid . fst) params case sequence oids of Nothing -> pure ["a parameter's type does not exist: " <> unwords [Text.unpack name | ((name, _), Nothing) <- zip params oids]]@@ -189,7 +188,10 @@ Right found -> do -- From the statement itself: prepared with the -- types hasql sends, it takes them all, used or not.- let used = [n | ParamType n <- t.whole]+ -- In the numbering the statement was written in,+ -- which lowering renumbers: each slot knows the+ -- parameter it came from.+ let used = p.parsedUsed sends = length q.params paramErrors = [ concat ["the Haskell type sends parameter $", show n, ", which the statement does not use"]@@ -386,7 +388,6 @@ Right [[Just name]] -> pure (Text.unpack (Text.decodeUtf8Lenient name)) _ -> pure ("type " <> show o) quoteLiteral name = mconcat ["'", Text.encodeUtf8 (Text.replace "'" "''" name), "'"]- zip4 :: [a] -> [b] -> [c] -> [d] -> [(a, b, c, d)] zip4 (a : as) (b : bs) (c : cs) (d : ds) = (a, b, c, d) : zip4 as bs cs ds
src/Hasql/Check/Inferred/TH.hs view
@@ -1,71 +1,290 @@+{-# LANGUAGE CPP #-} {-# LANGUAGE TemplateHaskell #-} --- |--- Module : Hasql.Check.Inferred.TH--- Copyright : (c) 2026 Kronor.io------ License : BSD-3-Clause--- Maintainer : lorenzo@kronor.io--- Stability : experimental--- Portability : GHC------ Quoters for SQL without annotations: the Haskell types a statement is used--- with decide its parameter and result types.------ > profile :: Statement Int64 (Maybe (Text, Maybe Text))--- > profile = [maybeStatement| select email, nickname from customer where id = $1 |]------ sends------ > WITH hasql_check_result (c1, c2) AS (SELECT email, nickname FROM customer WHERE id = $1 :: int8)--- > SELECT c1 :: text, c2 :: text FROM hasql_check_result------ GHC can only tell whether those types fit the schema with a database; see--- the README for checking them with @hasql-check --inferred@.+{- |+Module : Hasql.Check.Inferred.TH+Copyright : (c) 2026 Kronor.io++License : BSD-3-Clause+Maintainer : lorenzo@kronor.io+Stability : experimental+Portability : GHC++Quoters for SQL without annotations: the Haskell types a statement is used+with decide its parameter and result types.++> profile :: Statement Int64 (Maybe (Text, Maybe Text))+> profile = [maybeStatement| select email, nickname from customer where id = $1 |]++sends++> WITH hasql_check_result (c1, c2) AS (SELECT email, nickname FROM customer WHERE id = $1 :: int8)+> SELECT c1 :: text, c2 :: text FROM hasql_check_result++Kronor's Haskell targets and @$1.$field@ param fields work too: the quoter+builds the row decoder and the parameter encoder out of them, and the column+types come from the constructor's fields rather than from a tuple.++GHC can only tell whether those types fit the schema with a database; see+the README for checking them with @hasql-check --inferred@.+-} module Hasql.Check.Inferred.TH ( singletonStatement, maybeStatement, vectorStatement, resultlessStatement,+ rowsAffectedStatement,+ Parsed (..),+ Slot (..),+ Tgt (..),+ parsed, template, ) where import Data.Char (isAlphaNum)+import Data.List (foldl1')+import Data.Maybe (fromMaybe)+#ifdef KRONOR_SYNTAX+import Data.List.NonEmpty qualified as NonEmpty+import Data.Map.Strict qualified as Map+#endif import Data.Text (Text) import Data.Text qualified as Text import Data.Text.Encoding qualified as Text-import Hasql.Check (parsePlainStmt, renderStmt)+import GHC.Records (getField)+import Hasql.Check (parseForkStmt, parsePlainStmt, renderStmt) import Hasql.Check.Annotate (annotate, placeholder)-import Hasql.Check.Inferred (Piece (..), Template (..), Wrapped (..), resultless, statement)+import Hasql.Check.Inferred (+ Piece (..),+ Template (..),+ Wrapped (..),+ resultlessWith,+ rowsAffectedWith,+ slotsAp,+ slotsNone,+ slotsOne,+ statementRow,+ statementWith,+ targetAp,+ targetColumn,+ targetPure,+ ) import Hasql.Decoders qualified as D-import Language.Haskell.TH (Exp, Q)+import Language.Haskell.TH (Exp, Q, appTypeE, conE, litT, mkName, newName, strTyLit, varE)+import Language.Haskell.TH qualified as TH import Language.Haskell.TH.Quote (QuasiQuoter (..)) import Language.Haskell.TH.Syntax (lift) import PostgresqlSyntax qualified as Ast import Text.Read (readMaybe) import Prelude +{- | One SQL placeholder: which Haskell parameter it comes from, and which of+its fields, for Kronor's @$1.$field@.+-}+data Slot = Slot Int (Maybe Text)+ deriving stock (Eq, Show) -quoter :: (Q Exp -> Q Exp) -> QuasiQuoter+-- | A result column, or a Haskell constructor applied to some.+data Tgt+ = TgtColumn+ | -- | A constructor applied to its arguments in order.+ TgtApply Text [Tgt]+ | {- | A constructor whose fields are named, so the statement may write+ them in any order.+ -}+ TgtRecord Text [(Text, Tgt)]+ deriving stock (Eq, Show)++-- | Everything the quoter reads off a statement.+data Parsed = Parsed+ { parsedTemplate :: Template+ , parsedSlots :: [Slot]+ -- ^ One per SQL placeholder, in the order they are sent.+ , parsedArity :: Int+ -- ^ How many parameters the statement takes in Haskell.+ , parsedUsed :: [Int]+ {- ^ The parameters the statement actually refers to, numbered as it was+ written: lowering renumbers the placeholders, so this is not the same+ as the slots' positions.+ -}+ , parsedTargets :: Maybe [Tgt]+ -- ^ Its result columns, unless they cannot be counted here: a @*@.+ }+ deriving stock (Eq, Show)++quoter :: (Parsed -> Q Exp) -> QuasiQuoter quoter make = QuasiQuoter- { quoteExp = either fail (make . lift) . template . Text.pack+ { quoteExp = either fail make . parsed . Text.pack , quotePat = const (fail "Not supported in patterns") , quoteType = const (fail "Not supported in types") , quoteDec = const (fail "Not supported in declarations") } +-- | A quoter for a statement that returns rows, given what to make of them.+rowQuoter :: Q Exp -> QuasiQuoter+rowQuoter result = quoter \p -> do+ let t = lift p.parsedTemplate+ s = slotsExp p+ case p.parsedTargets of+ Just ts -> [|statementWith $t $s $(targetsExp ts) $result|]+ Nothing -> [|statementRow $t $s $result|] -singletonStatement, maybeStatement, vectorStatement, resultlessStatement :: QuasiQuoter-singletonStatement = quoter \t -> [|statement $t D.singleRow|]-maybeStatement = quoter \t -> [|statement $t D.rowMaybe|]-vectorStatement = quoter \t -> [|statement $t D.rowVector|]-resultlessStatement = quoter \t -> [|resultless $t|]+singletonStatement, maybeStatement, vectorStatement, resultlessStatement, rowsAffectedStatement :: QuasiQuoter+singletonStatement = rowQuoter [|D.singleRow|]+maybeStatement = rowQuoter [|D.rowMaybe|]+vectorStatement = rowQuoter [|D.rowVector|]+resultlessStatement = quoter \p -> [|resultlessWith $(lift p.parsedTemplate) $(slotsExp p)|]+rowsAffectedStatement = quoter \p -> [|rowsAffectedWith $(lift p.parsedTemplate) $(slotsExp p)|] +{- | The statement's parameter encoder: one slot per placeholder, each picking+its parameter out of the tuple, and its field out of that.+-}+slotsExp :: Parsed -> Q Exp+slotsExp p = case p.parsedSlots of+ [] -> [|slotsNone|]+ ss -> foldl1' (\a b -> [|slotsAp $a $b|]) (map (slotExp p.parsedArity) ss) --- | The statement, rendered as hasql-th would render it, cut where its--- parameters' annotations go, and split where its result columns' cast--- goes around it.+slotExp :: Int -> Slot -> Q Exp+slotExp arity (Slot n field) = do+ y <- newName "y"+ -- Wildcards elsewhere: an unused binding warns in the splice's module.+ let pat+ | arity <= 1 = TH.varP y+ | otherwise = TH.tupP [if i == n then TH.varP y else TH.wildP | i <- [1 .. arity]]+ body = case field of+ Nothing -> varE y+ Just f -> [|$(appTypeE (varE 'getField) (litT (strTyLit (Text.unpack f)))) $(varE y)|]+ [|slotsOne $(TH.lamE [pat] body)|]++-- | The statement's row decoder, built out of its target list.+targetsExp :: [Tgt] -> Q Exp+targetsExp = \case+ [t] -> targetExp t+ ts -> applied [|targetPure $(conE (TH.tupleDataName (length ts)))|] ts++targetExp :: Tgt -> Q Exp+targetExp = \case+ TgtColumn -> [|targetColumn|]+ TgtApply ctor args -> applied [|targetPure $(conE (mkName (Text.unpack ctor)))|] args+ TgtRecord ctor fields -> do+ -- Bound in the statement's order and assigned by name: applying the+ -- constructor positionally would cross the values over.+ xs <- traverse (const (newName "c")) fields+ let make =+ TH.lamE+ (map TH.varP xs)+ (TH.recConE (mkName (Text.unpack ctor)) [TH.fieldExp (mkName (Text.unpack n)) (varE x) | ((n, _), x) <- zip fields xs])+ applied [|targetPure $make|] (map snd fields)++applied :: Q Exp -> [Tgt] -> Q Exp+applied = foldl \f a -> [|targetAp $f $(targetExp a)|]++{- | Everything the quoters need: the statement cut where its parameters'+annotations go, which parameter each placeholder sends, and the shape of+its result row.+-}+parsed :: Text -> Either String Parsed+parsed sql = do+ forked <- parseForkStmt sql+ -- The targets are read off the lowered statement, before they are erased+ -- for the one that is sent.+ let (sent, lowered, slots') = lowerStmt forked+ t <- template (Text.decodeUtf8Lenient (renderStmt sent))+ let (slots, arity) = fromMaybe (plainSlots t) slots'+ -- Where the statement was lowered the slots carry what each+ -- placeholder was written as; where it was not, the template does.+ used = maybe [i | ParamType i <- t.whole] (\_ -> [n | Slot n _ <- slots]) slots'+ pure+ Parsed+ { parsedTemplate = t+ , parsedSlots = slots+ , parsedArity = arity+ , parsedUsed = used+ , parsedTargets = targets lowered+ }++{- | One slot per placeholder, each sending the whole of its parameter, for a+statement with no param fields to lower.+-}+plainSlots :: Template -> ([Slot], Int)+plainSlots t = ([Slot i Nothing | i <- [1 .. n]], n)+ where+ n = maximum (0 : [i | ParamType i <- t.whole])++#ifdef KRONOR_SYNTAX++-- | The statement as it is sent (lowered, with the Haskell targets erased),+-- as its targets are read (lowered, with them still there), and which+-- parameter each of its placeholders sends.+lowerStmt :: Ast.PreparableStmt -> (Ast.PreparableStmt, Ast.PreparableStmt, Maybe ([Slot], Int))+lowerStmt stmt =+ ( Ast.eraseHaskellTargets lowered+ , lowered+ , -- InputParams maps each ($n, field) to its lowered placeholder.+ Just+ ( [Slot n field | (_, (n, field)) <- Map.toAscList (Map.fromList [(v, k) | (k, v) <- Map.toList inputs])]+ , maximum (0 : [n | ((n, _), _) <- Map.toList inputs])+ )+ )+ where+ (lowered, inputs) = Ast.lower stmt++#else++-- | Upstream hasql-th has no param fields and no targets to erase, so the+-- statement is sent as parsed and its placeholders are its parameters.+lowerStmt :: Ast.PreparableStmt -> (Ast.PreparableStmt, Ast.PreparableStmt, Maybe ([Slot], Int))+lowerStmt stmt = (stmt, stmt, Nothing)++#endif++#ifdef KRONOR_SYNTAX++-- | The outermost SELECT's target list, as Haskell targets: 'Nothing' when it+-- is not a list this can count, such as a @*@, where the Haskell row type+-- decides the columns instead.+targets :: Ast.PreparableStmt -> Maybe [Tgt]+targets = \case+ Ast.SelectPreparableStmt s -> traverse targetOf . NonEmpty.toList =<< selectStmt s+ _ -> Nothing+ where+ selectStmt = \case+ Ast.NoParensSelectStmt (Ast.SelectNoParens _ c _ _ _) -> selectClause c+ Ast.WithParensSelectStmt p -> withParens p+ withParens = \case+ Ast.NoParensSelectWithParens (Ast.SelectNoParens _ c _ _ _) -> selectClause c+ Ast.WithParensSelectWithParens p -> withParens p+ selectClause = \case+ Ast.SimpleSelectSelectClause (Ast.NormalSimpleSelect (Just (Ast.NormalTargeting (Ast.HsTargetList ts))) _ _ _ _ _ _) -> Just ts+ Ast.WithParensSelectClause p -> withParens p+ _ -> Nothing+++-- | What a target element reads, or 'Nothing' when it stands for however many+-- columns a table has: a @*@ or a @t.*@, which only the schema can count.+targetOf :: Ast.HsTargetEl -> Maybe Tgt+targetOf = \case+ Ast.SqlTargetEl Ast.AsteriskTargetEl -> Nothing+ Ast.SqlTargetEl (Ast.ExprTargetEl (Ast.CExprAExpr (Ast.ColumnrefCExpr (Ast.Columnref _ (Just (Ast.Indirection is))))))+ | Ast.AllIndirectionEl <- NonEmpty.last is -> Nothing+ Ast.SqlTargetEl _ -> Just TgtColumn+ Ast.HsFuncTargetEl ctor args -> TgtApply ctor <$> traverse targetOf args+ Ast.HsRecTargetEl ctor fields -> TgtRecord ctor <$> traverse (\(Ast.HsFieldEl n t) -> (,) n <$> targetOf t) (NonEmpty.toList fields)++#else++-- | Upstream hasql-th has no Haskell targets, so the Haskell row type always+-- decides the columns.+targets :: Ast.PreparableStmt -> Maybe [Tgt]+targets _ = Nothing++#endif++{- | The statement, rendered as hasql-th would render it, cut where its+parameters' annotations go, and split where its result columns' cast+goes around it.+-} template :: Text -> Either String Template template sql = do stmt <- parsePlainStmt False sql@@ -90,7 +309,6 @@ <$> splitWith annotated } - -- | The statement's own WITH list, and the rest of it. splitWith :: Ast.PreparableStmt -> Maybe (Maybe Ast.WithClause, Ast.PreparableStmt) splitWith = \case@@ -106,14 +324,13 @@ Ast.DeletePreparableStmt (Ast.DeleteStmt w a b c d) -> Just (w, Ast.DeletePreparableStmt (Ast.DeleteStmt Nothing a b c d)) Ast.CallPreparableStmt _ -> Nothing ---- | A parenthesised SELECT's WITH list, and the rest of it: the list can go--- outside the parentheses, and must, if it has a data-modifying statement.+{- | A parenthesised SELECT's WITH list, and the rest of it: the list can go+outside the parentheses, and must, if it has a data-modifying statement.+-} inParens :: Ast.SelectWithParens -> (Maybe Ast.WithClause, Ast.SelectWithParens) inParens = \case Ast.NoParensSelectWithParens (Ast.SelectNoParens w c s l f) -> (w, Ast.NoParensSelectWithParens (Ast.SelectNoParens Nothing c s l f)) Ast.WithParensSelectWithParens s -> Ast.WithParensSelectWithParens <$> inParens s- cutWith :: Text -> Text -> [Piece] cutWith prefix = cut
+ test/Inferred/Shapes.hs view
@@ -0,0 +1,144 @@+{-# LANGUAGE CPP #-}+{-# LANGUAGE DataKinds #-}+{-# LANGUAGE DeriveGeneric #-}+{-# LANGUAGE DerivingVia #-}+{-# LANGUAGE OverloadedRecordDot #-}+{-# LANGUAGE QuasiQuotes #-}+{-# LANGUAGE TemplateHaskell #-}+{-# LANGUAGE UndecidableInstances #-}++{- | Every shape the inferred quoters must take. Nothing runs: the types are+the assertion, and a quoter that builds the wrong row, or reads a column at+the wrong type, fails to compile.+-}+module Inferred.Shapes where++import Data.Int (Int64)+#ifdef KRONOR_SYNTAX+import Data.Int (Int32)+import GHC.Generics (Generic)+#endif+import Data.Text (Text)+import Data.Vector (Vector)+import Hasql.Check.Inferred (Value)+import Hasql.Check.Inferred.TH+import Hasql.Statement (Statement)+import Prelude++-- A plain tuple row, as before.+plain :: Statement Int64 (Maybe (Text, Maybe Text))+plain = [maybeStatement| select email, nickname from customer where id = $1 |]++-- A row of more than eight columns, past the old tuple cap.+wide :: Statement () (Vector (Int64, Int64, Int64, Int64, Int64, Int64, Int64, Int64, Int64, Int64))+wide = [vectorStatement| select a, b, c, d, e, f, g, h, i, j from wide |]++-- Seventeen parameters, the widest statement in the repository.+manyParams :: Statement (Int64, Int64, Int64, Int64, Int64, Int64, Int64, Int64, Int64, Int64, Int64, Int64, Int64, Int64, Int64, Int64, Int64) ()+manyParams =+ [resultlessStatement|+ insert into wide+ ( a+ , b+ , c+ , d+ , e+ , f+ , g+ , h+ , i+ , j+ , k+ , l+ , m+ , n+ , o+ , p+ , q+ )+ values+ ( $1+ , $2+ , $3+ , $4+ , $5+ , $6+ , $7+ , $8+ , $9+ , $10+ , $11+ , $12+ , $13+ , $14+ , $15+ , $16+ , $17+ )+ |]++#ifdef KRONOR_SYNTAX++data CartItem = CartItem+ { productId :: Text+ , quantity :: Int32+ , title :: Maybe Text+ }+ deriving stock (Show, Eq)+++-- A record target, with its fields deliberately out of declaration order:+-- they are assigned by name, so a positional quoter would not compile.+record :: Statement Int64 (Vector CartItem)+record =+ [vectorStatement|+ select+ $CartItem+ { title = title+ , productId = product_id+ , quantity = quantity+ }+ from cart_item+ where cart_id = $1+ |]+++-- A constructor applied positionally, and nested inside a record.+nested :: Statement () (Maybe (Maybe Text))+nested = [maybeStatement| select $Just (name) from account |]+++data Payload = Payload+ { reportId :: Int64+ , orgId :: Int64+ }+ deriving stock (Generic)+++-- A param field: one placeholder per field of a record parameter.+paramField :: Statement (Payload, Text) ()+paramField =+ [resultlessStatement|+ update report+ set link = $2+ where id = $1.$reportId+ and organization_id = $1.$orgId+ |]+++#endif++-- rowsAffected, which had no inferred quoter.+affected :: Statement Int64 Int64+affected = [rowsAffectedStatement| update session set last_seen = now() where id = $1 |]++-- A star, whose columns only the Haskell type can count.+star :: Statement () (Vector (Int64, Text))+star = [vectorStatement| select * from pair |]++newtype Email = Email Text+ deriving newtype (Value)++-- A newtype column, read as the type it wraps.+newtyped :: Statement Int64 Email+newtyped = [singletonStatement| select email from customer where id = $1 |]
test/Main.hs view
@@ -39,7 +39,6 @@ import Test.Syd import Prelude - main :: IO () main = sydTest do describe "parseQuasiQuotes" lexerSpec@@ -54,14 +53,12 @@ -- so they run one at a time, in order. describe "Hasql.Check.TH" $ sequential $ doNotRandomiseExecutionOrder $ aroundAll withPostgres thSpec - -- | The quoter, its line and column, and the SQL, of every quasiquote found. quotes :: Text -> Either String [(Text, Int, Int, Text)] quotes source = map (\(QuasiQuote (AlexPn _ line col, quoter) (_, sql)) -> (quoter, line, col, sql)) <$> parseQuasiQuotes (ByteString.Lazy.fromStrict (Text.Encoding.encodeUtf8 source)) - lexerSpec :: Spec lexerSpec = do it "finds a quote" $@@ -116,9 +113,9 @@ quotes "f = [singletonStatement|select 1 :: int4\n" `shouldSatisfy` either ("not closed" `isInfixOf`) (const False) ---- | A connection string for a throwaway server, reachable only over a socket--- in a temporary directory.+{- | A connection string for a throwaway server, reachable only over a socket+in a temporary directory.+-} withPostgres :: (Text -> IO ()) -> IO () withPostgres action = withSystemTempDirectory "hasql-check" \dir -> do@@ -136,9 +133,9 @@ callProcess "psql" [Text.unpack conn, "--quiet", "--command", "create table account (id int4 primary key, name text not null, nickname text); create index on account (nickname); create table note (account_id int4 not null references account, body text not null); create domain cents as int8; create domain positive_cents as cents check (value > 0); create table wallet (balance positive_cents not null); create table ledger (id int8 primary key, small int2, amount int8 not null, rate float8, at timestamptz, price cents); create table tag (id int4 primary key, label varchar(20) not null); insert into tag values (1, 'red'); create table tagged (id int4 primary key, labels text[] not null, scores int4[]); insert into tagged values (1, '{a,b}', '{1,NULL,3}'); create table totals (id int4 primary key, amounts int8[] not null); create type payment_state as enum ('PENDING', 'PAID', 'REFUNDED'); create table payment (id int4 primary key, state payment_state not null); insert into payment values (1, 'PAID'); create domain payment_status as payment_state; create table payment_log (id int4 primary key, status payment_status not null); insert into payment_log values (1, 'REFUNDED')"] action conn ---- | Run the executable on a source file and the given flags, with extra--- environment variables; return the exit code and stdout.+{- | Run the executable on a source file and the given flags, with extra+environment variables; return the exit code and stdout.+-} runOn :: [(String, String)] -> [String] -> Text -> IO (ExitCode, String) runOn env args source = withSystemTempDirectory "hasql-check-src" \dir -> do@@ -153,7 +150,6 @@ "" pure (code, out <> err) - executableSpec :: TestDef '[Text] () executableSpec = do itWithOuter "accepts a statement that matches the schema" \conn -> do@@ -209,7 +205,6 @@ where isSuffixOfStr suffix s = Text.pack suffix `Text.isSuffixOf` Text.pack s - -- | The syntax only Kronor's fork of hasql-th accepts. syntaxSpec :: TestDef '[Text] () #ifdef KRONOR_SYNTAX@@ -222,6 +217,14 @@ (code, out) <- runOn [] ["--database", Text.unpack conn] "f = [maybeStatement|select $Just (nope :: text) from account|]\n" code `shouldBe` ExitFailure 1 out `shouldSatisfy` ("column \"nope\" does not exist" `isInfixOf`)++ -- The types come one per placeholder in the order the quoter sends them,+ -- which lowering renumbers: this writes $2 before $1, so pairing them+ -- with the numbering as written puts the label's text on tag.id and+ -- rejects a statement that is perfectly fine.+ itWithOuter "annotates the parameters in the order they are sent, not written" \conn ->+ runInferred conn [] [inferredQuote "resultlessStatement" "insert into tag (label, id) values ($2, $1)" [text, int32] Nothing]+ `shouldReturn` (ExitSuccess, "") #else syntaxSpec = itWithOuter "rejects Haskell targets, which upstream hasql-th does not accept" \conn -> do@@ -230,13 +233,11 @@ out `shouldSatisfy` ("Fixture.hs:1:5" `isInfixOf`) #endif - -- | Run with --nullability on one statement; return the exit code and output. nullability :: Text -> Text -> IO (ExitCode, String) nullability conn statement = runOn [] ["--database", Text.unpack conn, "--nullability"] ("f = [vectorStatement|" <> statement <> "|]\n") - nullabilitySpec :: TestDef '[Text] () nullabilitySpec = do itWithOuter "warns about a nullable column annotated non-null, without failing" \conn -> do@@ -316,14 +317,13 @@ out `shouldSatisfy` ("column 1 (nickname)" `isInfixOf`) out `shouldNotSatisfy` ("column 2" `isInfixOf`) ---- | Run a checked quoter as a splice would. Outside GHC a failing splice only--- says that it failed - the message goes to stderr - so the tests that expect--- a failure pair it with the same statement passing when nothing is checked.+{- | Run a checked quoter as a splice would. Outside GHC a failing splice only+says that it failed - the message goes to stderr - so the tests that expect+a failure pair it with the same statement passing when nothing is checked.+-} quote :: QuasiQuoter -> String -> IO (Either String ()) quote quoter sql = either (Left . show) (const (Right ())) <$> (try (void (runQ (quoteExp quoter sql))) :: IO (Either SomeException ())) - thSpec :: TestDef '[Text] () thSpec = do it "checks nothing when no database is set" do@@ -356,13 +356,11 @@ setEnv "HASQL_CHECK_DATABASE_URL" "host=/nonexistent" quote Checked.vectorStatement "select nope :: text from account" `shouldReturn` Right () - -- | Run with --types on one quote; return the exit code and output. types :: Text -> Text -> Text -> IO (ExitCode, String) types conn quoter statement = runOn [] ["--database", Text.unpack conn, "--types"] ("f = [" <> quoter <> "|" <> statement <> "|]\n") - typesSpec :: TestDef '[Text] () typesSpec = do itWithOuter "warns about a column read as a narrower type, without failing" \conn -> do@@ -435,12 +433,10 @@ out `shouldSatisfy` ("column 1 (id) is annotated smallint, but is an integer" `isInfixOf`) out `shouldSatisfy` ("parameter $1" `isInfixOf`) - -- | Run on a whole source with the given flags; return the exit code and output. checkSource :: Text -> [String] -> Text -> IO (ExitCode, String) checkSource conn flags = runOn [] (["--database", Text.unpack conn] <> flags) - suppressionSpec :: TestDef '[Text] () suppressionSpec = do itWithOuter "a directive above the quote suppresses the finding it names" \conn ->@@ -525,13 +521,12 @@ checkSource conn ["--nullability", "--fail-on-warnings"] ("-- hasql-check: allow nullable(\"display name\")\n" <> source) `shouldReturn` (ExitSuccess, "") ---- | The SQL the inferred quoters send for a statement, given the Postgres--- types of its parameters and result columns.+{- | The SQL the inferred quoters send for a statement, given the Postgres+types of its parameters and result columns.+-} sent :: Text -> [Text] -> [Text] -> Either String Text sent sql paramTypes columnTypes = render paramTypes columnTypes <$> Inferred.template sql - piecesSpec :: Spec piecesSpec = do it "annotates each parameter, and casts each result column around the statement" $@@ -591,38 +586,31 @@ it "rejects SQL it cannot parse" $ Inferred.template "select from where" `shouldSatisfy` isLeft - data PaymentState = PENDING | PAID | REFUNDED deriving stock (Eq, Show, Generic) deriving (Value) via PgEnum "payment_state" PaymentState - newtype Qualified = Qualified PaymentState deriving stock (Eq, Show) deriving (Value) via PgEnum "public.\"payment_state\"" PaymentState - -- The test database is "postgres". newtype InDatabase = InDatabase PaymentState deriving stock (Eq, Show) deriving (Value) via PgEnum "postgres.public.payment_state" PaymentState - newtype Status = Status PaymentState deriving stock (Eq, Show) deriving (Value) via Domain "payment_status" PaymentState - newtype Label = Label Text deriving stock (Eq, Show) deriving newtype (Value) - newtype Cents = Cents Int64 deriving stock (Eq, Show) deriving (Value) via Domain "cents" Int64 - -- | Run a statement on the test database. runStatement :: Text -> params -> Statement params result -> IO result runStatement conn params statement = do@@ -631,7 +619,6 @@ Connection.release c either (\e -> expectationFailure (show e) >> error "unreachable") pure result - runtimeSpec :: TestDef '[Text] () runtimeSpec = do itWithOuter "reads a varchar column as Text" \conn ->@@ -715,9 +702,9 @@ runStatement conn ("blue" :: Text, 2 :: Int64) [Inferred.resultlessStatement|insert into tag (label, id) values ($1, $2)|] `shouldReturn` () ---- | A quote as hasql-check-hie writes it: its SQL, and the qualified name and--- Postgres type of each parameter and result column.+{- | A quote as hasql-check-hie writes it: its SQL, and the qualified name and+Postgres type of each parameter and result column.+-} inferredQuote :: Text -> Text -> [Column] -> Maybe [Column] -> Text inferredQuote quoter sql params row = "{\"file\":\"src/Fixture.hs\",\"line\":3,\"column\":7,\"quoter\":\""@@ -742,15 +729,12 @@ <> (if c.nullable then "true" else "false") <> "}" - data Column = Column {haskell :: Text, postgres :: Text, nullable :: Bool, labels :: [Text]} - -- | The same column, as a 'Maybe'. optional :: Column -> Column optional c = c{nullable = True} - -- | Run with --inferred on the given quotes and flags. runInferred :: Text -> [String] -> [Text] -> IO (ExitCode, String) runInferred conn args quotes' =@@ -760,12 +744,10 @@ (code, out, err) <- readCreateProcessWithExitCode (proc "hasql-check" (["--database", Text.unpack conn, "--inferred", file] <> args)) "" pure (code, out <> err) - int32, int64, text :: Column int32 = Column "GHC.Internal.Int.Int32" "int4" False [] int64 = Column "GHC.Internal.Int.Int64" "int8" False [] text = Column "Data.Text.Internal.Text" "text" False []- inferredSpec :: TestDef '[Text] () inferredSpec = do