openapi-generator icon indicating copy to clipboard operation
openapi-generator copied to clipboard

[BUG] not nullable property is shown as nullable

Open whirm opened this issue 4 years ago • 4 comments

Bug Report Checklist

  • [X] Have you provided a full/minimal spec to reproduce the issue?
  • [X] Have you validated the input using an OpenAPI validator (example)?
  • [X] Have you tested with the latest master to confirm the issue still exists?
  • [X] Have you searched for related issues/PRs?
  • [X] What's the actual output vs expected output?
  • [ ] [Optional] Sponsorship to speed up the bug fix or feature request (example)
Description

The minimal declaration file pasted below results in the Bar.notNullable property getting isNullable: "true" set.

openapi-generator version

Current master (40018c333d55f311620398b6a73c903187b8da75)

It's a regresssion.

OpenAPI declaration file content or url
---
openapi: 3.0.3
info:
  title: Foo
  version: v1
servers:
- url: /
  description: Foo
paths:
  /foo:
    post:
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Bar'
      responses:
        "200":
          description: OK
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Bar'
components:
  schemas:
    Bar:
      required:
      - foo
      type: object
      properties:
        notNullable:
          allOf:
          - $ref: '#/components/schemas/EnumFoo'
            nullable: false
    EnumFoo:
      enum:
      - FOO
      - BAR
      type: string

Generation Details
Steps to reproduce
 openapi-generator-cli generate -g rust -o out -i openapi.yml --global-property debugModels=true 

Cheers!

whirm avatar Nov 04 '21 15:11 whirm

I'm having the same issue, using the typescript-angular generator. Note that it only happens when using allOf. If the following schema is used instead, the field is not generated as nullable:

properties:
  notNullable:
    $ref: '#/components/schemas/EnumFoo'

The change in behavior happened in 5.3.0. In version 5.2.1 the field was generated as non-nullable.

magnusbakken avatar Dec 09 '21 12:12 magnusbakken

@spacether Sorry for the ping, but I saw that you replied to the attempt to fix this with a justification for the current behavior, and I was wondering if you'd be able to answer a question.

I just ran into this confusing behavior and was wondering whether it's even possible to express what we want to do. Currently our project has essentially your first example but the property has a top-level $ref rather than having it under allOf:

components:
  schemas:
    Event:
      required:
        - motionStatus
      type: object
      properties:
        motionStatus:
          - $ref: "#/components/schemas/MotionStatus"
    MotionStatus:
      type: string
      enum:
        - inMotion
        - stationary

We now want to add a description to that field, which the schema generator does by pushing the $ref down into an allOf since you can't have a description property on the same level as the $ref. If the current behavior is the one intended, is there any way according to the OpenAPI specification to add a description to Event.motionStatus without the resulting property being nullable?

kyrias avatar Oct 14 '22 11:10 kyrias

There cannot be keywords adjacent to $ref per openapi v3.0.3 and lower. Nullable false has no impact on schemas per an issue in the openapi spec repo.

Please copy the rust language committee as I am unfamiliar with that generator. Have you tried making the enum schema inline rather than a ref? Using ref should fix the nullability issue as the field should be the of type enum in generators that support enums.

spacether avatar Oct 14 '22 14:10 spacether

We're using the typescript-fetch generator for the record.

Have you tried making the enum schema inline rather than a ref?

We're generating the schema from our backend application through a third-party library so we don't really have the option of inlining it, but we're also using most of these kinds of enums in multiple places so we wouldn't really want them inline either.

Using ref should fix the nullability issue as the field should be the of type enum in generators that support enums.

I don't understand your point. The MotionStatus enum is generated as an enum, yes, but what does that have to do with the property ref-ing it?

To give a reproducible example, with this:

openapi: "3.0.0"

info:
  title: foo
  version: "1.0.0"

paths:
  /foo/:
    get:
      responses:
        200:
          description:
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/Event"

components:
  schemas:
    Event:
      required:
        - motionStatus
      type: object
      properties:
        motionStatus:
          $ref: "#/components/schemas/MotionStatus"
    MotionStatus:
      type: string
      enum:
        - inMotion
        - stationary

we're getting the following typescript:

export interface Event {
    /**
     * 
     * @type {MotionStatus}
     * @memberof Event
     */
    motionStatus: MotionStatus;
}

if we add a description we'd instead get:

openapi: "3.0.0"
 
info:
  title: foo
  version: "1.0.0"

paths:
  /foo/:
    get:
      responses:
        200:
          description:
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/Event"

components:
  schemas:
    Event:
      required:
        - motionStatus
      type: object
      properties:
        motionStatus:
          description: foo
          allOf:
            - $ref: "#/components/schemas/MotionStatus"
    MotionStatus:
      type: string
      enum:
        - inMotion
        - stationary

and the generated code becomes:

export interface Event {
    /**
     * foo
     * @type {MotionStatus}
     * @memberof Event
     */
    motionStatus: MotionStatus | null;
}

kyrias avatar Oct 17 '22 07:10 kyrias