-
Notifications
You must be signed in to change notification settings - Fork 882
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Return enums from model getters and make enums follow the standard java naming scheme. #195
Conversation
475c2af
to
1a8aea6
Compare
validateConversion("TLSv1.2", "TLS_V1_2"); | ||
validateConversion("us-east-1", "US_EAST_1"); | ||
validateConversion("io1", "IO1"); | ||
validateConversion("application/vnd.amazonaws.card.generic", "APPLICATION_VND_AMAZONAWS_CARD_GENERIC"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Duplicated from line 49
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good catch!
* | ||
* @param value | ||
* real value | ||
* @return TestEnumClass corresponding to the value | ||
*/ | ||
public static TestEnumClass fromValue(String value) { | ||
if (isBlank(value)) { | ||
throw new IllegalArgumentException("Value cannot be null or empty!"); | ||
if (value == null) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why the change in behavior here?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It was easier to use this way. If the service returned null, you'd have to do a null and isEmpty check before converting it to an enum. This way, a null response from the service is a null enum, and an empty-string response from the service is an UNKNOWN enum.
ab2faeb
to
7ee7b13
Compare
@@ -307,11 +448,29 @@ public SubTypeOne polymorphicTypeWithoutSubTypes() { | |||
|
|||
/** | |||
* Returns the value of the EnumType property for this object. | |||
* <p> | |||
* If the service returns an enum value that is not available in the current SDK version, {@link #enumType} will | |||
* return {@link EnumType#UNKNOWN}. The raw value returned by the service is available from {@link #enumTypeString}. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We should use SDK_UNKNOWN or something like that to prevent clash with service define values
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
+1
* The new value for the ListOfEnums property for this object. | ||
* @return Returns a reference to this object so that method calls can be chained together. | ||
*/ | ||
Builder listOfEnums(String... listOfEnums); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why can't you set values via the enum?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We'll need to add support for that. We just don't have it yet, and I didn't want to make this PR any longer.
.containsExactly(new SimpleImmutableEntry<>(EnumType.ENUM_VALUE1, EnumType.UNKNOWN)); | ||
} | ||
|
||
private EnumType simulateUnmarshallingEnum(String value) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Seems kind of a weird name. You're really just testing the builder behavior here.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm doing what the unmarshaller does. I'll add a comment.
String sanitizedEnumValue = enumValue.replace("::", ":").replace("/", "").replace("(", "") | ||
.replace(")", ""); | ||
// Special cases | ||
result = result.replaceAll("IoT", "IOT") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Should we treat these as customizations rather then put them in Core?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do we have the feature in place to customize enum names? I didn't see anything like that.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not sure, but we can add one. In general we try not to put service specific customizations in the code gen.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That's fair - it's not good to have service-specific stuff in the generator.
IoT in this case isn't service-specific. I'm not aware of any service using it in their enums, but they may in the future and we'd probably not notice it (generating IO_T instead).
It's just textORcsv that is service-specific in this PR. Because it's just this one example, I'd vote we follow the rule-of-three and add a customization when we have more cases in which we would use it.
I don't think it is likely that more cases like this are going to happen. AWS service owners are warned now if their enums don't follow SCREAMING_CASE conventions. If something does happen to get through review: (a) we'll catch it before it's released and have the service owner fix their model, or (b) we won't catch it before it's released and at that point we can't change it anyway.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Should the IoT case just be baked into the logic then. I.E. is there any value where we'd want to separate a single capital letter via underscore? If not can we just treat that as part of the previous word boundary?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sounds good to me.
|
||
if (!result.matches("^[A-Z][A-Z0-9_]*$")) { | ||
String attempt = result; | ||
log.warn(() -> "Invalid enum member generated for input '" + enumValue + "'. Best attempt: '" + attempt + "' If this " |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why not kill it here?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We have customizations that remove these values in a later part of code generation.
result.add(enumMemberGetter(member)); | ||
} | ||
|
||
result.add(nonEnumMemberGetter(member)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Name is kind of unintuitive as you'd call it for enums too it would just emit the string one.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm trying to say "generate the non-enum getter for this member". For enums, that's a string. What name would you like me to use instead?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd just call it memberGetter since it's the primary getter for any type of field, the enum one is the convenience one.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
👍
naming scheme. Where appropriate, enums are now returned from model getters instead of strings, which have been moved to a separate method that indicates its value is a string. Generated enums now follow the SCREAMING_CASE convention instead of the PascalCase that was previously used.
Where appropriate, enums are now returned from model getters instead of
strings, which have been moved to a separate method that indicates its
value is a string.
Generated enums now follow the SCREAMING_CASE convention instead of the
PascalCase that was previously used.