Skip to content

Circular type support, or at least detection? #68

@csorfab

Description

@csorfab

Hi @sinclairzx81 ! First of all, thank you for creating and maintaining this project, it helped me a lot through the typed-openapi lib.

TL;DR: TypescriptToModel.Generate silently produces incorrect output from circular types. I'd be interested in creating a PR to detect circular types and fail/warn instead.


Yesterday I ran into a problem while working with an openAPI schema that, unbeknownst to me, contained circles - it started generating weird outputs, with some types missing altogether, other types unnecessarily expanded in Type_path_to_field formats, whereas previously it worked flawlessly.

It took me 4 hours of digging into typebox and typebox-codegen code, console.logging my way through to understand what's happening, to realize that we had a circle, and that it caused some types during TypescriptToModel.Exports to be evaluated to undefined, which made the wrapping Type invalid, which made an IsSchema check fail, that made TypescriptToModel.Types to start namespacing subfields, and cause the main type to be omitted from the output.

Here's a minimal repro for what I'm talking about:

import { ModelToTypeScript, TypeScriptToModel } from "@sinclair/typebox-codegen";

const model = TypeScriptToModel.Generate(`
export type A = {
    b: B[];
    c: {
        d: string;
    }
}

export type B = {
    a: A[];
}

`);

const code = ModelToTypeScript.Generate(model);

console.log(code, "\n\n", model);

this generates the following output (I include only the generated TS types for clarity's sake - the model already only contains these types, so the problem lies with TypescriptToModel):

export type A_properties_c = {
  d: string
}

export type B_properties_a_items_properties_c = {
  d: string
}

Both main types (A, B) are omitted without warning, and strange scoped types are generated for subfields.

I understand that it's difficult to represent circular types with Typebox, and even more difficult to write a parser that handles them in a general way, but I think you will agree that producing incorrect output without errors or warning is undesirable behavior.

Would you be interested in a PR that would add checking for circular type definitions while walking the TS AST, and throw an error if it detects one? It would be an interesting challenge to me, and it might spare some poor folks from going through the digging I had to go through :D

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions