public void ParseQueryWithFragment() { // arrange byte[] sourceText = Encoding.UTF8.GetBytes( "query a { x { ... y } } fragment y on Type { z } "); // act var parser = new Utf8GraphQLParser( sourceText, ParserOptions.Default); DocumentNode document = parser.Parse(); // assert Assert.Collection(document.Definitions, t => { Assert.IsType <OperationDefinitionNode>(t); var operationDefinition = (OperationDefinitionNode)t; Assert.Equal(SyntaxKind.OperationDefinition, operationDefinition.Kind); Assert.Equal("a", operationDefinition.Name.Value); Assert.Equal(OperationType.Query, operationDefinition.Operation); Assert.Empty(operationDefinition.VariableDefinitions); Assert.Empty(operationDefinition.Directives); Assert.Collection(operationDefinition.SelectionSet.Selections, s1 => { Assert.IsType <FieldNode>(s1); FieldNode field1 = (FieldNode)s1; Assert.Null(field1.Alias); Assert.Equal("x", field1.Name.Value); Assert.Empty(field1.Arguments); Assert.Empty(field1.Directives); Assert.Collection(field1.SelectionSet.Selections, s2 => { Assert.IsType <FragmentSpreadNode>(s2); FragmentSpreadNode spread = (FragmentSpreadNode)s2; Assert.Equal("y", spread.Name.Value); Assert.Empty(spread.Directives); }); }); }, t => { Assert.IsType <FragmentDefinitionNode>(t); var fragmentDefinition = (FragmentDefinitionNode)t; Assert.Equal("y", fragmentDefinition.Name.Value); Assert.Equal("Type", fragmentDefinition.TypeCondition.Name.Value); Assert.Empty(fragmentDefinition.VariableDefinitions); Assert.Empty(fragmentDefinition.Directives); ISelectionNode selectionNode = fragmentDefinition .SelectionSet.Selections.Single(); Assert.IsType <FieldNode>(selectionNode); Assert.Equal("z", ((FieldNode)selectionNode).Name.Value); }); }
private void ResolveFields( CompilerContext context, ISelectionNode selection, SelectionIncludeCondition?includeCondition) { switch (selection.Kind) { case SyntaxKind.Field: ResolveFieldSelection( context, (FieldNode)selection, includeCondition); break; case SyntaxKind.InlineFragment: ResolveInlineFragment( context, (InlineFragmentNode)selection, includeCondition); break; case SyntaxKind.FragmentSpread: ResolveFragmentSpread( context, (FragmentSpreadNode)selection, includeCondition); break; } }
private void CollectFields( ObjectType typeContext, SelectionSetNode selectionSet, SelectionIncludeCondition?includeCondition, IDictionary <ISelectionNode, SelectionIncludeCondition> includeConditionLookup, IDictionary <string, PreparedSelection> fields, bool internalSelection) { for (var i = 0; i < selectionSet.Selections.Count; i++) { ISelectionNode selection = selectionSet.Selections[i]; SelectionIncludeCondition?selectionVisibility = includeCondition; if (selectionVisibility is null) { includeConditionLookup.TryGetValue(selection, out selectionVisibility); } ResolveFields( typeContext, selection, ExtractVisibility(selection, selectionVisibility), includeConditionLookup, fields, internalSelection); } }
private void ResolveFields( ObjectType type, ISelectionNode selection, Path path, FieldVisibility fieldVisibility, IDictionary <string, FieldInfo> fields) { if (selection is FieldNode fs) { ResolveFieldSelection( type, fs, path, fieldVisibility, fields); } else if (selection is FragmentSpreadNode fragSpread) { ResolveFragmentSpread( type, fragSpread, path, fieldVisibility, fields); } else if (selection is InlineFragmentNode inlineFrag) { ResolveInlineFragment( type, inlineFrag, path, fieldVisibility, fields); } }
/// <summary> /// Adds the sub selection. /// </summary> /// <param name="selection">The <see cref="ISelectionNode"/> to which the sub selection is added.</param> /// <param name="child">The sub selection.</param> /// <returns>The <see cref="ISelectionNode"/></returns> public static ISelectionNode AddSubSelection(this ISelectionNode selection, ISelectionNode child) { Guard.ArgumentNotNull(selection, nameof(selection)); Guard.ArgumentNotNull(child, nameof(child)); selection.SelectionSet.Add(child); return(selection); }
private bool TryGetFragment(object container, ISelectionNode selection, out IFragment fragment) { var fragments = selection.SelectionSet.OfType <IFragment>().ToDictionary(it => it.GraphType, it => it); if (fragments.Count == 0 || null == container) { return((fragment = null) != null); } var containerType = container.GetType(); var graphTypes = fragments.Select(it => it.Key).ToArray(); var graphType = SelectBest(containerType); if (null == graphType) { return((fragment = null) != null); } return((fragment = fragments[graphType]) != null); IGraphType SelectBest(Type type) { var best = graphTypes.SingleOrDefault(it => it.Type == type); if (null != best) { return(best); } var parent = type.BaseType; return(parent == null ? null : SelectBest(parent)); } }
public void ParseQueryWithFragment() { // arrange string sourceText = "query a { x { ... y } } fragment y on Type { z } "; Source source = new Source(sourceText); // act Parser parser = new Parser(); DocumentNode document = parser.Parse(sourceText); // assert Assert.Collection(document.Definitions, t => { Assert.IsType <OperationDefinitionNode>(t); var operationDefinition = (OperationDefinitionNode)t; Assert.Equal(NodeKind.OperationDefinition, operationDefinition.Kind); Assert.Equal("a", operationDefinition.Name.Value); Assert.Equal(OperationType.Query, operationDefinition.Operation); Assert.Empty(operationDefinition.VariableDefinitions); Assert.Empty(operationDefinition.Directives); Assert.Collection(operationDefinition.SelectionSet.Selections, s1 => { Assert.IsType <FieldNode>(s1); FieldNode field1 = (FieldNode)s1; Assert.Null(field1.Alias); Assert.Equal("x", field1.Name.Value); Assert.Empty(field1.Arguments); Assert.Empty(field1.Directives); Assert.Collection(field1.SelectionSet.Selections, s2 => { Assert.IsType <FragmentSpreadNode>(s2); FragmentSpreadNode spread = (FragmentSpreadNode)s2; Assert.Equal("y", spread.Name.Value); Assert.Empty(spread.Directives); }); }); }, t => { Assert.IsType <FragmentDefinitionNode>(t); var fragmentDefinition = (FragmentDefinitionNode)t; Assert.Equal("y", fragmentDefinition.Name.Value); Assert.Equal("Type", fragmentDefinition.TypeCondition.Name.Value); Assert.Empty(fragmentDefinition.VariableDefinitions); Assert.Empty(fragmentDefinition.Directives); ISelectionNode selectionNode = fragmentDefinition .SelectionSet.Selections.Single(); Assert.IsType <FieldNode>(selectionNode); Assert.Equal("z", ((FieldNode)selectionNode).Name.Value); }); }
private bool ShouldBeIncluded(ISelectionNode selection) { if (selection.Directives.Skip(_variables)) { return(false); } return(selection.Directives.Include(_variables)); }
private void ResolveFieldSelection( CompilerContext context, FieldNode selection, SelectionIncludeCondition?includeCondition) { NameString fieldName = selection.Name.Value; NameString responseName = selection.Alias is null ? selection.Name.Value : selection.Alias.Value; if (context.Type.Fields.TryGetField(fieldName, out IObjectField? field)) { if ((selection.SelectionSet is null || selection.SelectionSet.Selections.Count == 0) && field.Type.NamedType().IsCompositeType()) { throw OperationCompiler_NoCompositeSelections(selection); } if (context.Fields.TryGetValue(responseName, out Selection? preparedSelection)) { preparedSelection.AddSelection(selection, includeCondition); } else { // if this is the first time we find a selection to this field we have to // create a new prepared selection. preparedSelection = new Selection( context.Type, field, selection, responseName: responseName, resolverPipeline: CreateFieldMiddleware(field, selection), arguments: CoerceArgumentValues(field, selection, responseName), includeCondition: includeCondition, internalSelection: context.IsInternalSelection); context.Fields.Add(responseName, preparedSelection); } if (includeCondition is not null && selection.SelectionSet is not null) { for (var i = 0; i < selection.SelectionSet.Selections.Count; i++) { ISelectionNode child = selection.SelectionSet.Selections[i]; if (!context.IncludeConditionLookup.ContainsKey(child)) { context.IncludeConditionLookup.Add(child, includeCondition); } } } } else { throw FieldDoesNotExistOnType(selection, context.Type.Name); } }
public override void VisitSelectionNode <T>(LogContext context, ISelectionNode <T> node) { using (_log.BeginScope <SelectionNode <T> >()) { _log.LogDebug("Condition: {0}", node.Condition); base.VisitAlphaNode(context, node); } }
private bool IsRelevant(ISelectionNode selection, string schemaName) { if (selection.Directives.Any(t => t.IsDelegateDirective())) { return(false); } return(selection.Directives .Any(t => t.IsSchemaDirective(schemaName))); }
public virtual void VisitSelectionNode <T>(TContext context, ISelectionNode <T> node) where T : class { VisitAlphaMemoryNode(context, node.MemoryNode); foreach (var childNode in node.GetChildNodes <INode>()) { childNode.Accept(this, context); } }
public override void VisitSelectionNode <T>(GraphContext context, ISelectionNode <T> node) { var nodeInfo = new Node(Interlocked.Increment(ref _id), node, typeof(T), "selection"); context.Add(nodeInfo); context.Link(nodeInfo, new Node(-1, node.MemoryNode, typeof(T), "")); foreach (var childNode in node.GetChildNodes <INode>()) { context.Link(nodeInfo, new Node(-1, childNode, typeof(T), "")); } base.VisitSelectionNode(context, node); }
private void ResolveFields( INamedOutputType type, ISelectionNode selection, Path path, IDictionary <string, FieldSelection> fields, ICollection <IFragmentNode> fragments) { if (selection is FieldNode fs && type is IComplexOutputType ct) { ResolveFieldSelection( ct, fs, path, fields); }
public SelectionSetNode AddSelection( ISelectionNode selection) { if (selection == null) { throw new ArgumentNullException(nameof(selection)); } var selections = new List <ISelectionNode>(Selections); selections.Add(selection); return(new SelectionSetNode( Location, selections)); }
private static bool HasFields(SelectionSetNode selectionSet) { for (int i = 0; i < selectionSet.Selections.Count; i++) { ISelectionNode selection = selectionSet.Selections[i]; if (selection.Kind == NodeKind.Field) { if (!IsTypeNameField(((FieldNode)selection).Name.Value)) { return(true); } } } return(false); }
private void ResolveFields( ObjectType type, ISelectionNode selection, Action <QueryError> reportError, Dictionary <string, FieldSelection> fields) { if (selection is FieldNode fs) { ResolveFieldSelection(type, fs, reportError, fields); } else if (selection is FragmentSpreadNode fragSpread) { ResolveFragmentSpread(type, fragSpread, reportError, fields); } else if (selection is InlineFragmentNode inlineFrag) { ResolveInlineFragment(type, inlineFrag, reportError, fields); } }
protected virtual ISelectionNode RewriteSelection( ISelectionNode node, TContext context) { switch (node) { case FieldNode value: return(RewriteField(value, context)); case FragmentSpreadNode value: return(RewriteFragmentSpread(value, context)); case InlineFragmentNode value: return(RewriteInlineFragment(value, context)); default: throw new NotSupportedException(); } }
private void ResolveFields( ObjectType type, ISelectionNode selection, Action <QueryError> reportError, Dictionary <string, FieldSelection> fields) { if (selection is FieldNode fs) { string fieldName = fs.Name.Value; if (fieldName.StartsWith("__")) { ResolveIntrospectionField(type, fs, reportError, fields); } else if (type.Fields.TryGetValue(fieldName, out Field field)) { string name = fs.Alias == null ? fs.Name.Value : fs.Alias.Value; fields[name] = new FieldSelection(fs, field, name); } else { reportError(new FieldError( "Could not resolve the specified field.", fs)); } } else if (selection is FragmentSpreadNode fragmentSpread) { Fragment fragment = _fragments.GetFragments(fragmentSpread.Name.Value) .FirstOrDefault(t => DoesFragmentTypeApply(type, t.TypeCondition)); if (fragment != null) { CollectFields(type, fragment.SelectionSet, reportError, fields); } } else if (selection is InlineFragmentNode inlineFragment) { Fragment fragment = _fragments.GetFragment(inlineFragment); if (DoesFragmentTypeApply(type, fragment.TypeCondition)) { CollectFields(type, fragment.SelectionSet, reportError, fields); } } }
protected virtual void VisitSelection(ISelectionNode node) { switch (node) { case FieldNode value: VisitField(value); break; case FragmentSpreadNode value: VisitFragmentSpread(value); break; case InlineFragmentNode value: VisitInlineFragment(value); break; default: throw new NotSupportedException(); } }
private void ResolveFields( ObjectType typeContext, ISelectionNode selection, SelectionIncludeCondition?includeCondition, IDictionary <ISelectionNode, SelectionIncludeCondition> includeConditionLookup, IDictionary <string, PreparedSelection> fields, bool internalSelection) { switch (selection.Kind) { case SyntaxKind.Field: ResolveFieldSelection( typeContext, (FieldNode)selection, includeCondition, includeConditionLookup, fields, internalSelection); break; case SyntaxKind.InlineFragment: ResolveInlineFragment( typeContext, (InlineFragmentNode)selection, includeCondition, includeConditionLookup, fields, internalSelection); break; case SyntaxKind.FragmentSpread: ResolveFragmentSpread( typeContext, (FragmentSpreadNode)selection, includeCondition, includeConditionLookup, fields, internalSelection); break; } }
private void CollectFields( CompilerContext context, SelectionSetNode selectionSet, SelectionIncludeCondition?includeCondition) { for (var i = 0; i < selectionSet.Selections.Count; i++) { ISelectionNode selection = selectionSet.Selections[i]; SelectionIncludeCondition?selectionCondition = includeCondition; if (selectionCondition is null) { context.IncludeConditionLookup.TryGetValue(selection, out selectionCondition); } ResolveFields( context, selection, ExtractVisibility(selection, selectionCondition)); } }
public virtual void VisitSelectionNode <T>(TContext context, ISelectionNode <T> node) where T : class { VisitAlphaNode(context, node); }
private void ResolveFieldSelection( CompilerContext context, FieldNode selection, SelectionIncludeCondition?includeCondition) { NameString fieldName = selection.Name.Value; NameString responseName = selection.Alias is null ? selection.Name.Value : selection.Alias.Value; if (context.Type.Fields.TryGetField(fieldName, out IObjectField? field)) { if ((selection.SelectionSet is null || selection.SelectionSet.Selections.Count == 0) && field.Type.NamedType().IsCompositeType()) { throw OperationCompiler_NoCompositeSelections(selection); } if (context.Fields.TryGetValue(responseName, out Selection? preparedSelection)) { preparedSelection.AddSelection(selection, includeCondition); } else { Func <object, IAsyncEnumerable <object?> >?createStream = null; bool isStreamable = selection.IsStreamable(); if (field.MaybeStream || field.Type.IsListType() && isStreamable) { IType elementType = field.Type.ElementType(); if (elementType.IsCompositeType()) { Type runtimeType = elementType.ToRuntimeType(); CreateStreamDelegate streamDelegate = CreateStream(runtimeType); createStream = o => streamDelegate(o); } } // if this is the first time we find a selection to this field we have to // create a new prepared selection. preparedSelection = new Selection( GetNextId(), context.Type, field, selection.SelectionSet is not null ? selection.WithSelectionSet( selection.SelectionSet.WithSelections( selection.SelectionSet.Selections)) : selection, responseName: responseName, resolverPipeline: CreateFieldMiddleware(field, selection), pureResolver: TryCreatePureField(field, selection), strategy: field.IsParallelExecutable ? null // use default strategy : SelectionExecutionStrategy.Serial, arguments: CoerceArgumentValues(field, selection, responseName), includeCondition: includeCondition, internalSelection: context.IsInternalSelection, createStream: createStream, isStreamable: isStreamable); context.Fields.Add(responseName, preparedSelection); } if (includeCondition is not null && selection.SelectionSet is not null) { SelectionPath selectionPath = context.SelectionPath.Append(responseName); for (var i = 0; i < selection.SelectionSet.Selections.Count; i++) { ISelectionNode child = selection.SelectionSet.Selections[i]; var reference = new SelectionReference(selectionPath, child); if (!context.IncludeConditionLookup.ContainsKey(reference)) { context.IncludeConditionLookup.Add(reference, includeCondition); } } } } else { throw FieldDoesNotExistOnType(selection, context.Type.Name); } }