1- import { gql , makeExtendSchemaPlugin , Resolvers } from "graphile-utils" ;
1+ import { PgClassExpressionStep } from "@dataplan/pg" ;
2+ import { access , SafeError } from "grafast" ;
3+ import { gql , makeExtendSchemaPlugin , Plans , Resolvers } from "graphile-utils" ;
24
3- import { OurGraphQLContext } from "../graphile.config " ;
5+ import type { } from "../middleware/installPostGraphile " ;
46import { ERROR_MESSAGE_OVERRIDES } from "../utils/handleErrors" ;
57
68const PassportLoginPlugin = makeExtendSchemaPlugin ( ( build ) => {
@@ -14,7 +16,7 @@ const PassportLoginPlugin = makeExtendSchemaPlugin((build) => {
1416 }
1517
1618 type RegisterPayload {
17- user: User! @pgField
19+ user: User!
1820 }
1921
2022 input LoginInput {
@@ -23,7 +25,7 @@ const PassportLoginPlugin = makeExtendSchemaPlugin((build) => {
2325 }
2426
2527 type LoginPayload {
26- user: User! @pgField
28+ user: User!
2729 }
2830
2931 type LogoutPayload {
@@ -85,12 +87,40 @@ const PassportLoginPlugin = makeExtendSchemaPlugin((build) => {
8587 resetPassword(input: ResetPasswordInput!): ResetPasswordPayload
8688 }
8789 ` ;
90+ const userSource = build . input . pgSources . find ( ( s ) => s . name === "users" ) ;
91+ const currentUserIdSource = build . input . pgSources . find (
92+ ( s ) => s . name === "current_user_id"
93+ ) ;
94+ if ( ! userSource || ! currentUserIdSource ) {
95+ throw new Error (
96+ "Couldn't find either the 'users' or 'current_user_id' source"
97+ ) ;
98+ }
99+ const plans : Plans = {
100+ RegisterPayload : {
101+ user ( $obj ) {
102+ const $userId = access ( $obj , "userId" ) ;
103+ return userSource . get ( { id : $userId } ) ;
104+ } ,
105+ } ,
106+ LoginPayload : {
107+ user ( ) {
108+ const $userId = currentUserIdSource . execute ( ) as PgClassExpressionStep <
109+ any ,
110+ any ,
111+ any ,
112+ any ,
113+ any
114+ > ;
115+ return userSource . get ( { id : $userId } ) ;
116+ } ,
117+ } ,
118+ } ;
88119 const resolvers : Resolvers = {
89120 Mutation : {
90- async register ( _mutation , args , context : OurGraphQLContext , resolveInfo ) {
91- const { selectGraphQLResultFromTable } = resolveInfo . graphile ;
121+ async register ( _mutation , args , context : Grafast . Context ) {
92122 const { username, password, email, name, avatarUrl } = args . input ;
93- const { rootPgPool, login, pgClient } = context ;
123+ const { rootPgPool, login, pgSettings } = context ;
94124 try {
95125 // Create a user and create a session for it in the proccess
96126 const {
@@ -123,28 +153,15 @@ const PassportLoginPlugin = makeExtendSchemaPlugin((build) => {
123153 }
124154
125155 if ( details . session_id ) {
126- // Store into transaction
127- await pgClient . query (
128- `select set_config('jwt.claims.session_id', $1, true)` ,
129- [ details . session_id ]
130- ) ;
156+ // Update pgSettings so future queries will use the new session
157+ pgSettings ! [ "jwt.claims.session_id" ] = details . session_id ;
131158
132159 // Tell Passport.js we're logged in
133160 await login ( { session_id : details . session_id } ) ;
134161 }
135162
136- // Fetch the data that was requested from GraphQL, and return it
137- const sql = build . pgSql ;
138- const [ row ] = await selectGraphQLResultFromTable (
139- sql . fragment `app_public.users` ,
140- ( tableAlias , sqlBuilder ) => {
141- sqlBuilder . where (
142- sql . fragment `${ tableAlias } .id = ${ sql . value ( details . user_id ) } `
143- ) ;
144- }
145- ) ;
146163 return {
147- data : row ,
164+ userId : details . user_id ,
148165 } ;
149166 } catch ( e : any ) {
150167 const { code } = e ;
@@ -155,6 +172,7 @@ const PassportLoginPlugin = makeExtendSchemaPlugin((build) => {
155172 ...Object . keys ( ERROR_MESSAGE_OVERRIDES ) ,
156173 ] ;
157174 if ( safeErrorCodes . includes ( code ) ) {
175+ // TODO: make SafeError
158176 throw e ;
159177 } else {
160178 console . error (
@@ -167,10 +185,9 @@ const PassportLoginPlugin = makeExtendSchemaPlugin((build) => {
167185 }
168186 }
169187 } ,
170- async login ( _mutation , args , context : OurGraphQLContext , resolveInfo ) {
171- const { selectGraphQLResultFromTable } = resolveInfo . graphile ;
188+ async login ( _mutation , args , context : Grafast . Context ) {
172189 const { username, password } = args . input ;
173- const { rootPgPool, login, pgClient } = context ;
190+ const { rootPgPool, login, pgSettings } = context ;
174191 try {
175192 // Call our login function to find out if the username/password combination exists
176193 const {
@@ -191,29 +208,15 @@ const PassportLoginPlugin = makeExtendSchemaPlugin((build) => {
191208 await login ( { session_id : session . uuid } ) ;
192209 }
193210
194- // Get session_id from PG
195- await pgClient . query (
196- `select set_config('jwt.claims.session_id', $1, true)` ,
197- [ session . uuid ]
198- ) ;
211+ // Update pgSettings so future queries will use the new session
212+ pgSettings ! [ "jwt.claims.session_id" ] = session . uuid ;
199213
200- // Fetch the data that was requested from GraphQL, and return it
201- const sql = build . pgSql ;
202- const [ row ] = await selectGraphQLResultFromTable (
203- sql . fragment `app_public.users` ,
204- ( tableAlias , sqlBuilder ) => {
205- sqlBuilder . where (
206- sql . fragment `${ tableAlias } .id = app_public.current_user_id()`
207- ) ;
208- }
209- ) ;
210- return {
211- data : row ,
212- } ;
214+ return { } ;
213215 } catch ( e : any ) {
214216 const code = e . extensions ?. code ?? e . code ;
215217 const safeErrorCodes = [ "LOCKD" , "CREDS" ] ;
216218 if ( safeErrorCodes . includes ( code ) ) {
219+ // TODO: throw SafeError
217220 throw e ;
218221 } else {
219222 console . error ( e ) ;
@@ -224,21 +227,18 @@ const PassportLoginPlugin = makeExtendSchemaPlugin((build) => {
224227 }
225228 } ,
226229
227- async logout ( _mutation , _args , context : OurGraphQLContext , _resolveInfo ) {
228- const { pgClient, logout } = context ;
229- await pgClient . query ( "select app_public.logout();" ) ;
230+ async logout ( _mutation , _args , context : Grafast . Context ) {
231+ const { pgSettings, withPgClient, logout } = context ;
232+ await withPgClient ( pgSettings , ( pgClient ) =>
233+ pgClient . query ( { text : "select app_public.logout();" } )
234+ ) ;
230235 await logout ( ) ;
231236 return {
232237 success : true ,
233238 } ;
234239 } ,
235240
236- async resetPassword (
237- _mutation ,
238- args ,
239- context : OurGraphQLContext ,
240- _resolveInfo
241- ) {
241+ async resetPassword ( _mutation , args , context : Grafast . Context ) {
242242 const { rootPgPool } = context ;
243243 const { userId, resetToken, newPassword, clientMutationId } =
244244 args . input ;
@@ -264,6 +264,7 @@ const PassportLoginPlugin = makeExtendSchemaPlugin((build) => {
264264 } ;
265265 return {
266266 typeDefs,
267+ plans,
267268 resolvers,
268269 } ;
269270} ) ;
0 commit comments