@@ -382,136 +382,150 @@ format_default_translators(AnRes, Opts) ->
382382
383383format_default_map_translators (# anres {map_types = MapTypes ,
384384 map_value_types = MVT }= AnRes , Opts ) ->
385+ DoMergers = gpb_lib :get_gen_mergers (Opts ),
386+ DoEncoders = gpb_lib :get_gen_encoders (Opts ),
387+ DoDecoders = gpb_lib :get_gen_decoders (Opts ),
385388 HaveMaps = sets :size (MapTypes ) > 0 ,
386389 {HaveMapSubmsgs , HaveMapNonSubmsgs } = MVT ,
390+ {M ,K ,V } = {? expr (M ), ? expr (K ), ? expr (V )},
387391 [% % Auxiliary helpers in case of fields of type map<_,_>
388- [case gpb_lib :get_2tuples_or_maps_for_maptype_fields_by_opts (Opts ) of
389- '2tuples' ->
390- [inline_attr (mt_maptuple_to_pseudomsg_r ,2 ),
391- gpb_codegen :format_fn (
392- mt_maptuple_to_pseudomsg_r ,
393- fun ({K ,V },RName ) -> {RName ,K ,V } end ),
394- " \n " ,
395- inline_attr (mt_empty_map_r ,0 ),
396- gpb_codegen :format_fn (
397- mt_empty_map_r ,
398- fun () -> [] end ),
399- [[inline_attr (mt_add_item_r ,2 ),
400- gpb_codegen :format_fn (
401- mt_add_item_r ,
402- fun ({_RName ,K ,V }, Acc ) -> [{K ,V } | Acc ] end ),
403- " \n " ]
404- || HaveMapNonSubmsgs ],
405- [[inline_attr (mt_add_item_r_verify_value ,2 ),
406- gpb_codegen :format_fn (
407- mt_add_item_r_verify_value ,
408- fun ({_ ,_ ,undefined }, _ ) -> error ({gpb_error , missing_value });
409- ({_RName ,K ,V }, Acc ) -> [{K ,V } | Acc ]
410- end ),
411- " \n " ]
412- || HaveMapSubmsgs ],
413- inline_attr (mt_finalize_items_r ,1 ),
414- gpb_codegen :format_fn (
415- mt_finalize_items_r ,
416- fun (Acc ) ->
417- % % Reverse to store the items in the dict
418- % % in the same order they were decoded,
419- % % in case a key occurs more than once.
420- mt_finalize_items_r_aux (lists :reverse (Acc ),
421- dict :new ())
422- end ),
423- gpb_codegen :format_fn (
424- mt_finalize_items_r_aux ,
425- fun ([{K ,V } | Tl ], D ) -> call_self (Tl , dict :store (K , V , D ));
426- ([], D ) -> dict :to_list (D )
427- end ),
428- " \n " ];
429- maps ->
430- {M ,K ,V } = {? expr (M ), ? expr (K ), ? expr (V )},
431- [inline_attr (mt_maptuple_to_pseudomsg_m ,1 ),
432- gpb_codegen :format_fn (
433- mt_maptuple_to_pseudomsg_m ,
434- fun ({K ,V }) -> '#{key => K, value => V}' end ,
435- [replace_tree ('#{key => K, value => V}' ,
436- gpb_lib :map_create ([{key ,K }, {value ,V }],
437- Opts ))]),
438- " \n " ,
439- inline_attr (mt_map_to_list_m ,1 ),
440- gpb_codegen :format_fn (
441- mt_map_to_list_m ,
442- fun (M ) -> maps :to_list (M ) end ),
443- " \n " ,
444- inline_attr (mt_empty_map_m ,0 ),
445- gpb_codegen :format_fn (
446- mt_empty_map_m ,
447- fun () -> '#{}' end ,
448- [replace_tree ('#{}' , gpb_lib :map_create ([], []))]),
449- " \n " ,
450- [[inline_attr (mt_add_item_m ,2 ),
451- case gpb_lib :target_has_variable_key_map_update (Opts ) of
452- true ->
453- gpb_codegen :format_fn (
454- mt_add_item_m ,
455- fun ('#{key := K,value := V}' , M ) -> 'M#{K => V}' end ,
456- [replace_tree (
457- '#{key := K,value := V}' ,
458- gpb_lib :map_match ([{key ,K }, {value ,V }], Opts )),
459- replace_tree (
460- 'M#{K => V}' ,
461- gpb_lib :map_set (M , [{K ,V }], []))]);
462- false ->
463- gpb_codegen :format_fn (
464- mt_add_item_m ,
465- fun ('#{key := K,value := V}' , M ) ->
466- maps :put ('K' , 'V' , 'M' )
467- end ,
468- [replace_tree (
469- '#{key := K,value := V}' ,
470- gpb_lib :map_match ([{key ,K }, {value ,V }], Opts )),
471- replace_tree ('K' , K ),
472- replace_tree ('V' , V ),
473- replace_tree ('M' , M )])
474- end ]
475- || HaveMapNonSubmsgs ],
476- [[inline_attr (mt_add_item_m_verify_value ,2 ),
477- case gpb_lib :target_has_variable_key_map_update (Opts ) of
478- true ->
479- gpb_codegen :format_fn (
480- mt_add_item_m_verify_value ,
481- fun ('#{key := K,value := V}' , M ) ->
482- if V =:= '$undef' ->
483- error ({gpb_error , missing_value });
484- true ->
485- 'M#{K => V}'
486- end
487- end ,
488- [replace_tree (
489- '#{key := K,value := V}' ,
490- gpb_lib :map_match ([{key ,K }, {value ,V }], Opts )),
491- replace_tree (
492- 'M#{K => V}' ,
493- gpb_lib :map_set (M , [{K ,V }], []))]);
494- false ->
495- gpb_codegen :format_fn (
496- mt_add_item_m_verify_value ,
497- fun ('#{key := K,value := V}' , M ) ->
498- if V =:= '$undef' ->
499- error ({gpb_error , missing_value });
500- true ->
501- maps :put ('K' , 'V' , 'M' )
502- end
503- end ,
504- [replace_tree (
505- '#{key := K,value := V}' ,
506- gpb_lib :map_match ([{key ,K }, {value ,V }], Opts )),
507- replace_tree ('K' , K ),
508- replace_tree ('V' , V ),
509- replace_tree ('M' , M )])
510- end ]
511- || HaveMapSubmsgs ],
512- " \n " ]
513- end ,
514- format_default_merge_translators (AnRes , Opts )]
392+ [[% % If encoders:
393+ case gpb_lib :get_2tuples_or_maps_for_maptype_fields_by_opts (Opts ) of
394+ '2tuples' ->
395+ [inline_attr (mt_maptuple_to_pseudomsg_r ,2 ),
396+ gpb_codegen :format_fn (
397+ mt_maptuple_to_pseudomsg_r ,
398+ fun ({K ,V },RName ) -> {RName ,K ,V } end )];
399+ maps ->
400+ [inline_attr (mt_maptuple_to_pseudomsg_m ,1 ),
401+ gpb_codegen :format_fn (
402+ mt_maptuple_to_pseudomsg_m ,
403+ fun ({K ,V }) -> '#{key => K, value => V}' end ,
404+ [replace_tree ('#{key => K, value => V}' ,
405+ gpb_lib :map_create ([{key ,K }, {value ,V }],
406+ Opts ))]),
407+ " \n " ,
408+ inline_attr (mt_map_to_list_m ,1 ),
409+ gpb_codegen :format_fn (
410+ mt_map_to_list_m ,
411+ fun (M ) -> maps :to_list (M ) end )]
412+ end
413+ || DoEncoders ],
414+ " \n " ,
415+ [% % If decoders:
416+ case gpb_lib :get_2tuples_or_maps_for_maptype_fields_by_opts (Opts ) of
417+ '2tuples' ->
418+ [inline_attr (mt_empty_map_r ,0 ),
419+ gpb_codegen :format_fn (
420+ mt_empty_map_r ,
421+ fun () -> [] end ),
422+ [[inline_attr (mt_add_item_r ,2 ),
423+ gpb_codegen :format_fn (
424+ mt_add_item_r ,
425+ fun ({_RName ,K ,V }, Acc ) -> [{K ,V } | Acc ] end ),
426+ " \n " ]
427+ || HaveMapNonSubmsgs ],
428+ [[inline_attr (mt_add_item_r_verify_value ,2 ),
429+ gpb_codegen :format_fn (
430+ mt_add_item_r_verify_value ,
431+ fun ({_ ,_ ,undefined }, _ ) ->
432+ error ({gpb_error , missing_value });
433+ ({_RName ,K ,V }, Acc ) ->
434+ [{K ,V } | Acc ]
435+ end ),
436+ " \n " ]
437+ || HaveMapSubmsgs ],
438+ inline_attr (mt_finalize_items_r ,1 ),
439+ gpb_codegen :format_fn (
440+ mt_finalize_items_r ,
441+ fun (Acc ) ->
442+ % % Reverse to store the items in the dict
443+ % % in the same order they were decoded,
444+ % % in case a key occurs more than once.
445+ mt_finalize_items_r_aux (lists :reverse (Acc ),
446+ dict :new ())
447+ end ),
448+ gpb_codegen :format_fn (
449+ mt_finalize_items_r_aux ,
450+ fun ([{K ,V } | Tl ], D ) -> call_self (Tl , dict :store (K , V , D ));
451+ ([], D ) -> dict :to_list (D )
452+ end )];
453+ maps ->
454+ [inline_attr (mt_empty_map_m ,0 ),
455+ gpb_codegen :format_fn (
456+ mt_empty_map_m ,
457+ fun () -> '#{}' end ,
458+ [replace_tree ('#{}' , gpb_lib :map_create ([], []))]),
459+ " \n " ,
460+ [[inline_attr (mt_add_item_m ,2 ),
461+ case gpb_lib :target_has_variable_key_map_update (Opts ) of
462+ true ->
463+ gpb_codegen :format_fn (
464+ mt_add_item_m ,
465+ fun ('#{key := K,value := V}' , M ) ->
466+ 'M#{K => V}'
467+ end ,
468+ [replace_tree (
469+ '#{key := K,value := V}' ,
470+ gpb_lib :map_match ([{key ,K }, {value ,V }], Opts )),
471+ replace_tree (
472+ 'M#{K => V}' ,
473+ gpb_lib :map_set (M , [{K ,V }], []))]);
474+ false ->
475+ gpb_codegen :format_fn (
476+ mt_add_item_m ,
477+ fun ('#{key := K,value := V}' , M ) ->
478+ maps :put ('K' , 'V' , 'M' )
479+ end ,
480+ [replace_tree (
481+ '#{key := K,value := V}' ,
482+ gpb_lib :map_match ([{key ,K }, {value ,V }], Opts )),
483+ replace_tree ('K' , K ),
484+ replace_tree ('V' , V ),
485+ replace_tree ('M' , M )])
486+ end ]
487+ || HaveMapNonSubmsgs ],
488+ [[inline_attr (mt_add_item_m_verify_value ,2 ),
489+ case gpb_lib :target_has_variable_key_map_update (Opts ) of
490+ true ->
491+ gpb_codegen :format_fn (
492+ mt_add_item_m_verify_value ,
493+ fun ('#{key := K,value := V}' , M ) ->
494+ if V =:= '$undef' ->
495+ error ({gpb_error , missing_value });
496+ true ->
497+ 'M#{K => V}'
498+ end
499+ end ,
500+ [replace_tree (
501+ '#{key := K,value := V}' ,
502+ gpb_lib :map_match ([{key ,K }, {value ,V }], Opts )),
503+ replace_tree (
504+ 'M#{K => V}' ,
505+ gpb_lib :map_set (M , [{K ,V }], []))]);
506+ false ->
507+ gpb_codegen :format_fn (
508+ mt_add_item_m_verify_value ,
509+ fun ('#{key := K,value := V}' , M ) ->
510+ if V =:= '$undef' ->
511+ error ({gpb_error , missing_value });
512+ true ->
513+ maps :put ('K' , 'V' , 'M' )
514+ end
515+ end ,
516+ [replace_tree (
517+ '#{key := K,value := V}' ,
518+ gpb_lib :map_match ([{key ,K }, {value ,V }], Opts )),
519+ replace_tree ('K' , K ),
520+ replace_tree ('V' , V ),
521+ replace_tree ('M' , M )])
522+ end ]
523+ || HaveMapSubmsgs ]]
524+ end
525+ || DoDecoders ],
526+ " \n " ,
527+ [format_default_merge_translators (AnRes , Opts )
528+ || DoMergers ]]
515529 || HaveMaps ].
516530
517531format_default_merge_translators (# anres {map_types = MapTypes }, Opts ) ->
0 commit comments