Skip to content

[Bug][Java] jaxrs-cxf-client missing annotation when generating Enum #5077

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

Open
jvs64893 opened this issue Jan 22, 2020 · 4 comments · May be fixed by #21101
Open

[Bug][Java] jaxrs-cxf-client missing annotation when generating Enum #5077

jvs64893 opened this issue Jan 22, 2020 · 4 comments · May be fixed by #21101

Comments

@jvs64893
Copy link

Description

Integer Enums are generated with missing @JsonCreator annotation and causing InvalidFormatException while deserialization.

com.fasterxml.jackson.databind.exc.InvalidFormatException: Cannot deserialize value of type `package.class$CodeEnum` from number 3: index value outside legal index range [0..2]

The Enum is defined for values {1, 2, 3} but the deserialization is trying to work with the index, so it is wrong for values 1 and 2 and fails for value 3.

openapi-generator version

4.2.2

OpenAPI declaration file content or url

yaml file:

components:
  schemas:
    CodeResponse:
      type: object
      required: [isValid]
      properties:
        isValid:
          type: boolean
        serial:
          type: string
          pattern: /^[abcdefghkmnpqrstuvwxyz23456789]{7,}$/i
        discount:
          type: integer
          format: int32
          minimum: 0
        reason:
          type: object
          required: [code, message]
          properties:
            code:
              type: integer
              enum: [1, 2, 3]
            message:
              type: object
              required: [en, de]
              properties:
                en:
                  type: string
                de:
                  type: string

generated java code:

@XmlType(name="CodeEnum")
@XmlEnum(Integer.class)
public enum CodeEnum {

@XmlEnumValue("1") NUMBER_1(Integer.valueOf(1)), @XmlEnumValue("2") NUMBER_2(Integer.valueOf(2)), @XmlEnumValue("3") NUMBER_3(Integer.valueOf(3));


    private Integer value;

    CodeEnum (Integer v) {
        value = v;
    }

    public Integer value() {
        return value;
    }

    @Override
    public String toString() {
        return String.valueOf(value);
    }

    public static CodeEnum fromValue(Integer value) {
        for (CodeEnum b : CodeEnum.values()) {
            if (b.value.equals(value)) {
                return b;
            }
        }
        throw new IllegalArgumentException("Unexpected value '" + value + "'");
    }
}
Command line used for generation

Gradle task:

  group = "build"
  description = "..."
  generatorName = "jaxrs-cxf-client"
  inputSpec = "...".toString()
  outputDir = "...".toString()
  apiPackage = "..."
  invokerPackage = "..."
  modelPackage = "..."
  generateModelTests = false
  generateModelDocumentation = false
  generateApiTests = false
  validateSpec = false
  withXml = false
  configOptions = [
      dateLibrary        : "java8",
      booleanGetterPrefix: "is"
  ]
Steps to reproduce
  • deserialize respsonse object like:
{
  "isValid": false,
  "reason": {
    "code": 3,
    "message": {
      "en": "...",
      "de": "..."
    }
  }
}
Related issues/PRs
Suggest a fix/enhancement

Adding @JsonCreator annotation to generated fromValue() method:

    @JsonCreator
    public static CodeEnum fromValue(Integer value) {
        for (CodeEnum b : CodeEnum.values()) {
            if (b.value.equals(value)) {
                return b;
            }
        }
        throw new IllegalArgumentException("Unexpected value '" + value + "'");
    }
@arnis87
Copy link

arnis87 commented Jan 12, 2021

Similar behavior occurs when enum name is defined in camel-case and during code generation it gets value for the original name used in api and name in upper case. When this is (de)serialized it does not use this value but name instead.

Can be fixed also with @JsonCreator annotation on the generated fromValue(String) method.

Currently the only workaround seems to be to override the enumOuterClass.mustache file locally with the said annotation in place

@hamburml
Copy link
Contributor

hamburml commented Sep 6, 2021

@arnis87 Can you please provide an example? Thanks!

@arnis87
Copy link

arnis87 commented Sep 6, 2021

Hmm, This was some time ago and do not remember exact details but something like this:
I have json defined as

...
"Blacklisted": {
            "$ref": "#/components/schemas/BlacklistType"
          },
...
"BlacklistType": {
        "enum": [
          "NotListed",
          "Denied",
          "Warning"
        ],
        "type": "string"
      }

This is then generated into java:

public enum BlacklistType {
  
  NOTLISTED("NotListed"),
  
  DENIED("Denied"),
  
  WARNING("Warning");

  private String value;

  BlacklistType(String value) {
    this.value = value;
  }

  @Override
  public String toString() {
    return String.valueOf(value);
  }

  public static BlacklistType fromValue(String value) {
    for (BlacklistType b : BlacklistType.values()) {
      if (b.value.equals(value)) {
        return b;
      }
    }
    throw new IllegalArgumentException("Unexpected value '" + value + "'");
  }
  
}

Notice that the value for the java enum is same as in the json definition and name is all caps. However when request is made filling the object with enum setBlacklisted(BlacklistType.NOTLISTED) it gets serialized into string:
"Blacklisted" : "NOTLISTED", but due to JSON contract the expected value is ins serialized string is NotListed

@jockep123
Copy link

Is this bug solved yet? If yes, which release has it?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

4 participants