graphql-kotlin icon indicating copy to clipboard operation
graphql-kotlin copied to clipboard

Allow a single schema entity to be composed from multiple classes

Open martin-dd opened this issue 2 years ago • 1 comments

Is your feature request related to a problem? Please describe. Currently it is not possible to compose a GraphQL entity from multiple classes without using federation. In some cases, the source organization requires individual fields of a GraphQL entity to be in their own source files / different gradle modules for organizational purposes, however currently graphql-kotlin library requires a full entity to be represented by a single class. This limits the flexibility of the code organization in a medium size projects (i.e. projects which do not need full federation yet).

Describe the solution you'd like Ideally we would like to be able to compose a single entity from multiple classes like the following:

module1/src/domain1/Entity.kt:
class Entity {
    fun fieldFromDomain1() = Domain1Component.fetchField()
}

module2/src/domain2/Entity.kt:
class Entity {
    fun fieldFromDomain2() = Domain2Component.fetchField()
}

In the example above - there are two classes called Entity, each of them in a different source root (gradle module) and its own package. Both classes are used to compose the resulting schema:

type Entity {
    fieldFromDomain1: String!
    fieldFromDomain2: String!
}

If a full blown class would make the system too complicated, perhaps using Kotlin extension function might be good enough. In that case the sources might look like this:

module1/src/domain1/Entity.kt:
class Entity {
    fun fieldFromDomain1() = Domain1Component.fetchField()
}

module2/src/domain2/EntityExtensions.kt:
fun Entity.fieldFromDomain2() = Domain2Component.fetchField()

Describe alternatives you've considered While federation is the obvious choice for the above, it might be an overkill for a medium size projects as it requires each federated subgraph to execute in its own service and also required deploying federated gateway itself. For small-medium projects this is too much complexity and these project would rather benefit from an ability to properly separate the individual domains in different source roots / gradle modules.

Additional context A slack channel discussion which led to this FR: https://kotlinlang.slack.com/archives/CQLNT7B29/p1654908642621919

martin-dd avatar Jun 13 '22 16:06 martin-dd

related: https://github.com/ExpediaGroup/graphql-kotlin/pull/384

dariuszkuc avatar Jun 13 '22 16:06 dariuszkuc