MichalLytek / type-graphql

Create GraphQL schema and resolvers with TypeScript, using classes and decorators!
https://typegraphql.com
MIT License
8.04k stars 676 forks source link

Circular dependency issue when using functional syntax #1449

Open zacharyclaysmith opened 1 year ago

zacharyclaysmith commented 1 year ago

Describe the Bug A ReferenceError is thrown at startup due to circular references. These circular references occur while using the @Field(type => SomeType) syntax.

To Reproduce Example Repository: https://github.com/zacharyclaysmith/type-graphql-circular-dependency-repro

(Key code extracts in Additional Context below)

Expected Behavior The "functional syntax" should keep this kind of issue from happening:

From https://typegraphql.com/docs/0.17.1/types-and-fields.html:

Why use function syntax and not a simple { type: Rate } config object? Because, by using function syntax we solve the problem of circular dependencies (e.g. Post <--> User), so it was adopted as a convention. You can use the shorthand syntax @Field(() => Rate) if you want to save some keystrokes but it might be less readable for others.

Logs If applicable, add some console logs to help explain your problem. You can paste the errors with stack trace that were printed when the error occurred.

Environment (please complete the following information):

Additional Context This example was recreated from a larger project where I'm running into this issue. I tried to remove any unnecessary cruft when copying over pieces of code/dependency lists.

The original project also uses mikro-orm, and I avoid circular dependencies with their library due to the ability to use a string version of the type name, e.g. @Property('User').

Key Code extracts:

@ObjectType()
export class User {
  //...

  // NOTE: comment out the next line to remove the error.
  @Field(() => [Item])
  items: Item[];
}
@ObjectType()
export class Item {
  //...

  @Field(() => User)
  owner: User;
}
carlocorradini commented 1 year ago

type: module is not currently supported in V2 beta until PR #1400 is merged. I think this is the main cause of the issue 🙃

carlocorradini commented 1 year ago

Does it work if you remove type: module?

zacharyclaysmith commented 1 year ago

Tried it in this branch: https://github.com/zacharyclaysmith/type-graphql-circular-dependency-repro/tree/remove-type-module

It caused some cascading issues that had to be addressed (changing to commonjs and rewriting the index.ts file to not have a top-level await), but I think it technically works. I'll try similar in my actual application, though it's likely to not be as easy to solve with other major libraries in play.

zacharyclaysmith commented 1 year ago

Now getting "TypeError: Class extends value undefined is not a constructor or null" in my main application after trying to make those changes (I'm using interfaces there that I didn't include in my original example). I'll see if I can recreate the issue in the example repo.

LordotU commented 4 months ago

Hello all,

I have the same issue with my setup in 2.0.0-rc2. Unfortunately, all the things in my monorepo are modules and it's very undesirable to change.

Is there any workaround which allows to stay on module?