Skip to content

Commit ba81cfb

Browse files
committed
feat(codegen): allow "kRepresentation" directive on interface
1 parent 611223c commit ba81cfb

File tree

2 files changed

+33
-14
lines changed

2 files changed

+33
-14
lines changed

graphql-kotlin-toolkit-codegen/src/main/kotlin/com/auritylab/graphql/kotlin/toolkit/codegen/directive/implementation/RepresentationDirective.kt

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,11 @@ class RepresentationDirective : AbstractDirective("kRepresentation", false),
1515
override val reference: GraphQLDirective =
1616
GraphQLDirective.newDirective()
1717
.name(name)
18-
.validLocations(Introspection.DirectiveLocation.OBJECT, Introspection.DirectiveLocation.SCALAR)
18+
.validLocations(
19+
Introspection.DirectiveLocation.OBJECT,
20+
Introspection.DirectiveLocation.SCALAR,
21+
Introspection.DirectiveLocation.INTERFACE
22+
)
1923
.argument {
2024
it.name("class")
2125
it.type(GraphQLNonNull(Scalars.GraphQLString))

graphql-kotlin-toolkit-codegen/src/main/kotlin/com/auritylab/graphql/kotlin/toolkit/codegen/mapper/KotlinTypeMapper.kt

Lines changed: 28 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ import com.squareup.kotlinpoet.asClassName
2020
import graphql.schema.GraphQLDirectiveContainer
2121
import graphql.schema.GraphQLEnumType
2222
import graphql.schema.GraphQLInputObjectType
23+
import graphql.schema.GraphQLInterfaceType
2324
import graphql.schema.GraphQLObjectType
2425
import graphql.schema.GraphQLScalarType
2526
import graphql.schema.GraphQLType
@@ -43,6 +44,7 @@ internal class KotlinTypeMapper(
4344
is GraphQLInputObjectType -> generatedMapper.getGeneratedTypeClassName(unwrappedType)
4445
is GraphQLEnumType -> generatedMapper.getGeneratedTypeClassName(unwrappedType)
4546
is GraphQLObjectType -> getObjectKotlinType(unwrappedType)
47+
is GraphQLInterfaceType -> getInterfaceKotlinType(unwrappedType)
4648
else -> ANY
4749
}
4850

@@ -114,20 +116,33 @@ internal class KotlinTypeMapper(
114116
* Will return the [ClassName] for the given [type].
115117
*/
116118
private fun getObjectKotlinType(type: GraphQLObjectType): ClassName {
117-
// Check if the type is annotated with the "kotlinRepresentation" directive.
118-
val helperResult = DirectiveFacade.representation.getArguments(type)?.className
119+
// Try to resolve the class via the representation directive.
120+
// Return the representation class if its available.
121+
resolveRepresentationClass(type)
122+
?.let { return it }
119123

120-
// If the directive is available return the content.
121-
if (helperResult != null)
122-
return helperResult
124+
// Try to resolve the type via a generated class. This will fallback to ANY.
125+
return resolveGeneratedClass(type)
126+
}
127+
128+
private fun getInterfaceKotlinType(type: GraphQLInterfaceType): ClassName =
129+
// Resolve the representation and return if it's available.
130+
resolveRepresentationClass(type) ?: ANY
131+
132+
/**
133+
* Will resolve the [ClassName] for the given [container]. This will basically just check if the
134+
* [DirectiveFacade.representation] directive is given, if so it will return the value of the className argument.
135+
*/
136+
private fun resolveRepresentationClass(container: GraphQLDirectiveContainer): ClassName? =
137+
// Check if the type is annotated with the "kRepresentation" directive.
138+
DirectiveFacade.representation.getArguments(container)?.className
123139

124-
// Use the generated class if "generateAll" is enabled or
125-
// the object type is annotated with the generate directive
126-
return if (options.generateAll || DirectiveFacade.generate[type]) {
127-
// The object has a generated type, return the generated one.
140+
/**
141+
* Will resolve the [ClassName] for the given [type]. This will check if the [CodegenOptions.generateAll] attribute
142+
* is true or the type is annotated with the [DirectiveFacade.generate] directive.
143+
*/
144+
private fun resolveGeneratedClass(type: GraphQLType): ClassName =
145+
if (options.generateAll || (type is GraphQLDirectiveContainer && DirectiveFacade.generate[type]))
128146
generatedMapper.getGeneratedTypeClassName(type, false)
129-
} else
130-
// The object does not have a generated type, therefore return Any.
131-
ANY
132-
}
147+
else ANY
133148
}

0 commit comments

Comments
 (0)