@@ -203,7 +203,7 @@ export function extendSchema(
203203 const typeName = typeRef . name . value ;
204204 const existingType = schema . getType ( typeName ) ;
205205 if ( existingType ) {
206- return extendType ( existingType ) ;
206+ return getExtendedType ( existingType ) ;
207207 }
208208
209209 throw new GraphQLError (
@@ -221,22 +221,24 @@ export function extendSchema(
221221 // typed values below, that would throw immediately while type system
222222 // validation with validateSchema() will produce more actionable results.
223223 const existingQueryType = schema . getQueryType ( ) ;
224- const queryType = existingQueryType ? extendType ( existingQueryType ) : null ;
224+ const queryType = existingQueryType
225+ ? getExtendedType ( existingQueryType )
226+ : null ;
225227
226228 const existingMutationType = schema . getMutationType ( ) ;
227229 const mutationType = existingMutationType
228- ? extendType ( existingMutationType )
230+ ? getExtendedType ( existingMutationType )
229231 : null ;
230232
231233 const existingSubscriptionType = schema . getSubscriptionType ( ) ;
232234 const subscriptionType = existingSubscriptionType
233- ? extendType ( existingSubscriptionType )
235+ ? getExtendedType ( existingSubscriptionType )
234236 : null ;
235237
236238 const types = [
237239 // Iterate through all types, getting the type definition for each, ensuring
238240 // that any type not directly referenced by a field will get created.
239- ...objectValues ( schema . getTypeMap ( ) ) . map ( type => extendType ( type ) ) ,
241+ ...objectValues ( schema . getTypeMap ( ) ) . map ( type => getExtendedType ( type ) ) ,
240242 // Do the same with new types.
241243 ...objectValues ( typeDefinitionMap ) . map ( type => astBuilder . buildType ( type ) ) ,
242244 ] ;
@@ -276,23 +278,26 @@ export function extendSchema(
276278 ) ;
277279 }
278280
279- function extendType < T : GraphQLNamedType > (type: T): T {
280- let extendedType = extendTypeCache [ type . name ] ;
281+ function getExtendedType < T : GraphQLNamedType > (type: T): T {
282+ if ( ! extendTypeCache [ type . name ] ) {
283+ extendTypeCache [ type . name ] = extendType ( type ) ;
284+ }
285+ return (extendTypeCache[type.name]: any);
286+ }
281287
282- if ( ! extendedType ) {
283- if ( isIntrospectionType ( type ) ) {
284- extendedType = type ;
285- } else if ( isObjectType ( type ) ) {
288+ // Should be called only once per type so only getExtendedType should call it.
289+ function extendType < T : GraphQLNamedType > (type: T): T {
290+ let extendedType = type ;
291+ if ( ! isIntrospectionType ( type ) ) {
292+ if ( isObjectType ( type ) ) {
286293 extendedType = extendObjectType ( type ) ;
287294 } else if ( isInterfaceType ( type ) ) {
288295 extendedType = extendInterfaceType ( type ) ;
289296 } else if ( isUnionType ( type ) ) {
290297 extendedType = extendUnionType ( type ) ;
291- } else {
292- extendedType = type ;
293298 }
294- extendTypeCache [ type . name ] = extendedType ;
295299 }
300+ // Workaround: Flow should figure out correct type, but it doesn't.
296301 return (extendedType: any);
297302 }
298303
@@ -337,7 +342,7 @@ export function extendSchema(
337342 return new GraphQLUnionType ( {
338343 name : type . name ,
339344 description : type . description ,
340- types : type . getTypes ( ) . map ( extendType ) ,
345+ types : type . getTypes ( ) . map ( getExtendedType ) ,
341346 astNode : type . astNode ,
342347 resolveType : type . resolveType ,
343348 } ) ;
@@ -346,7 +351,7 @@ export function extendSchema(
346351 function extendImplementedInterfaces(
347352 type: GraphQLObjectType,
348353 ): Array< GraphQLInterfaceType > {
349- const interfaces = type . getInterfaces ( ) . map ( extendType ) ;
354+ const interfaces = type . getInterfaces ( ) . map ( getExtendedType ) ;
350355
351356 // If there are any extensions to the interfaces, apply those here.
352357 const extensions = typeExtensionsMap [ type . name ] ;
@@ -407,6 +412,6 @@ export function extendSchema(
407412 if (isNonNullType(typeDef)) {
408413 return ( GraphQLNonNull ( extendFieldType ( typeDef . ofType ) ) : any ) ;
409414 }
410- return extendType (typeDef);
415+ return getExtendedType (typeDef);
411416 }
412417}
0 commit comments