@@ -519,10 +519,13 @@ public ModelsMap postProcessModels(ModelsMap objs) {
519
519
public Map <String , ModelsMap > postProcessAllModels (Map <String , ModelsMap > objs ) {
520
520
final Map <String , ModelsMap > processed = super .postProcessAllModels (objs );
521
521
522
- // TODO: move the logic of these three methods into patchProperty so all CodegenProperty instances get the same treatment
523
- postProcessEnumRefs (processed );
524
- updateValueTypeProperty (processed );
525
- updateNullableTypeProperty (processed );
522
+ Map <String , CodegenModel > enumRefs = new HashMap <>();
523
+ for (Map .Entry <String , ModelsMap > entry : processed .entrySet ()) {
524
+ CodegenModel model = ModelUtils .getModelByName (entry .getKey (), processed );
525
+ if (model .isEnum ) {
526
+ enumRefs .put (model .getClassname (), model );
527
+ }
528
+ }
526
529
527
530
for (Map .Entry <String , ModelsMap > entry : objs .entrySet ()) {
528
531
CodegenModel model = ModelUtils .getModelByName (entry .getKey (), objs );
@@ -532,34 +535,52 @@ public Map<String, ModelsMap> postProcessAllModels(Map<String, ModelsMap> objs)
532
535
// TODO: why do these collections contain different instances?
533
536
// fixing allVars should suffice instead of patching every collection
534
537
for (CodegenProperty property : model .allVars ) {
535
- patchProperty (model , property );
538
+ patchProperty (enumRefs , model , property );
536
539
}
537
540
for (CodegenProperty property : model .vars ) {
538
- patchProperty (model , property );
541
+ patchProperty (enumRefs , model , property );
539
542
}
540
543
for (CodegenProperty property : model .readWriteVars ) {
541
- patchProperty (model , property );
544
+ patchProperty (enumRefs , model , property );
542
545
}
543
546
for (CodegenProperty property : model .optionalVars ) {
544
- patchProperty (model , property );
547
+ patchProperty (enumRefs , model , property );
545
548
}
546
549
for (CodegenProperty property : model .parentVars ) {
547
- patchProperty (model , property );
550
+ patchProperty (enumRefs , model , property );
548
551
}
549
552
for (CodegenProperty property : model .requiredVars ) {
550
- patchProperty (model , property );
553
+ patchProperty (enumRefs , model , property );
551
554
}
552
555
for (CodegenProperty property : model .readOnlyVars ) {
553
- patchProperty (model , property );
556
+ patchProperty (enumRefs , model , property );
554
557
}
555
558
for (CodegenProperty property : model .nonNullableVars ) {
556
- patchProperty (model , property );
559
+ patchProperty (enumRefs , model , property );
557
560
}
558
561
}
559
562
return processed ;
560
563
}
561
564
562
- private void patchProperty (CodegenModel model , CodegenProperty property ) {
565
+ private void patchProperty (Map <String , CodegenModel > enumRefs , CodegenModel model , CodegenProperty property ) {
566
+ if (enumRefs .containsKey (property .dataType )) {
567
+ // Handle any enum properties referred to by $ref.
568
+ // This is different in C# than most other generators, because enums in C# are compiled to integral types,
569
+ // while enums in many other languages are true objects.
570
+ CodegenModel refModel = enumRefs .get (property .dataType );
571
+ property .allowableValues = refModel .allowableValues ;
572
+ property .isEnum = true ;
573
+
574
+ // We do these after updateCodegenPropertyEnum to avoid generalities that don't mesh with C#.
575
+ property .isPrimitiveType = true ;
576
+ }
577
+
578
+ if (!property .isContainer && (nullableType .contains (property .dataType ) || property .isEnum )) {
579
+ property .vendorExtensions .put ("x-csharp-value-type" , true );
580
+ }
581
+
582
+ property .vendorExtensions .put ("x-is-value-type" , isValueType (property ));
583
+
563
584
String tmpPropertyName = escapeReservedWord (model , property .name );
564
585
if (property .name != tmpPropertyName ) {
565
586
// the casing will be wrong if we just set the name to escapeReservedWord
@@ -646,137 +667,6 @@ protected List<Map<String, Object>> buildEnumVars(List<Object> values, String da
646
667
return enumVars ;
647
668
}
648
669
649
- /**
650
- * C# differs from other languages in that Enums are not _true_ objects; enums are compiled to integral types.
651
- * So, in C#, an enum is considers more like a user-defined primitive.
652
- * <p>
653
- * When working with enums, we can't always assume a RefModel is a nullable type (where default(YourType) == null),
654
- * so this post processing runs through all models to find RefModel'd enums. Then, it runs through all vars and modifies
655
- * those vars referencing RefModel'd enums to work the same as inlined enums rather than as objects.
656
- *
657
- * @param models processed models to be further processed for enum references
658
- */
659
- private void postProcessEnumRefs (final Map <String , ModelsMap > models ) {
660
- Map <String , CodegenModel > enumRefs = new HashMap <>();
661
- for (Map .Entry <String , ModelsMap > entry : models .entrySet ()) {
662
- CodegenModel model = ModelUtils .getModelByName (entry .getKey (), models );
663
- if (model .isEnum ) {
664
- enumRefs .put (model .getClassname (), model );
665
- }
666
- }
667
-
668
- for (String openAPIName : models .keySet ()) {
669
- CodegenModel model = ModelUtils .getModelByName (openAPIName , models );
670
- if (model != null ) {
671
- for (CodegenProperty var : model .allVars ) {
672
- if (enumRefs .containsKey (var .dataType )) {
673
- // Handle any enum properties referred to by $ref.
674
- // This is different in C# than most other generators, because enums in C# are compiled to integral types,
675
- // while enums in many other languages are true objects.
676
- CodegenModel refModel = enumRefs .get (var .dataType );
677
- var .allowableValues = refModel .allowableValues ;
678
- var .isEnum = true ;
679
-
680
- // We do these after updateCodegenPropertyEnum to avoid generalities that don't mesh with C#.
681
- var .isPrimitiveType = true ;
682
- }
683
- }
684
- for (CodegenProperty var : model .vars ) {
685
- if (enumRefs .containsKey (var .dataType )) {
686
- // Handle any enum properties referred to by $ref.
687
- // This is different in C# than most other generators, because enums in C# are compiled to integral types,
688
- // while enums in many other languages are true objects.
689
- CodegenModel refModel = enumRefs .get (var .dataType );
690
- var .allowableValues = refModel .allowableValues ;
691
- var .isEnum = true ;
692
-
693
- // We do these after updateCodegenPropertyEnum to avoid generalities that don't mesh with C#.
694
- var .isPrimitiveType = true ;
695
- }
696
- }
697
- for (CodegenProperty var : model .readWriteVars ) {
698
- if (enumRefs .containsKey (var .dataType )) {
699
- // Handle any enum properties referred to by $ref.
700
- // This is different in C# than most other generators, because enums in C# are compiled to integral types,
701
- // while enums in many other languages are true objects.
702
- CodegenModel refModel = enumRefs .get (var .dataType );
703
- var .allowableValues = refModel .allowableValues ;
704
- var .isEnum = true ;
705
-
706
- // We do these after updateCodegenPropertyEnum to avoid generalities that don't mesh with C#.
707
- var .isPrimitiveType = true ;
708
- }
709
- }
710
- for (CodegenProperty var : model .readOnlyVars ) {
711
- if (enumRefs .containsKey (var .dataType )) {
712
- // Handle any enum properties referred to by $ref.
713
- // This is different in C# than most other generators, because enums in C# are compiled to integral types,
714
- // while enums in many other languages are true objects.
715
- CodegenModel refModel = enumRefs .get (var .dataType );
716
- var .allowableValues = refModel .allowableValues ;
717
- var .isEnum = true ;
718
-
719
- // We do these after updateCodegenPropertyEnum to avoid generalities that don't mesh with C#.
720
- var .isPrimitiveType = true ;
721
- }
722
- }
723
-
724
- /* Comment out the following as model.dataType is always the model name, eg. OuterIntegerEnum,
725
- * and this will fix the integer enum via #9035.
726
- * Only x-enum-byte is used in the template but it won't work due to the bug mentioned above.
727
- * A better solution is to introduce isLong, isInteger, etc in the DefaultCodegen
728
- * so that there is no need for each generator to post-process model enums.
729
- *
730
- // We're looping all models here.
731
- if (model.isEnum) {
732
- // We now need to make allowableValues.enumVars look like the context of CodegenProperty
733
- Boolean isString = false;
734
- Boolean isInteger = false;
735
- Boolean isLong = false;
736
- Boolean isByte = false;
737
-
738
- if (model.dataType.startsWith("byte")) {
739
- // C# Actually supports byte and short enums, swagger spec only supports byte.
740
- isByte = true;
741
- model.vendorExtensions.put("x-enum-byte", true);
742
- } else if (model.dataType.startsWith("int32")) {
743
- isInteger = true;
744
- model.vendorExtensions.put("x-enum-integer", true);
745
- } else if (model.dataType.startsWith("int64")) {
746
- isLong = true;
747
- model.vendorExtensions.put("x-enum-long", true);
748
- } else {
749
- // C# doesn't support non-integral enums, so we need to treat everything else as strings (e.g. to not lose precision or data integrity)
750
- isString = true;
751
- model.vendorExtensions.put("x-enum-string", true);
752
- }
753
-
754
- // Since we iterate enumVars for modelInnerEnum and enumClass templates, and CodegenModel is missing some of CodegenProperty's properties,
755
- // we can take advantage of Mustache's contextual lookup to add the same "properties" to the model's enumVars scope rather than CodegenProperty's scope.
756
- List<Map<String, String>> enumVars = (ArrayList<Map<String, String>>) model.allowableValues.get("enumVars");
757
- List<Map<String, Object>> newEnumVars = new ArrayList<Map<String, Object>>();
758
- for (Map<String, String> enumVar : enumVars) {
759
- Map<String, Object> mixedVars = new HashMap<String, Object>();
760
- mixedVars.putAll(enumVar);
761
-
762
- mixedVars.put("isString", isString);
763
- mixedVars.put("isLong", isLong);
764
- mixedVars.put("isInteger", isInteger);
765
- mixedVars.put("isByte", isByte);
766
-
767
- newEnumVars.add(mixedVars);
768
- }
769
-
770
- if (!newEnumVars.isEmpty()) {
771
- model.allowableValues.put("enumVars", newEnumVars);
772
- }
773
- } */
774
- } else {
775
- LOGGER .warn ("Expected to retrieve model %s by name, but no model was found. Check your -Dmodels inclusions." , openAPIName );
776
- }
777
- }
778
- }
779
-
780
670
/**
781
671
* Update codegen property's enum by adding "enumVars" (with name and value)
782
672
*
@@ -813,49 +703,6 @@ public void updateCodegenPropertyEnum(CodegenProperty var) {
813
703
}
814
704
}
815
705
816
- /**
817
- * Update property if it is a C# value type
818
- *
819
- * @param models list of all models
820
- */
821
- protected void updateValueTypeProperty (Map <String , ModelsMap > models ) {
822
- for (String openAPIName : models .keySet ()) {
823
- CodegenModel model = ModelUtils .getModelByName (openAPIName , models );
824
- if (model != null ) {
825
- for (CodegenProperty var : model .vars ) {
826
- var .vendorExtensions .put ("x-is-value-type" , isValueType (var ));
827
- }
828
- }
829
- }
830
- }
831
-
832
- /**
833
- * Update property if it is a C# nullable type
834
- *
835
- * @param models list of all models
836
- */
837
- protected void updateNullableTypeProperty (Map <String , ModelsMap > models ) {
838
- for (String openAPIName : models .keySet ()) {
839
- CodegenModel model = ModelUtils .getModelByName (openAPIName , models );
840
- if (model != null ) {
841
- for (CodegenProperty var : model .vars ) {
842
- if (!var .isContainer && (nullableType .contains (var .dataType ) || var .isEnum )) {
843
- var .vendorExtensions .put ("x-csharp-value-type" , true );
844
- }
845
- }
846
-
847
- // https://github.com/OpenAPITools/openapi-generator/issues/12324
848
- // we should not need to iterate both vars and allVars
849
- // the collections dont have the same instance, so we have to do it again
850
- for (CodegenProperty var : model .allVars ) {
851
- if (!var .isContainer && (nullableType .contains (var .dataType ) || var .isEnum )) {
852
- var .vendorExtensions .put ("x-csharp-value-type" , true );
853
- }
854
- }
855
- }
856
- }
857
- }
858
-
859
706
@ Override
860
707
public OperationsMap postProcessOperationsWithModels (OperationsMap objs , List <ModelMap > allModels ) {
861
708
super .postProcessOperationsWithModels (objs , allModels );
0 commit comments