@@ -12,7 +12,7 @@ First, we need some language extensions because Squeal uses modern GHC
1212features.
1313
1414>>> :set -XDataKinds -XDeriveGeneric -XOverloadedLabels
15−>>> :set -XOverloadedStrings -XTypeApplications -XTypeOperators
15+>>> :set -XOverloadedStrings -XTypeApplications -XTypeOperators -XGADTs
1616
1717We'll need some imports.
1818
@@ -117,25 +117,18 @@ of our inserts.
117117
118118>>> :{
119119let
120− insertUser :: Manipulation Schema '[ 'NotNull 'PGtext ] '[ "fromOnly" ::: 'NotNull 'PGint4 ]
121− insertUser = insertInto #users
122− (Values_ (defaultAs #id :* param @1 `as` #name))
123− (OnConflict (OnConstraint #pk_users) DoNothing) (Returning (#id `as` #fromOnly))
124−:}
125−
126−>>> :{
127−let
128− insertEmail :: Manipulation Schema '[ 'NotNull 'PGint4, 'Null 'PGtext] '[]
129− insertEmail = insertInto #emails
130− (Values_ (defaultAs #id :* param @1 `as` #user_id :* param @2 `as` #email))
131− (OnConflict (OnConstraint #pk_emails) DoNothing) (Returning Nil)
120+ insertUser :: Manipulation Schema '[ 'NotNull 'PGtext, 'Null 'PGtext ] '[]
121+ insertUser = with (u `as` #u) e
122+ where
123+ u = insertInto #users
124+ (Values_ (defaultAs #id :* param @1 `as` #name))
125+ OnConflictDoRaise (Returning (#id :* param @2 `as` #email))
126+ e = insertInto_ #emails
127+ (Select (defaultAs #id :* #u ! #id `as` #user_id :* #u ! #email) (from (view #u)))
132128:}
133129
134130>>> printSQL insertUser
135−INSERT INTO "users" ("id", "name") VALUES (DEFAULT, ($1 :: text)) ON CONFLICT ON CONSTRAINT "pk_users" DO NOTHING RETURNING "id" AS "fromOnly"
136−
137−>>> printSQL insertEmail
138−INSERT INTO "emails" ("id", "user_id", "email") VALUES (DEFAULT, ($1 :: int4), ($2 :: text)) ON CONFLICT ON CONSTRAINT "pk_emails" DO NOTHING
131+WITH "u" AS (INSERT INTO "users" ("id", "name") VALUES (DEFAULT, ($1 :: text)) RETURNING "id" AS "id", ($2 :: text) AS "email") INSERT INTO "emails" ("user_id", "email") SELECT "u"."id", "u"."email" FROM "u" AS "u"
139132
140133Next we write a `Query` to retrieve users from the database. We're not
141134interested in the ids here, just the usernames and email addresses. We
@@ -191,9 +184,7 @@ transformer and when the schema doesn't change we can use `Monad` and
191184let
192185 session :: PQ Schema Schema IO ()
193186 session = do
194− idResults <- traversePrepared insertUser (Only . userName <$> users)
195− ids <- traverse (fmap fromOnly . getRow 0) idResults
196− traversePrepared_ insertEmail (zip (ids :: [Int32]) (userEmail <$> users))
187+ _ <- traversePrepared_ insertUser users
197188 usersResult <- runQuery getUsers
198189 usersRows <- getRows usersResult
199190 liftBase $ print (usersRows :: [User])