Skip to content

Commit 5e49d99

Browse files
authored
Merge pull request #645 from graphql-java-kickstart/renovate/major-graphql-java-(ignoring-snapshot-builds)
Update dependency com.graphql-java:graphql-java to v18
2 parents 278f8b1 + 8eb11c9 commit 5e49d99

File tree

10 files changed

+260
-90
lines changed

10 files changed

+260
-90
lines changed

pom.xml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717
<kotlin.version>1.6.21</kotlin.version>
1818
<kotlin-coroutines.version>1.6.1-native-mt</kotlin-coroutines.version>
1919
<jackson.version>2.13.2.20220328</jackson.version>
20-
<graphql-java.version>17.3</graphql-java.version>
20+
<graphql-java.version>18.0</graphql-java.version>
2121
<reactive-streams.version>1.0.3</reactive-streams.version>
2222

2323
<maven.compiler.source>${java.version}</maven.compiler.source>

src/main/kotlin/graphql/kickstart/tools/ScannedSchemaObjects.kt

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import graphql.kickstart.tools.util.BiMap
55
import graphql.kickstart.tools.util.JavaType
66
import graphql.language.FieldDefinition
77
import graphql.language.ObjectTypeDefinition
8+
import graphql.language.SDLNamedDefinition
89
import graphql.language.TypeDefinition
910
import graphql.schema.GraphQLScalarType
1011

