Skip to content

[BUG][Typescript] generate API, model does not compile(or is this feature request)? #21098

Open
@deanbiltup

Description

@deanbiltup

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

To me an API is a contract and stands alone without depending on any implementation. It is simply interface plus model classes depending on no implementation. Having an API depend on any implementation defeats the purpose of the definition of an API. When I generated api/model, it generates code assuming it would be for a client :( :( which is incorrect. We use the API on our server and our client. more below.

Expected an API (one interface + multiple DTO model classes) that compiles when using "--global-property models,apis" such that on client, I can have my client implement it. On server, I can have my controller implement it. Instead generated classes do not compile and refer to a non-existent ../runtime for many many things which makes it hard to use the generated content both on server and client (we generate into a lib for our monorepo that both server and clients use so they 100% use the same code. This code is then implemented by controller in server or by a semi-generated client in the client side. The generated code for client and server shoudl contain 100% the same api and 100% the same model classes.

openapi-generator version

not sure, but CLI version ->
(.venv) 09:15 ~/workspace/biltup/biltup/scripts $ openapi-generator-cli version
Did set selected version to 7.12.0
7.12.0

OpenAPI declaration file content or url
openapi: 3.0.3
info:
  title: Database API
  version: "1.0.0"
paths:
  /fetchData:
    post:
      summary: Fake Endpoint
      operationId: /fetchData
      requestBody:
        description: Request payload to fetch customer details.
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/FetchDataRequest'
      responses:
        '200':
          description: Successful response with customer details.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FetchDataResponse'
components:
  schemas:
    FetchDataRequest:
      type: object
      description: Empty request payload for fetching customer details.
      properties:
        placeHolder:
          type: string
          description: Placeholder
    FetchDataResponse:
      type: object
      description: Response containing the customer details.
      properties:
        placeHolder:
          type: string
          description: Placeholder
Generation Details

Doing this for BOTH server and client (however neither compile)
openapi-generator-cli generate
-i biltup-db-ai.api.yaml
-g typescript-fetch
-o ${SERVICES_DIR}/biltup-db/src/apis-gen/server
--global-property models,apis
--additional-properties=withInterfaces=true,supportsES6=true,typescriptThreePlus=true

Steps to reproduce

Run the command and it does not compile. missing "../runtime" and "../model/index".
Expected results: It contains only the 'API contract' and compiles. APIs should compile by themselves. In this example, if you really need RequestInit as part of contract, generate RequestInit but do not generate the client. I would much prefer simply

export interface DefaultApiInterface {
    /**
     * 
     * @summary Fetch Customer Details
     * @param {object} body Request payload to fetch customer details.
     * @param {*} [options] Override http request option.
     * @throws {RequiredError}
     * @memberof DefaultApiInterface
     */
    fetchCustomerRaw(requestParameters: FetchCustomerRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise<runtime.ApiResponse<FetchCustomerResponse>>;

    /**
     * Fetch Customer Details
     */
    fetchCustomer(requestParameters: FetchCustomerRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise<FetchCustomerResponse>;

}

Personally,I would much prefer you to generate this as you can set all initOverrides in asyncLocalStorage and errors, we use underlying json ProtocolError when received by client, we throw error on client. Server receives Error and translates to ProtocolError. In this way, we never need your ApiResponse that you ahve here as exceptions are always Errors. All our apis currently without open api that are shared between typescript projects are of below format containing no extra code. We implement with controller and on client implement with a client ...

Now this is code I can use on both the client and the server AND EVEN BETTER, for testing, we embed a whole microservice in another since the APIs are 100% the same. We pass traceId, login, email, companyId, etc. etc using asynLocalStorage + http headers so we get full tracing as well without corrupting the API with this RequestInit object and can further configure other things if we want with asyncLocalStorage. Having the apis be 100% the same is extremely useful. This is just super clean ->

//DefaultApiInterface should really be called from the title of my open api spec as this will clash with other apis too
//We have microservices that implement 2 apis sometimes as makes it easy to transition over or in preparation for separation later as well

export interface DefaultApiInterface {
    /**
     * Fetch Customer Details
     */
    fetchCustomer(requestParameters: FetchCustomerRequest): Promise<FetchCustomerResponse>;

}
Related issues/PRs
Suggest a fix

Perhaps this is a feature request(I was not sure but to me api, model generation should compile. I have never seen an api be tied to implementation. that defeats the purpose of an api to be a contract).

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions