private void MapSelectionSubSet(SelectionSubset selSubset, TypeDefBase typeDef) { switch (typeDef) { case ScalarTypeDef _: case EnumTypeDef _: // that should never happen AddError($"Scalar or Enum may not have a selection subset", selSubset); break; case ObjectTypeDef objTypeDef: MapObjectSelectionSubset(selSubset, objTypeDef); break; case InterfaceTypeDef intTypeDef: foreach (var objType in intTypeDef.PossibleTypes) { MapObjectSelectionSubset(selSubset, objType); } break; case UnionTypeDef unionTypeDef: foreach (var objType in unionTypeDef.PossibleTypes) { MapObjectSelectionSubset(selSubset, objType, isForUnion: true); } break; } }
private void RegisterTypeDef(TypeDefBase typeDef) { _model.Types.Add(typeDef); // do not register further (by name or CLR type) the special objects if (typeDef is ObjectTypeDef otd && otd.TypeRole != ObjectTypeRole.Data) { return; } // data types - we register them by name and CLR type; they always have module and CLR type var modName = typeDef.Module.Name; if (typeDef.IsDefaultForClrType) { if (_model.TypesByClrType.ContainsKey(typeDef.ClrType)) { AddError($"Duplicate registration of type {typeDef.Name} as default for CLR type {typeDef.ClrType}, module {modName}."); return; } _model.TypesByClrType.Add(typeDef.ClrType, typeDef); } if (_model.TypesByName.ContainsKey(typeDef.Name)) { AddError($"GraphQL type {typeDef.Name} already registered; module: {modName}."); return; } _model.TypesByName.Add(typeDef.Name, typeDef); }
public static bool IsOneOf(this TypeDefBase typeDef, params TypeKind[] kinds) { for (int i = 0; i < kinds.Length; i++) { if (typeDef.Kind == kinds[i]) { return(true); } } return(false); }
public FieldContext(RequestContext requestContext, OperationFieldExecuter fieldExecuter, MappedSelectionField mappedField, IList <OutputObjectScope> allParentScopes = null) { _requestContext = requestContext; _executer = fieldExecuter; MappedField = mappedField; FieldDef = MappedField.Resolver.Field; TypeDef = FieldDef.TypeRef.TypeDef; AllParentScopes = allParentScopes ?? OutputObjectScope.EmptyList; if (MappedField.Field.SelectionSubset != null) { AllResultScopes = new List <OutputObjectScope>(); } }
private void RegisterTypeDef(TypeDefBase typeDef) { _model.Types.Add(typeDef); // data types - we register them by name and CLR type; they always have module and CLR type var modName = typeDef.Module?.Name ?? "(no module)"; if (typeDef.ClrType != null && typeDef.IsDefaultForClrType) { if (_model.TypesByClrType.ContainsKey(typeDef.ClrType)) { AddError($"Duplicate registration of type {typeDef.Name} as default for CLR type {typeDef.ClrType}, module {modName}."); return; } _model.TypesByClrType.Add(typeDef.ClrType, typeDef); } if (_model.TypesByName.ContainsKey(typeDef.Name)) { AddError($"GraphQL type {typeDef.Name} already registered; module: {modName}."); return; } _model.TypesByName.Add(typeDef.Name, typeDef); }
private void CreateTypeObject(TypeDefBase typeDef) { var type_ = new __Type() { Name = typeDef.Name, Kind = typeDef.Kind, Description = typeDef.Description, DisplayName = typeDef.Name, }; typeDef.Intro_ = type_; _schema.Types.Add(type_); // Initialize lists - we do this for all types upfront to allow Build methods to access other type's lists // without worrying if it is created or not. For ex, BuildObjectType finds interfaces and adds itself // to PossibleTypes list of each interface it implements switch (type_.Kind) { case TypeKind.Object: type_.Fields = new List <__Field>(); type_.Interfaces = new List <__Type>(); break; case TypeKind.Interface: type_.Fields = new List <__Field>(); type_.PossibleTypes = new List <__Type>(); break; case TypeKind.InputObject: type_.InputFields = new List <__InputValue>(); break; case TypeKind.Enum: type_.EnumValues = new List <__EnumValue>(); break; case TypeKind.Union: type_.PossibleTypes = new List <__Type>(); break; } }
private void MapSelectionFieldSubsetIfPresent(SelectionField selField, TypeDefBase fieldType) { var selSubset = selField.SelectionSubset; switch (fieldType) { case ScalarTypeDef _: case EnumTypeDef _: if (selSubset != null) { AddError($"Field '{selField.Key}' of type '{fieldType.Name}' may not have a selection subset.", selSubset); } break; default: // ObjectType, Union or Interface if (selSubset == null) { AddError($"Field '{selField.Key}' of type '{fieldType.Name}' must have a selection subset.", selField); return; } MapSelectionSubSet(selSubset, fieldType); break; } }
public static ObjectTypeMapping FindMapping(this TypeDefBase typeDef, Type fromType) { ObjectTypeMapping mapping = null; switch (typeDef) { case ObjectTypeDef otd: mapping = otd.FindObjectTypeMapping(fromType); break; case InterfaceTypeDef itd: mapping = FindObjectTypeMapping(itd.PossibleTypes, fromType); break; case UnionTypeDef utd: mapping = FindObjectTypeMapping(utd.PossibleTypes, fromType); break; default: // should never happen throw new Exception($"FATAL: Invalid target type kind {typeDef.Kind}, type {typeDef.Name}"); } return(mapping); }
} //method private bool Fragments_CheckFragmentSpreadCompatible(FragmentSpread fragmentSpread, TypeDefBase parentType) { var fragmOnTypeDef = fragmentSpread.Fragment.OnTypeRef.TypeDef; if (parentType == fragmOnTypeDef) { return(true); //trivial case } var fragmName = fragmentSpread.Name; switch (parentType) { case ObjectTypeDef parObjType: // parent type is object type; the only allowed (non-trivial) case is fragment on interface if (!parObjType.Implements.Contains(fragmOnTypeDef)) { AddError($"Fragment ref '{fragmName}': fragment is defined on type '{fragmOnTypeDef.Name}'" + $" which is not compatible with type '{parentType.Name}'.", fragmentSpread); return(false); } break; case InterfaceTypeDef parIntfType: // parent type is interface; fragment's type must be object implementing interface if (!parIntfType.PossibleTypes.Contains(fragmOnTypeDef)) { AddError($"Fragment ref {fragmName}: fragment is defined on type '{fragmOnTypeDef.Name}'" + $" which is not compatible with type '{parentType.Name}'.", fragmentSpread); return(false); } break; case UnionTypeDef parUnionType: // fragment's on-type must be one of the unioned types; of if fragm is on interface, implemented by at least one of the types if (fragmOnTypeDef is InterfaceTypeDef fragmIntType) { if (!parUnionType.PossibleTypes.Any(t => t.Implements.Contains(fragmIntType))) { AddError($"Fragment ref {fragmName}: fragment is defined on interface '{fragmIntType.Name}' which is " + $"not implemented by any of the unioned types in '{parentType.Name}'.", fragmentSpread); return(false); } } else { // fragm is on object type if (!parUnionType.PossibleTypes.Contains(fragmOnTypeDef)) { AddError($"Fragment ref {fragmName}: fragment is defined on type '{fragmOnTypeDef.Name}' which is not " + $"one of the unioned types in '{parentType.Name}'.", fragmentSpread); return(false); } } break; } return(true); }