@@ -109,6 +109,8 @@ async fn map_single<'a>(
109109 subsystem : & ' a PostgresGraphQLSubsystem ,
110110 request_context : & ' a RequestContext < ' a > ,
111111) -> Result < ( InsertionRow , Vec < AbstractPredicate > ) , PostgresExecutionError > {
112+ let enriched_argument = enrich_argument_for_access ( data_type, argument, subsystem) ;
113+ let access_input_value = enriched_argument. as_ref ( ) . unwrap_or ( argument) ;
112114 let AccessCheckOutcome {
113115 precheck_predicate, ..
114116 } = check_access (
@@ -118,9 +120,9 @@ async fn map_single<'a>(
118120 subsystem,
119121 request_context,
120122 Some ( & AccessInput {
121- value : argument ,
123+ value : access_input_value ,
122124 ignore_missing_value : true ,
123- aliases : HashMap :: new ( ) ,
125+ aliases : Default :: default ( ) ,
124126 } ) ,
125127 )
126128 . await ?;
@@ -201,6 +203,77 @@ async fn map_single<'a>(
201203 Ok ( ( InsertionRow { elems : row? } , vec ! [ precheck_predicate] ) )
202204}
203205
206+ fn enrich_argument_for_access (
207+ data_type : & MutationType ,
208+ argument : & Val ,
209+ subsystem : & PostgresGraphQLSubsystem ,
210+ ) -> Option < Val > {
211+ let argument_object = match argument {
212+ Val :: Object ( map) => map,
213+ _ => return None ,
214+ } ;
215+
216+ let mut column_to_field: HashMap < ColumnId , & str > = HashMap :: new ( ) ;
217+ for field in & data_type. fields {
218+ if let PostgresRelation :: Scalar { column_id, .. } = & field. relation {
219+ column_to_field. insert ( * column_id, field. name . as_str ( ) ) ;
220+ }
221+ }
222+
223+ let mut enriched = argument_object. clone ( ) ;
224+ let mut modified = false ;
225+
226+ for field in & data_type. fields {
227+ if enriched. contains_key ( & field. name ) {
228+ continue ;
229+ }
230+
231+ if let PostgresRelation :: ManyToOne { relation, .. } = & field. relation {
232+ let relation_details = relation
233+ . relation_id
234+ . deref ( & subsystem. core_subsystem . database ) ;
235+
236+ let mut related_fields: HashMap < String , Val > = HashMap :: new ( ) ;
237+
238+ for ( pair, pk_field_id) in relation_details
239+ . column_pairs
240+ . iter ( )
241+ . zip ( relation. foreign_pk_field_ids . iter ( ) )
242+ {
243+ let fk_field_name = match column_to_field. get ( & pair. self_column_id ) {
244+ Some ( name) => * name,
245+ None => {
246+ related_fields. clear ( ) ;
247+ break ;
248+ }
249+ } ;
250+
251+ let fk_value = match argument_object. get ( fk_field_name) {
252+ Some ( value) => value. clone ( ) ,
253+ None => {
254+ related_fields. clear ( ) ;
255+ break ;
256+ }
257+ } ;
258+
259+ let pk_field = pk_field_id. resolve ( & subsystem. core_subsystem . entity_types ) ;
260+ related_fields. insert ( pk_field. name . clone ( ) , fk_value) ;
261+ }
262+
263+ if !related_fields. is_empty ( ) {
264+ enriched. insert ( field. name . clone ( ) , Val :: Object ( related_fields) ) ;
265+ modified = true ;
266+ }
267+ }
268+ }
269+
270+ if modified {
271+ Some ( Val :: Object ( enriched) )
272+ } else {
273+ None
274+ }
275+ }
276+
204277async fn map_self_column < ' a > (
205278 key_column_id : ColumnId ,
206279 field : & ' a PostgresField < MutationType > ,
0 commit comments