question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Invalid interface generated by import when `allOf` is used with an object type

See original GitHub issue

Describe the bug The code generated by importing an OpenAPI definition that featured a requestBody using allOf to combine multiple types, including an object type, is invalid, and the fixed version of that code does not match the semantics of the OpenAPI definition.

To Reproduce I imported the following OpenAPI definition

openapi: 3.1.0
info:
    title: Customer API
    version: "1.0"
    description: ""
paths:
    /customers/{CustomerId}:
        patch:
            operationId: api.customers.update
            tags:
                - Customer
            requestBody:
                description: Update customer with properties to be changed
                content:
                    application/json:
                        schema:
                            allOf:
                                - $ref: "#/components/schemas/CustomerProperties"
                                - $ref: "#/components/schemas/CustomerRequiredProperties"
                                - type: object
                                  properties:
                                      Segment:
                                          nullable: true
            parameters:
                - $ref: "#/components/parameters/CustomerId"
            responses:
                204:
                    description: Updated
components:
    schemas:
        CustomerProperties:
            type: object
            properties:
                FirstName:
                    type: string
                LastName:
                    type: string
                DOB:
                    type: string
                    format: date-time
                Segment:
                    type: string
                    enum:
                        - Young
                        - MiddleAged
                        - Old
                        - Moribund
        CustomerRequiredProperties:
            type: object
            required:
                - FirstName
                - LastName
                - DOB
        Id:
            type: integer
    parameters:
        CustomerId:
            name: CustomerId
            in: path
            required: true
            schema:
                $ref: "#/components/schemas/Id"

by running npx restful-react import --file customer-api.yaml --output customer-api.tsx. The generated TypeScript output code included a broken interface definition:

export interface ApiCustomersUpdateRequestBody CustomerProperties & CustomerRequiredProperties & {
  Segment?: {} | null;
}

This should probably be defined as an intersection type instead to make it valid TypeScript:

export type ApiCustomersUpdateRequestBody = CustomerProperties & CustomerRequiredProperties & {
  Segment?: {} | null;
}

However, this type still does not behave as intended:

  1. Segment in ApiCustomersUpdateRequestBody cannot have null assigned to it.
  2. FirstName, LastName and DOB would still be optional.

Expected behavior I expected the TypeScript generated by the import of the OpenAPI definition to be valid, and for the generated ApiCustomersUpdateRequestBody to have a nullable Segment property, and required FirstName, LastName and DOB properties.

Desktop (please complete the following information):

  • OS: macOS Catalina 10.15.7

Additional context I was trying out the code from this guide, which is intended to solve the problem of lots of repetition in schemas for related endpoints, where properties can differ in terms of nullability or optionality across endpoints. The solution involves splitting schemas into reusable parts that are composed together using OpenAPI’s allOf.

Issue Analytics

  • State:open
  • Created 3 years ago
  • Comments:5

github_iconTop GitHub Comments

2reactions
fabien0102commented, Nov 9, 2020

I will not call this a difficult problem, we “just” need to combine the specs before computing the type. I didn’t payed enought attention to this part of specs. I would also love to keep the composition when possible, because this can add some context about the type so this is always good to have (and this is how this task become a more tricky 😁)

BTW, regarding this allOf feature, and types compositions, I’m not sure about the benefit, yes this will probably reduce your specs size, but not sure this is worth it, this will become a nightmare to review, since you need to merge the specs in your head on github and most of time with a part context due to the openAPI spec structure & github PR UX. Don’t get me wrong, I also hate code duplications in my software, but we are talking about a piece of documentation here. This was just to challenge a bit this nice article you sent, looks like a good idea but carreful of the side effects 😉

This said, I will totally enjoy this little allOf generation challenge 😁 🤘

1reaction
chrisahardiecommented, May 13, 2021

I believe anyOf also exhibits this undesired behaviour.

Read more comments on GitHub >

github_iconTop Results From Across the Web

[BUG] Code is not generated correctly for allOf. #6815 - GitHub
Description I am not able to get the following definition to generate java or type script correctly. Have tried with 4.3.1.
Read more >
jsonschema - JSON schema allOf - Stack Overflow
I have tried many different variations of structure but none have validated successfully. The input JSON, which should be invalid (but showing ...
Read more >
Using $ref - Swagger
OAS 3 This guide is for OpenAPI 3.0. Using $ref. When you document an API, it is common to have some features which...
Read more >
Documentation for the spring Generator
generator name, spring, pass this to the generate command after -g ... Additional annotations for oneOf interfaces(class level annotations).
Read more >
Generator Options | Nx
export interface GeneratorOptions { name: string; type?: string; }. Import the TypeScript schema into your generator file and replace the any in your ......
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found