@@ -13,7 +14,7 @@ import graphql.schema.GraphQLScalarType
1314
*/
1415
internal data class ScannedSchemaObjects(
1516
val dictionary: TypeClassDictionary,
16-
val definitions: Set<TypeDefinition<*>>,
17+
val definitions: Set<SDLNamedDefinition<*>>,
1718
val customScalars: CustomScalarMap,
1819
val rootInfo: RootTypeInfo,
1920
val fieldResolversByType: Map<ObjectTypeDefinition, MutableMap<FieldDefinition, FieldResolver>>,

src/main/kotlin/graphql/kickstart/tools/SchemaClassScanner.kt

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,8 @@ internal class SchemaClassScanner(
3333
private val initialDictionary = initialDictionary.mapValues { InitialDictionaryEntry(it.value) }
3434
private val extensionDefinitions = allDefinitions.filterIsInstance<ObjectTypeExtensionDefinition>()
3535
private val inputExtensionDefinitions = allDefinitions.filterIsInstance<InputObjectTypeExtensionDefinition>()
36+
private val directiveDefinitions = allDefinitions.filterIsInstance<DirectiveDefinition>()
37+
private val scalarDefinitions = allDefinitions.filterIsInstance<ScalarTypeDefinition>()
3638

3739
private val definitionsByName = (allDefinitions.filterIsInstance<TypeDefinition<*>>() - extensionDefinitions - inputExtensionDefinitions).associateBy { it.name }
3840
private val objectDefinitions = (allDefinitions.filterIsInstance<ObjectTypeDefinition>() - extensionDefinitions)
@@ -42,7 +44,7 @@ internal class SchemaClassScanner(
4244
private val fieldResolverScanner = FieldResolverScanner(options)
4345
private val typeClassMatcher = TypeClassMatcher(definitionsByName)
4446
private val dictionary = mutableMapOf<TypeDefinition<*>, DictionaryEntry>()
45-
private val unvalidatedTypes = mutableSetOf<TypeDefinition<*>>()
47+
private val unvalidatedTypes = mutableSetOf<TypeDefinition<*>>(*scalarDefinitions.toTypedArray())
4648
private val queue = linkedSetOf<QueueItem>()
4749

4850
private val fieldResolversByType = mutableMapOf<ObjectTypeDefinition, MutableMap<FieldDefinition, FieldResolver>>()
@@ -193,7 +195,9 @@ internal class SchemaClassScanner(
193195
validateRootResolversWereUsed(rootTypeHolder.mutation, fieldResolvers)
194196
validateRootResolversWereUsed(rootTypeHolder.subscription, fieldResolvers)
195197

196-
return ScannedSchemaObjects(dictionary, observedDefinitions + extensionDefinitions + inputExtensionDefinitions, scalars, rootInfo, fieldResolversByType.toMap(), unusedDefinitions)
198+
val definitions = observedDefinitions + extensionDefinitions + inputExtensionDefinitions + directiveDefinitions
199+
200+
return ScannedSchemaObjects(dictionary, definitions, scalars, rootInfo, fieldResolversByType.toMap(), unusedDefinitions)
197201
}
198202

199203
private fun validateRootResolversWereUsed(rootType: RootType?, fieldResolvers: List<FieldResolver>) {

src/main/kotlin/graphql/kickstart/tools/SchemaObjects.kt

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,6 @@
11
package graphql.kickstart.tools
22

3-
import graphql.schema.GraphQLCodeRegistry
4-
import graphql.schema.GraphQLObjectType
5-
import graphql.schema.GraphQLSchema
6-
import graphql.schema.GraphQLType
3+
import graphql.schema.*
74

85
/**
96
* @author Andrew Potter
@@ -13,6 +10,7 @@ data class SchemaObjects(
1310
val mutation: GraphQLObjectType?,
1411
val subscription: GraphQLObjectType?,
1512
val dictionary: Set<GraphQLType>,
13+
val directives: Set<GraphQLDirective>,
1614
val codeRegistryBuilder: GraphQLCodeRegistry.Builder,
1715
val description: String?
1816
) {
@@ -26,6 +24,7 @@ data class SchemaObjects(
2624
.mutation(mutation)
2725
.subscription(subscription)
2826
.additionalTypes(dictionary)
27+
.additionalDirectives(directives)
2928
.codeRegistry(codeRegistryBuilder.build())
3029
.build()
3130
}

src/main/kotlin/graphql/kickstart/tools/SchemaParser.kt

Lines changed: 79 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,7 @@ class SchemaParser internal constructor(
4545
private val inputObjectDefinitions = (definitions.filterIsInstance<InputObjectTypeDefinition>() - inputExtensionDefinitions)
4646
private val enumDefinitions = definitions.filterIsInstance<EnumTypeDefinition>()
4747
private val interfaceDefinitions = definitions.filterIsInstance<InterfaceTypeDefinition>()
48+
private val directiveDefinitions = definitions.filterIsInstance<DirectiveDefinition>()
4849

4950
private val unionDefinitions = definitions.filterIsInstance<UnionTypeDefinition>()
5051

@@ -82,6 +83,8 @@ class SchemaParser internal constructor(
8283
val unions = unionDefinitions.map { createUnionObject(it, objects) }
8384
val enums = enumDefinitions.map { createEnumObject(it) }
8485

86+
val directives = directiveDefinitions.map { createDirective(it, inputObjects) }.toSet()
87+
8588
// Assign type resolver to interfaces now that we know all of the object types
8689
interfaces.forEach { codeRegistryBuilder.typeResolver(it, InterfaceTypeResolver(dictionary.inverse(), it)) }
8790
unions.forEach { codeRegistryBuilder.typeResolver(it, UnionTypeResolver(dictionary.inverse(), it)) }
@@ -101,7 +104,7 @@ class SchemaParser internal constructor(
101104
val additionalObjects = objects.filter { o -> o != query && o != subscription && o != mutation }
102105

103106
val types = (additionalObjects.toSet() as Set<GraphQLType>) + inputObjects + enums + interfaces + unions
104-
return SchemaObjects(query, mutation, subscription, types, codeRegistryBuilder, rootInfo.getDescription())
107+
return SchemaObjects(query, mutation, subscription, types, directives, codeRegistryBuilder, rootInfo.getDescription())
105108
}
106109

107110
/**
@@ -123,6 +126,7 @@ class SchemaParser internal constructor(
123126
.description(getDocumentation(objectDefinition, options))
124127

125128
builder.withDirectives(*buildDirectives(objectDefinition.directives, Introspection.DirectiveLocation.OBJECT))
129+
builder.withAppliedDirectives(*buildAppliedDirectives(objectDefinition.directives))
126130

127131
objectDefinition.implements.forEach { implementsDefinition ->
128132
val interfaceName = (implementsDefinition as TypeName).name
@@ -163,6 +167,7 @@ class SchemaParser internal constructor(
163167
.description(getDocumentation(definition, options))
164168

165169
builder.withDirectives(*buildDirectives(definition.directives, Introspection.DirectiveLocation.INPUT_OBJECT))
170+
builder.withAppliedDirectives(*buildAppliedDirectives(definition.directives))
166171

167172
referencingInputObjects.add(definition.name)
168173

@@ -175,6 +180,7 @@ class SchemaParser internal constructor(
175180
.apply { inputDefinition.defaultValue?.let { v -> defaultValueLiteral(v) } }
176181
.type(determineInputType(inputDefinition.type, inputObjects, referencingInputObjects))
177182
.withDirectives(*buildDirectives(inputDefinition.directives, Introspection.DirectiveLocation.INPUT_FIELD_DEFINITION))
183+
.withAppliedDirectives(*buildAppliedDirectives(inputDefinition.directives))
178184
builder.field(fieldBuilder.build())
179185
}
180186
}
@@ -194,20 +200,23 @@ class SchemaParser internal constructor(
194200
.description(getDocumentation(definition, options))
195201

196202
builder.withDirectives(*buildDirectives(definition.directives, Introspection.DirectiveLocation.ENUM))
203+
builder.withAppliedDirectives(*buildAppliedDirectives(definition.directives))
197204

198205
definition.enumValueDefinitions.forEach { enumDefinition ->
199206
val enumName = enumDefinition.name
200207
val enumValue = type.unwrap().enumConstants.find { (it as Enum<*>).name == enumName }
201208
?: throw SchemaError("Expected value for name '$enumName' in enum '${type.unwrap().simpleName}' but found none!")
202209

203210
val enumValueDirectives = buildDirectives(enumDefinition.directives, Introspection.DirectiveLocation.ENUM_VALUE)
211+
val enumValueAppliedDirectives = buildAppliedDirectives(enumDefinition.directives)
204212
getDeprecated(enumDefinition.directives).let {
205213
val enumValueDefinition = GraphQLEnumValueDefinition.newEnumValueDefinition()
206214
.name(enumName)
207215
.description(getDocumentation(enumDefinition, options))
208216
.value(enumValue)
209217
.deprecationReason(it)
210218
.withDirectives(*enumValueDirectives)
219+
.withAppliedDirectives(*enumValueAppliedDirectives)
211220
.definition(enumDefinition)
212221
.build()
213222

@@ -226,6 +235,7 @@ class SchemaParser internal constructor(
226235
.description(getDocumentation(interfaceDefinition, options))
227236

228237
builder.withDirectives(*buildDirectives(interfaceDefinition.directives, Introspection.DirectiveLocation.INTERFACE))
238+
builder.withAppliedDirectives(*buildAppliedDirectives(interfaceDefinition.directives))
229239

230240
interfaceDefinition.fieldDefinitions.forEach { fieldDefinition ->
231241
builder.field { field -> createField(field, fieldDefinition, inputObjects) }
@@ -247,6 +257,7 @@ class SchemaParser internal constructor(
247257
.description(getDocumentation(definition, options))
248258

249259
builder.withDirectives(*buildDirectives(definition.directives, Introspection.DirectiveLocation.UNION))
260+
builder.withAppliedDirectives(*buildAppliedDirectives(definition.directives))
250261

251262
getLeafUnionObjects(definition, types).forEach { builder.possibleType(it) }
252263
return schemaGeneratorDirectiveHelper.onUnion(builder.build(), schemaDirectiveParameters)
@@ -288,14 +299,44 @@ class SchemaParser internal constructor(
288299
.type(determineInputType(argumentDefinition.type, inputObjects, setOf()))
289300
.apply { argumentDefinition.defaultValue?.let { defaultValueLiteral(it) } }
290301
.withDirectives(*buildDirectives(argumentDefinition.directives, Introspection.DirectiveLocation.ARGUMENT_DEFINITION))
302+
.withAppliedDirectives(*buildAppliedDirectives(argumentDefinition.directives))
291303

292304
field.argument(argumentBuilder.build())
293305
}
294306
field.withDirectives(*buildDirectives(fieldDefinition.directives, Introspection.DirectiveLocation.FIELD_DEFINITION))
307+
field.withAppliedDirectives(*buildAppliedDirectives(fieldDefinition.directives))
295308

296309
return field
297310
}
298311

312+
private fun createDirective(definition: DirectiveDefinition, inputObjects: List<GraphQLInputObjectType>): GraphQLDirective {
313+
val locations = definition.directiveLocations.map { Introspection.DirectiveLocation.valueOf(it.name) }.toTypedArray()
314+
315+
val graphQLDirective = GraphQLDirective.newDirective()
316+
.name(definition.name)
317+
.description(getDocumentation(definition, options))
318+
.definition(definition)
319+
.comparatorRegistry(runtimeWiring.comparatorRegistry)
320+
.validLocations(*locations)
321+
.repeatable(definition.isRepeatable)
322+
.apply {
323+
definition.inputValueDefinitions.forEach { arg ->
324+
argument(GraphQLArgument.newArgument()
325+
.name(arg.name)
326+
.definition(arg)
327+
.description(getDocumentation(arg, options))
328+
.type(determineInputType(arg.type, inputObjects, setOf()))
329+
.apply { arg.defaultValue?.let { defaultValueLiteral(it) } }
330+
.withDirectives(*buildDirectives(arg.directives, Introspection.DirectiveLocation.ARGUMENT_DEFINITION))
331+
.withAppliedDirectives(*buildAppliedDirectives(arg.directives))
332+
.build())
333+
}
334+
}
335+
.build()
336+
337+
return graphQLDirective
338+
}
339+
299340
private fun buildDirectives(directives: List<Directive>, directiveLocation: Introspection.DirectiveLocation): Array<GraphQLDirective> {
300341
val names = mutableSetOf<String>()
301342

@@ -326,14 +367,43 @@ class SchemaParser internal constructor(
326367
return output.toTypedArray()
327368
}
328369

370+
private fun buildAppliedDirectives(directives: List<Directive>): Array<GraphQLAppliedDirective> {
371+
val names = mutableSetOf<String>()
372+
373+
val output = mutableListOf<GraphQLAppliedDirective>()
374+
for (directive in directives) {
375+
if (!names.contains(directive.name)) {
376+
names.add(directive.name)
377+
val graphQLDirective = GraphQLAppliedDirective.newDirective()
378+
.name(directive.name)
379+
.description(getDocumentation(directive, options))
380+
.comparatorRegistry(runtimeWiring.comparatorRegistry)
381+
.apply {
382+
directive.arguments.forEach { arg ->
383+
argument(GraphQLAppliedDirectiveArgument.newArgument()
384+
.name(arg.name)
385+
.type(buildDirectiveInputType(arg.value))
386+
.valueLiteral(arg.value)
387+
.build())
388+
}
389+
}
390+
.build()
391+
392+
output.add(graphQLDirective)
393+
}
394+
}
395+
396+
return output.toTypedArray()
397+
}
398+
329399
private fun buildDirectiveInputType(value: Value<*>): GraphQLInputType? {
330-
when (value) {
331-
is NullValue -> return Scalars.GraphQLString
332-
is FloatValue -> return Scalars.GraphQLFloat
333-
is StringValue -> return Scalars.GraphQLString
334-
is IntValue -> return Scalars.GraphQLInt
335-
is BooleanValue -> return Scalars.GraphQLBoolean
336-
is ArrayValue -> return GraphQLList.list(buildDirectiveInputType(getArrayValueWrappedType(value)))
400+
return when (value) {
401+
is NullValue -> Scalars.GraphQLString
402+
is FloatValue -> Scalars.GraphQLFloat
403+
is StringValue -> Scalars.GraphQLString
404+
is IntValue -> Scalars.GraphQLInt
405+
is BooleanValue -> Scalars.GraphQLBoolean
406+
is ArrayValue -> GraphQLList.list(buildDirectiveInputType(getArrayValueWrappedType(value)))
337407
else -> throw SchemaError("Directive values of type '${value::class.simpleName}' are not supported yet.")
338408
}
339409
}
@@ -448,14 +518,10 @@ class SchemaParser internal constructor(
448518
* indicating no deprecation directive was found within the directives list.
449519
*/
450520
private fun getDeprecated(directives: List<Directive>): String? =
451-
getDirective(directives, "deprecated")?.let { directive ->
521+
directives.find { it.name == "deprecated" }?.let { directive ->
452522
(directive.arguments.find { it.name == "reason" }?.value as? StringValue)?.value
453523
?: DEFAULT_DEPRECATION_MESSAGE
454524
}
455-
456-
private fun getDirective(directives: List<Directive>, name: String): Directive? = directives.find {
457-
it.name == name
458-
}
459525
}
460526

461527
class SchemaError(message: String, cause: Throwable? = null) : RuntimeException(message, cause)

src/main/kotlin/graphql/kickstart/tools/directive/SchemaDirectiveWiringEnvironmentImpl.java

Lines changed: 20 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -3,14 +3,7 @@
33
import graphql.Internal;
44
import graphql.language.NamedNode;
55
import graphql.language.NodeParentTree;
6-
import graphql.schema.DataFetcher;
7-
import graphql.schema.FieldCoordinates;
8-
import graphql.schema.GraphQLCodeRegistry;
9-
import graphql.schema.GraphQLDirective;
10-
import graphql.schema.GraphQLDirectiveContainer;
11-
import graphql.schema.GraphQLFieldDefinition;
12-
import graphql.schema.GraphQLFieldsContainer;
13-
import graphql.schema.GraphqlElementParentTree;
6+
import graphql.schema.*;
147
import graphql.schema.idl.SchemaDirectiveWiringEnvironment;
158
import graphql.schema.idl.TypeDefinitionRegistry;
169
import graphql.util.FpKit;
@@ -31,6 +24,7 @@ public class SchemaDirectiveWiringEnvironmentImpl<T extends GraphQLDirectiveCont
3124

3225
private final T element;
3326
private final Map<String, GraphQLDirective> directives;
27+
private final Map<String, GraphQLAppliedDirective> appliedDirectives;
3428
private final NodeParentTree<NamedNode<?>> nodeParentTree;
3529
private final TypeDefinitionRegistry typeDefinitionRegistry;
3630
private final Map<String, Object> context;
@@ -40,11 +34,18 @@ public class SchemaDirectiveWiringEnvironmentImpl<T extends GraphQLDirectiveCont
4034
private final GraphQLFieldDefinition fieldDefinition;
4135
private final GraphQLDirective registeredDirective;
4236

43-
public SchemaDirectiveWiringEnvironmentImpl(T element, List<GraphQLDirective> directives, GraphQLDirective registeredDirective, SchemaGeneratorDirectiveHelper.Parameters parameters) {
37+
public SchemaDirectiveWiringEnvironmentImpl(
38+
T element,
39+
List<GraphQLDirective> directives,
40+
List<GraphQLAppliedDirective> appliedDirectives,
41+
GraphQLDirective registeredDirective,
42+
SchemaGeneratorDirectiveHelper.Parameters parameters
43+
) {
4444
this.element = element;
4545
this.registeredDirective = registeredDirective;
4646
this.typeDefinitionRegistry = parameters.getTypeRegistry();
4747
this.directives = FpKit.getByName(directives, GraphQLDirective::getName);
48+
this.appliedDirectives = FpKit.getByName(appliedDirectives, GraphQLAppliedDirective::getName);
4849
this.context = parameters.getContext();
4950
this.codeRegistry = parameters.getCodeRegistry();
5051
this.nodeParentTree = parameters.getNodeParentTree();
@@ -73,6 +74,16 @@ public GraphQLDirective getDirective(String directiveName) {
7374
return directives.get(directiveName);
7475
}
7576

77+
@Override
78+
public Map<String, GraphQLAppliedDirective> getAppliedDirectives() {
79+
return appliedDirectives;
80+
}
81+
82+
@Override
83+
public GraphQLAppliedDirective getAppliedDirective(String directiveName) {
84+
return appliedDirectives.get(directiveName);
85+
}
86+
7687
@Override
7788
public boolean containsDirective(String directiveName) {
7889
return directives.containsKey(directiveName);

0 commit comments

Comments
 (0)