Exemple #1
0
        /// <summary>
        /// Creates an AnyNode or an AllNode from the given
        /// </summary>
        /// <param name="state">State of binding.</param>
        /// <param name="parent">Parent node to the lambda.</param>
        /// <param name="lambdaExpression">Bound Lambda expression.</param>
        /// <param name="newRangeVariable">The new range variable being added by this lambda node.</param>
        /// <param name="queryTokenKind">Token kind.</param>
        /// <returns>A new LambdaNode bound to metadata.</returns>
        internal static LambdaNode CreateLambdaNode(
            BindingState state,
            CollectionNode parent,
            SingleValueNode lambdaExpression,
            RangeVariable newRangeVariable,
            QueryTokenKind queryTokenKind)
        {
            LambdaNode lambdaNode;

            if (queryTokenKind == QueryTokenKind.Any)
            {
                lambdaNode = new AnyNode(new Collection <RangeVariable>(state.RangeVariables.ToList()), newRangeVariable)
                {
                    Body   = lambdaExpression,
                    Source = parent,
                };
            }
            else
            {
                Debug.Assert(queryTokenKind == QueryTokenKind.All, "LambdaQueryNodes must be Any or All only.");
                lambdaNode = new AllNode(new Collection <RangeVariable>(state.RangeVariables.ToList()), newRangeVariable)
                {
                    Body   = lambdaExpression,
                    Source = parent,
                };
            }

            return(lambdaNode);
        }
        private void TestLambda <TLambda, TParam, TReturn>(CollectionNode source, string parameterName, SingleValueNode body, Expression <Func <TParam, TReturn> > expectedExpression)
            where TLambda : LambdaNode
        {
            ResourceRangeVariable currentRangeVariable = null;

            if (parameterName != null)
            {
                currentRangeVariable = new ResourceRangeVariable(parameterName, new EdmEntityTypeReference(this.customerEdmType, false), this.entitySet);
                this.testSubject.ParameterExpressions[currentRangeVariable] = Expression.Parameter(typeof(TParam), parameterName);
            }

            LambdaNode node;

            if (typeof(TLambda) == typeof(AnyNode))
            {
                node = new AnyNode(new Collection <RangeVariable>(), currentRangeVariable);
            }
            else
            {
                node = new AllNode(new Collection <RangeVariable>(), currentRangeVariable);
            }

            node.Body   = body;
            node.Source = source;

            var result = this.testSubject.TranslateNode(node);

            CompareExpressions(expectedExpression.Body, result);
        }
        private string BindAnyNode(AnyNode anyNode, ICollection <BinderNode> nodes)
        {
            const string pattern = @"^\.";
            var          rgx     = new Regex(pattern);

            var    source = rgx.Replace(Bind(anyNode.Source, nodes), String.Empty);
            string body   = null;

            var innerQuery = "exists ( from " + source + " " + anyNode.RangeVariables.First().Name;

            if (anyNode.Body != null)
            {
                body        = Bind(anyNode.Body, nodes);
                innerQuery += " where " + body;
            }

            nodes.Add(new BinderNode
            {
                Left         = source,
                OperatorKind = BinaryOperatorKind.Equal,
                Right        = body,
            });

            return(innerQuery + ")");
        }
 private void FindKeyNodes()
 {
     for (int i = nodes.Count - 1; i > -1; i--)
     {
         if (nodes[i] == null)
         {
             nodes.RemoveAt(i);
         }
     }
     foreach (BaseNode node in nodes)
     {
         node.graph = this;
         if (node.NodeType == NodeType.Start)
         {
             startNode = (StartNode)node;
         }
         if (node.NodeType == NodeType.End)
         {
             endNode = (EndNode)node;
         }
         if (node.NodeType == NodeType.Any)
         {
             anyNode = (AnyNode)node;
         }
     }
 }
        /// <summary>
        /// Override this method to restrict the 'any' query inside the filter query.
        /// </summary>
        /// <remarks>
        /// This method is intended to be called from method overrides in subclasses. This method also supports unit-testing scenarios and is not intended to be called from user code.
        /// Call the Validate method to validate a <see cref="FilterQueryOption"/> instance.
        /// </remarks>
        /// <param name="anyNode"></param>
        /// <param name="settings"></param>
        public virtual void ValidateAnyNode(AnyNode anyNode, ODataValidationSettings settings)
        {
            if (anyNode == null)
            {
                throw Error.ArgumentNull("anyNode");
            }

            if (settings == null)
            {
                throw Error.ArgumentNull("settings");
            }

            ValidateFunction("any", settings);
            EnterLambda(settings);

            try
            {
                ValidateQueryNode(anyNode.Source, settings);

                if (anyNode.Body != null && anyNode.Body.Kind != QueryNodeKind.Constant)
                {
                    ValidateQueryNode(anyNode.Body, settings);
                }
            }
            finally
            {
                ExitLambda();
            }
        }
Exemple #6
0
        private Node ParseFactor()
        {
            Node  n;
            Token t = GetToken();

            switch (t)
            {
            case Token.Byte:
                n = new ByteNode(this.b, positions.Count);
                positions.Add(n);
                AddCharacterClass(b);
                break;

            case Token.Dot:
                n = new AnyNode(positions.Count);
                positions.Add(n);
                break;

            case Token.LParen:
                n = Parse();
                Expect(Token.RParen);
                break;

            default:
                return(SyntaxError());
            }
            return(n);
        }
Exemple #7
0
        /// <summary>
        /// We return the <see cref="ResourceRangeVariableReferenceNode"/> within a <see cref="QueryNode"/>
        /// </summary>
        /// <param name="node">The node to extract the ResourceRangeVariableReferenceNode.</param>
        /// <returns>The extracted ResourceRangeVariableReferenceNode.</returns>
        private ResourceRangeVariableReferenceNode GetResourceRangeVariableReferenceNode(QueryNode node)
        {
            if (node == null)
            {
                return(null);
            }

            switch (node.Kind)
            {
            case QueryNodeKind.SingleValuePropertyAccess:
                SingleValuePropertyAccessNode singleValuePropertyAccessNode = node as SingleValuePropertyAccessNode;
                return(GetResourceRangeVariableReferenceNode(singleValuePropertyAccessNode.Source));

            case QueryNodeKind.Convert:
                ConvertNode convertNode = node as ConvertNode;
                return(GetResourceRangeVariableReferenceNode(convertNode.Source));

            case QueryNodeKind.Any:
                AnyNode anyNode = node as AnyNode;
                return(GetResourceRangeVariableReferenceNode(anyNode.Source));

            case QueryNodeKind.SingleValueFunctionCall:
                SingleValueFunctionCallNode singleValueFunctionCallNode = node as SingleValueFunctionCallNode;
                return(GetResourceRangeVariableReferenceNode(singleValueFunctionCallNode.Parameters.First()));

            case QueryNodeKind.ResourceRangeVariableReference:
                return(node as ResourceRangeVariableReferenceNode);

            case QueryNodeKind.SingleValueOpenPropertyAccess:
                SingleValueOpenPropertyAccessNode singleValueOpenPropertyAccessNode = node as SingleValueOpenPropertyAccessNode;
                return(GetResourceRangeVariableReferenceNode(singleValueOpenPropertyAccessNode.Source));

            case QueryNodeKind.SingleComplexNode:
                SingleComplexNode singleComplexNode = node as SingleComplexNode;
                return(GetResourceRangeVariableReferenceNode(singleComplexNode.Source));

            case QueryNodeKind.CollectionComplexNode:
                CollectionComplexNode collectionComplexNode = node as CollectionComplexNode;
                return(GetResourceRangeVariableReferenceNode(collectionComplexNode.Source));

            case QueryNodeKind.CollectionNavigationNode:
                CollectionNavigationNode collectionNavigationNode = node as CollectionNavigationNode;
                return(GetResourceRangeVariableReferenceNode(collectionNavigationNode.Source));

            case QueryNodeKind.SingleNavigationNode:
                SingleNavigationNode singleNavigationNode = node as SingleNavigationNode;
                return(GetResourceRangeVariableReferenceNode(singleNavigationNode.Source));

            case QueryNodeKind.CollectionResourceFunctionCall:
                CollectionResourceFunctionCallNode collectionResourceFunctionCallNode = node as CollectionResourceFunctionCallNode;
                return(GetResourceRangeVariableReferenceNode(collectionResourceFunctionCallNode.Source));

            case QueryNodeKind.SingleResourceFunctionCall:
                SingleResourceFunctionCallNode singleResourceFunctionCallNode = node as SingleResourceFunctionCallNode;
                return(GetResourceRangeVariableReferenceNode(singleResourceFunctionCallNode.Source));
            }

            return(null);
        }
 /// <summary>
 /// Translates a V3 AnyNode to V4 AnyNode
 /// </summary>
 /// <param name="nodeIn">V3 AnyNode</param>
 /// <returns>V4 AnyNode</returns>
 public override QueryNode Visit(Data.OData.Query.SemanticAst.AnyNode nodeIn)
 {
     List<RangeVariable> translated = nodeIn.RangeVariables.Select(r => TranslateRangeVariable(r)).ToList();
     AnyNode ret = new AnyNode(new Collection<RangeVariable>(translated), TranslateRangeVariable(nodeIn.CurrentRangeVariable));
     ret.Source = (CollectionNode)nodeIn.Source.Accept(this);
     ret.Body = (SingleValueNode)nodeIn.Body.Accept(this);
     return ret;
 }
Exemple #9
0
        public override int Visit(AnyNode nodeIn)
        {
            var sourceNode = (CollectionNavigationNode)nodeIn.Source;
            int h1         = sourceNode.NavigationProperty.Name.GetHashCode();
            int h2         = nameof(Enumerable.Any).GetHashCode();
            int h3         = TranslateNode(nodeIn.Body);

            return(CombineHashCodes(h1, h2, h3));
        }
Exemple #10
0
 public void TypeReferenceShouldBeBoolean()
 {
     EntityRangeVariable rangeVariable = (EntityRangeVariable)NodeFactory.CreateImplicitRangeVariable(HardCodedTestModel.GetDogTypeReference(), HardCodedTestModel.GetDogsSet());
     Collection<RangeVariable> rangeVariables = new Collection<RangeVariable>
         {
             rangeVariable
         };
     AnyNode anyNode = new AnyNode(rangeVariables, rangeVariable);
     anyNode.TypeReference.FullName().Should().Be("Edm.Boolean");
 }
Exemple #11
0
        private void ValidateAnyNode(AnyNode node, ValidationSettings settings)
        {
            ValidateFunction("any", settings);
            ValidateQueryNode(node.Source, settings);

            if (node.Body != null && node.Body.Kind != QueryNodeKind.Constant)
            {
                ValidateQueryNode(node.Body, settings);
            }
        }
Exemple #12
0
 public void KindShouldBeAnyNode()
 {
     EntityRangeVariable rangeVariable = (EntityRangeVariable)NodeFactory.CreateImplicitRangeVariable(HardCodedTestModel.GetDogTypeReference(), HardCodedTestModel.GetDogsSet());
     Collection<RangeVariable> rangeVariables = new Collection<RangeVariable>
         {
             rangeVariable
         };
     AnyNode anyNode = new AnyNode(rangeVariables, rangeVariable);
     anyNode.InternalKind.Should().Be(InternalQueryNodeKind.Any);
 }
Exemple #13
0
        static string BindAnyNode(AnyNode anyNode, List <DbParameter> pars, DbUtility dbUtility)
        {
            string innerQuery = "exists ( from " + Bind(anyNode.Source, pars, dbUtility) + " " + anyNode.RangeVariables.First().Name;

            if (anyNode.Body != null)
            {
                innerQuery += " where " + Bind(anyNode.Body, pars, dbUtility);
            }
            return(innerQuery + ")");
        }
        private string BindAnyNode(AnyNode anyNode)
        {
            string innerQuery = "exists ( from " + Bind(anyNode.Source) + " " + anyNode.RangeVariables.First().Name;

            if (anyNode.Body != null)
            {
                innerQuery += " where " + Bind(anyNode.Body);
            }
            return(innerQuery + ")");
        }
        protected virtual QueryNode VisitAny(AnyNode node, AzureQueryOptimizerState state)
        {
            QueryNode queryNode1 = this.Visit(node.SourceNode, state);
            QueryNode queryNode2 = this.Visit(node.PredicateNode, state);

            if (queryNode2.NodeType == QueryNodeType.MatchAll)
            {
                return((QueryNode) new AnyNode(queryNode1, queryNode2));
            }
            return((QueryNode) new AnyNode(this.VisitAnd(new AndNode(queryNode1, queryNode2), state), (QueryNode) new MatchAllNode()));
        }
        public void TypeReferenceShouldBeBoolean()
        {
            ResourceRangeVariable      rangeVariable  = (ResourceRangeVariable)NodeFactory.CreateImplicitRangeVariable(HardCodedTestModel.GetDogTypeReference(), HardCodedTestModel.GetDogsSet());
            Collection <RangeVariable> rangeVariables = new Collection <RangeVariable>
            {
                rangeVariable
            };
            AnyNode anyNode = new AnyNode(rangeVariables, rangeVariable);

            Assert.Equal("Edm.Boolean", anyNode.TypeReference.FullName());
        }
        public void KindShouldBeAnyNode()
        {
            ResourceRangeVariable      rangeVariable  = (ResourceRangeVariable)NodeFactory.CreateImplicitRangeVariable(HardCodedTestModel.GetDogTypeReference(), HardCodedTestModel.GetDogsSet());
            Collection <RangeVariable> rangeVariables = new Collection <RangeVariable>
            {
                rangeVariable
            };
            AnyNode anyNode = new AnyNode(rangeVariables, rangeVariable);

            Assert.Equal(InternalQueryNodeKind.Any, anyNode.InternalKind);
        }
Exemple #18
0
        public void KindShouldBeAnyNode()
        {
            EntityRangeVariable        rangeVariable  = (EntityRangeVariable)NodeFactory.CreateImplicitRangeVariable(HardCodedTestModel.GetDogTypeReference(), HardCodedTestModel.GetDogsSet());
            Collection <RangeVariable> rangeVariables = new Collection <RangeVariable>
            {
                rangeVariable
            };
            AnyNode anyNode = new AnyNode(rangeVariables, rangeVariable);

            anyNode.InternalKind.Should().Be(InternalQueryNodeKind.Any);
        }
Exemple #19
0
        public void TypeReferenceShouldBeBoolean()
        {
            EntityRangeVariable        rangeVariable  = (EntityRangeVariable)NodeFactory.CreateImplicitRangeVariable(HardCodedTestModel.GetDogTypeReference(), HardCodedTestModel.GetDogsSet());
            Collection <RangeVariable> rangeVariables = new Collection <RangeVariable>
            {
                rangeVariable
            };
            AnyNode anyNode = new AnyNode(rangeVariables, rangeVariable);

            anyNode.TypeReference.FullName().Should().Be("Edm.Boolean");
        }
Exemple #20
0
 /// <summary>
 /// Translates a <see cref="AnyNode"/> into a corresponding <see cref="string"/>.
 /// </summary>
 /// <param name="node">The node to translate.</param>
 /// <returns>The translated string.</returns>
 public override string Visit(AnyNode node)
 {
     if (node.CurrentRangeVariable == null && node.Body.Kind == QueryNodeKind.Constant)
     {
         return(string.Concat(this.TranslateNode(node.Source), Constants.SymbolForwardSlash, Constants.KeywordAny, Constants.SymbolOpenParen, Constants.SymbolClosedParen));
     }
     else
     {
         return(string.Concat(this.TranslateNode(node.Source), Constants.SymbolForwardSlash, Constants.KeywordAny, Constants.SymbolOpenParen, node.CurrentRangeVariable.Name, ":", this.TranslateNode(node.Body), Constants.SymbolClosedParen));
     }
 }
        protected virtual QueryNode VisitAny(AnyNode node, ElasticSearchQueryOptimizerState state)
        {
            var node2 = Visit(node.SourceNode, state);
            var node3 = Visit(node.PredicateNode, state);

            if (node3.NodeType == QueryNodeType.MatchAll)
            {
                return(new AnyNode(node2, node3));
            }
            return(new AnyNode(VisitAnd(new AndNode(node2, node3), state), new MatchAllNode()));
        }
 /// <summary>
 /// Translates a <see cref="AnyNode"/> into a corresponding <see cref="string"/>.
 /// </summary>
 /// <param name="node">The node to translate.</param>
 /// <returns>The translated string.</returns>
 public override string Visit(AnyNode node)
 {
     //should return something like JOIN a in c.companies
     //if (node.CurrentRangeVariable == null && node.Body.Kind == QueryNodeKind.Constant)
     //{
     //    return string.Concat(Constants.Delimiter, this.TranslateNode(node.Source, true), Constants.SymbolForwardSlash, Constants.KeywordAny, Constants.SymbolOpenParen, Constants.SymbolClosedParen, Constants.Delimiter);
     //}
     //else
     //{
     return(string.Concat(Constants.Delimiter, this.TranslateNode(node.Source, true), Constants.Delimiter, this.TranslateNode(node.Body)));
     //}
 }
Exemple #23
0
        /// <summary>
        /// in AnyNode: such as SkuBomParents/any(m: m eq 1363)
        /// anyNode.Source is SkuBomParents, which is a CollectionPropertyAccessNode.
        /// anyNode.Body is m eq 1363, which is a BinaryOperatorNode.
        /// For $filter=SkuBomParents/any(m: m eq 1363)
        /// it translates to
        /// 1 self join clause: join d0 in c.SkuBomParents
        /// the where clause:   d0 = 1363
        /// For $filter=BGs/any(m: m eq '640') and DCs/any(m: m eq 'ACT01')
        /// it translates to
        /// 2 self join clauses:
        /// join d0 in c.BGs
        /// join d1 in c.DCs
        /// and the where clause is (d0 = "640") and (d1="ACT01")
        /// For SkuChildren/any(m:m/dummy/any(n:n eq 'abc'))
        /// it translates to
        /// 2 self join clauses:
        /// join d0 in c.SkuChildren
        /// join d1 in d0.dummy
        /// and the where clause is ((d1 = "abc"))
        /// </summary>
        private string TranslateAnyNode(AnyNode anyNode)
        {
            var cnt = whereAndJoinClause.JoinClause.Count();
            var rangeVariableName = string.Format("d{0}", cnt);
            var src = Translate(anyNode.Source);

            whereAndJoinClause.JoinClause.Add(string.Format("join {0} in {1}", rangeVariableName, src));
            RangeVariablesNameForAnyNodeBody.Push(rangeVariableName);
            var res = Translate(anyNode.Body);

            RangeVariablesNameForAnyNodeBody.Pop();
            return(res);
        }
        /// <summary>
        /// Translates a <see cref="AnyNode"/> into a corresponding <see cref="String"/>.
        /// </summary>
        /// <param name="node">The node to translate.</param>
        /// <returns>The translated String.</returns>
        public override String Visit(AnyNode node)
        {
            ExceptionUtils.CheckArgumentNotNull(node, "node");

            if (node.CurrentRangeVariable == null && node.Body.Kind == QueryNodeKind.Constant)
            {
                return(String.Concat(this.TranslateNode(node.Source), ExpressionConstants.SymbolForwardSlash, ExpressionConstants.KeywordAny, ExpressionConstants.SymbolOpenParen, ExpressionConstants.SymbolClosedParen));
            }
            else
            {
                return(String.Concat(this.TranslateNode(node.Source), ExpressionConstants.SymbolForwardSlash, ExpressionConstants.KeywordAny, ExpressionConstants.SymbolOpenParen, node.CurrentRangeVariable.Name, ":", this.TranslateNode(node.Body), ExpressionConstants.SymbolClosedParen));
            }
        }
Exemple #25
0
 public void RangeVariableShouldBeSetCorrectly()
 {
     EntityRangeVariable rangeVariable =
         (EntityRangeVariable)
         NodeFactory.CreateImplicitRangeVariable(HardCodedTestModel.GetDogTypeReference(), HardCodedTestModel.GetDogsSet());
     Collection<RangeVariable> rangeVariables = new Collection<RangeVariable>
         {
             rangeVariable
         };
     AnyNode anyNode = new AnyNode(rangeVariables, rangeVariable);
     anyNode.CurrentRangeVariable.Name.Should().Be(ExpressionConstants.It);
     anyNode.CurrentRangeVariable.Kind.Should().Be(RangeVariableKind.Entity);
     anyNode.CurrentRangeVariable.TypeReference.FullName().Should().Be(HardCodedTestModel.GetDogTypeReference().FullName());
 }
Exemple #26
0
        /// <summary>
        /// Binds a <see cref="AnyNode"/> to create a LINQ <see cref="Expression"/> that
        /// represents the semantics of the <see cref="AnyNode"/>.
        /// </summary>
        /// <param name="anyNode">The node to bind.</param>
        /// <returns>The LINQ <see cref="Expression"/> created.</returns>
        public virtual Expression BindAnyNode(AnyNode anyNode)
        {
            if (anyNode == null)
            {
                throw Error.ArgumentNull(nameof(anyNode));
            }

            ParameterExpression anyIt = HandleLambdaParameters(anyNode.RangeVariables);

            Expression source;

            Contract.Assert(anyNode.Source != null);
            source = Bind(anyNode.Source);

            Expression body = null;

            // uri parser places an Constant node with value true for empty any() body
            if (anyNode.Body != null && anyNode.Body.Kind != QueryNodeKind.Constant)
            {
                body = Bind(anyNode.Body);
                body = ApplyNullPropagationForFilterBody(body);
                body = Expression.Lambda(body, anyIt);
            }
            else if (anyNode.Body != null && anyNode.Body.Kind == QueryNodeKind.Constant &&
                     (bool)(anyNode.Body as ConstantNode).Value == false)
            {
                // any(false) is the same as just false
                ExitLamdbaScope();
                return(FalseConstant);
            }

            Expression any = Any(source, body);

            ExitLamdbaScope();

            if (QuerySettings.HandleNullPropagation == HandleNullPropagationOption.True && IsNullable(source.Type))
            {
                // IFF(source == null) null; else Any(body);
                any = ToNullable(any);
                return(Expression.Condition(
                           test: Expression.Equal(source, NullConstant),
                           ifTrue: Expression.Constant(null, any.Type),
                           ifFalse: any));
            }
            else
            {
                return(any);
            }
        }
        public void RangeVariableShouldBeSetCorrectly()
        {
            ResourceRangeVariable rangeVariable =
                (ResourceRangeVariable)
                NodeFactory.CreateImplicitRangeVariable(HardCodedTestModel.GetDogTypeReference(), HardCodedTestModel.GetDogsSet());
            Collection <RangeVariable> rangeVariables = new Collection <RangeVariable>
            {
                rangeVariable
            };
            AnyNode anyNode = new AnyNode(rangeVariables, rangeVariable);

            Assert.Equal(ExpressionConstants.It, anyNode.CurrentRangeVariable.Name);
            Assert.Equal(RangeVariableKind.Resource, anyNode.CurrentRangeVariable.Kind);
            Assert.Equal(HardCodedTestModel.GetDogTypeReference().FullName(), anyNode.CurrentRangeVariable.TypeReference.FullName());
        }
Exemple #28
0
        public void TranslatorShouldRequireProtocolAndRequestVersionThreeForAnyAndAll()
        {
            ODataProtocolVersion validatedProtocolVersion = ODataProtocolVersion.V4;
            ODataProtocolVersion validatedRequestVersion  = ODataProtocolVersion.V4;
            var withVersionCallbacks = this.CreateTestSubject(verifyProtocolVersion: v => { validatedProtocolVersion = v; }, verifyRequestVersion: v => { validatedRequestVersion = v; });

            LambdaNode node = new AnyNode(new Collection <RangeVariable>(), null);

            node.Body   = Constant(true);
            node.Source = this.CollectionNavigationFromParameter("o");

            withVersionCallbacks.TranslateNode(node);
            validatedProtocolVersion.Should().Be(ODataProtocolVersion.V4);
            validatedRequestVersion.Should().Be(ODataProtocolVersion.V4);
        }
Exemple #29
0
        public void RangeVariableShouldBeSetCorrectly()
        {
            EntityRangeVariable rangeVariable =
                (EntityRangeVariable)
                NodeFactory.CreateImplicitRangeVariable(HardCodedTestModel.GetDogTypeReference(), HardCodedTestModel.GetDogsSet());
            Collection <RangeVariable> rangeVariables = new Collection <RangeVariable>
            {
                rangeVariable
            };
            AnyNode anyNode = new AnyNode(rangeVariables, rangeVariable);

            anyNode.CurrentRangeVariable.Name.Should().Be(ExpressionConstants.It);
            anyNode.CurrentRangeVariable.Kind.Should().Be(RangeVariableKind.Entity);
            anyNode.CurrentRangeVariable.TypeReference.FullName().Should().Be(HardCodedTestModel.GetDogTypeReference().FullName());
        }
        /// <summary>
        /// Translate an AnyNode.
        /// </summary>
        /// <param name="nodeIn">The node to be translated.</param>
        /// <returns>The translated node.</returns>
        public override QueryNode Visit(AnyNode nodeIn)
        {
            AnyNode anyNode = new AnyNode(nodeIn.RangeVariables, nodeIn.CurrentRangeVariable);

            if (nodeIn.Source != null)
            {
                anyNode.Source = (CollectionNode)nodeIn.Source.Accept(this);
            }

            if (nodeIn.Body != null)
            {
                anyNode.Body = (SingleValueNode)nodeIn.Body.Accept(this);
            }

            return(anyNode);
        }
Exemple #31
0
        public override QueryNode Visit(AnyNode nodeIn)
        {
            var            body   = (SingleValueNode)Visit(nodeIn.Body);
            CollectionNode?source = nodeIn.Source == null ? null : (CollectionNode)Visit(nodeIn.Source);

            if (nodeIn.Body != body || nodeIn.Source != source)
            {
                nodeIn = new AnyNode(nodeIn.RangeVariables, nodeIn.CurrentRangeVariable)
                {
                    Body   = body,
                    Source = source
                }
            }
            ;
            return(nodeIn);
        }
Exemple #32
0
        public void RangeVariablesShouldBeSetCorrectly()
        {
            ResourceRangeVariable      rangeVariable  = (ResourceRangeVariable)NodeFactory.CreateImplicitRangeVariable(HardCodedTestModel.GetDogTypeReference(), HardCodedTestModel.GetDogsSet());
            Collection <RangeVariable> rangeVariables = new Collection <RangeVariable>
            {
                rangeVariable
            };
            AnyNode anyNode = new AnyNode(rangeVariables, rangeVariable);

            anyNode.RangeVariables.Count.Should().Be(1);
            anyNode.RangeVariables[0].Name.Should().Be(ExpressionConstants.It);
            anyNode.RangeVariables[0].Kind.Should().Be(RangeVariableKind.Resource);
            anyNode.RangeVariables[0].TypeReference.FullName().Should().Be(HardCodedTestModel.GetDogTypeReference().FullName());
            ResourceRangeVariable returnedRangeVariable = (ResourceRangeVariable)anyNode.RangeVariables[0];

            returnedRangeVariable.NavigationSource.Should().Be(HardCodedTestModel.GetDogsSet());
        }
        /// <summary>
        /// Override this method to restrict the 'any' query inside the filter query
        /// </summary>
        /// <param name="anyNode"></param>
        /// <param name="settings"></param>
        public virtual void ValidateAnyNode(AnyNode anyNode, ODataValidationSettings settings)
        {
            if (anyNode == null)
            {
                throw Error.ArgumentNull("anyNode");
            }

            if (settings == null)
            {
                throw Error.ArgumentNull("settings");
            }

            ValidateQueryNode(anyNode.Source, settings);

            if (anyNode.Body != null && anyNode.Body.Kind != QueryNodeKind.Constant)
            {
                ValidateQueryNode(anyNode.Body, settings);
            }
        }
Exemple #34
0
        /// <inheritdoc />
        public override string Visit(AnyNode node)
        {
            if (node.CurrentRangeVariable == null && node.Body.Kind == QueryNodeKind.Constant)
            {
                return(string.Concat(TranslateNode(node.Source), Constants.SymbolForwardSlash, Constants.KeywordAny, Constants.SymbolOpenParen, Constants.SymbolClosedParen));
            }
            else
            {
                var source       = TranslateNode(node.Source);
                var body         = TranslateNode(node.Body);
                var variableName = node.CurrentRangeVariable?.Name;

                var result = string.Concat(source, Constants.SymbolForwardSlash, Constants.KeywordAny,
                                           Constants.SymbolOpenParen, variableName, ":", body,
                                           Constants.SymbolClosedParen);

                return(result);
            }
        }
        /// <summary>
        /// Writes any node to string.
        /// </summary>
        /// <param name="node">Node to write to string</param>
        /// <returns>String representation of node.</returns>
        private static string ToString(AnyNode node)
        {
            if (node != null)
            {
                return tabHelper.Prefix + "AnyNode" +
                    tabHelper.Indent(() =>
                    {
                        string text = tabHelper.Prefix + "TypeReference = " + node.TypeReference +
                                tabHelper.Prefix + "Body = " + ToString(node.Body) +
                                tabHelper.Prefix + "Source = " + ToString(node.Source) +
                                tabHelper.Prefix + "Parameters = ";

                        for (int i = 0; i < node.RangeVariables.Count(); ++i)
                        {
                            text += ToStringParameter(node.RangeVariables.ElementAt(i));
                        }

                        return text;
                    });
            }

            return String.Empty;
        }
Exemple #36
0
        private static void BuildFilterWithNestedAny()
        {
            var personTypeRef = new EdmEntityTypeReference(TripPinModel.Person, false);
            var tripTypeRef = new EdmEntityTypeReference(TripPinModel.Trip, false);

            var friendsProp = (IEdmNavigationProperty)TripPinModel.Person.FindProperty("Friends");
            var tripsProp = (IEdmNavigationProperty)TripPinModel.Person.FindProperty("Trips");
            var budgetProp = TripPinModel.Trip.FindProperty("Budget");

            var topIt = new EntityRangeVariable("$it", personTypeRef, TripPinModel.PeopleSet);
            var topItRef = new EntityRangeVariableReferenceNode("$it", topIt);

            var friendsNavNode0 = new CollectionNavigationNode(friendsProp, topItRef);
            var e0 = new EntityRangeVariable("e0", personTypeRef, friendsNavNode0);
            var e0Ref = new EntityRangeVariableReferenceNode("e0", e0);

            var friendsNavNode1 = new CollectionNavigationNode(friendsProp, e0Ref);
            var e1 = new EntityRangeVariable("e1", personTypeRef, friendsNavNode1);
            var e1Ref = new EntityRangeVariableReferenceNode("e1", e1);

            var tripNavNode = new CollectionNavigationNode(tripsProp, e1Ref);
            var e2 = new EntityRangeVariable("e2", tripTypeRef, friendsNavNode1);
            var e2Ref = new EntityRangeVariableReferenceNode("e2", e2);

            var bugetNode = new SingleValuePropertyAccessNode(e2Ref, budgetProp);

            var gt = new BinaryOperatorNode(
                BinaryOperatorKind.GreaterThan,
                bugetNode,
                new ConstantNode(1200, "1200"));

            var any2 = new AnyNode(new Collection<RangeVariable> { e2 }, e2) { Body = gt, Source = tripNavNode };
            var any1 = new AnyNode(new Collection<RangeVariable> { e1 }, e1) { Body = any2, Source = friendsNavNode1 };
            var any0 = new AnyNode(new Collection<RangeVariable> { e0 }, e0) { Body = any1, Source = friendsNavNode0 };


            var odataUri = new ODataUri
            {
                Path = new ODataPath(new EntitySetSegment(TripPinModel.PeopleSet)),
                ServiceRoot = TripPinRoot,
                Filter = new FilterClause(any0, topIt)
            };
            var builder = new ODataUriBuilder(ODataUrlConventions.Default, odataUri);
            Console.WriteLine(builder.BuildUri());
            // http://services.odata.org/V4/TripPinService/People?$filter=Friends%2Fany(e0:e0%2FFriends%2Fany(e1:e1%2FTrips%2Fany(e2:e2%2FBudget gt 1200)))
        }
 private string BindAnyNode(AnyNode anyNode)
 {
     string innerQuery = "exists ( from " + Bind(anyNode.Source) + " " + anyNode.RangeVariables.First().Name;
     if (anyNode.Body != null)
     {
         innerQuery += " where " + Bind(anyNode.Body);
     }
     return innerQuery + ")";
 }
Exemple #38
0
        private static void BuildFilterWithBinaryOperator()
        {
            var personTypeRef = new EdmEntityTypeReference(TripPinModel.Person, false);
            var friendsProp = (IEdmNavigationProperty)TripPinModel.Person.FindProperty("Friends");
            var firstNameProp = TripPinModel.Person.FindProperty("FirstName");
            var lastNameProp = TripPinModel.Person.FindProperty("LastName");

            var topIt = new EntityRangeVariable("$it", personTypeRef, TripPinModel.PeopleSet);
            var topItRef = new EntityRangeVariableReferenceNode("$it", topIt);
            var friendsNavNode = new CollectionNavigationNode(friendsProp, topItRef);
            var e0 = new EntityRangeVariable("e0", personTypeRef, friendsNavNode);
            var e0Ref = new EntityRangeVariableReferenceNode("e0", e0);
            var fun1 = new SingleValueFunctionCallNode(
                "startswith",
                new QueryNode[]
                {
                    new SingleValuePropertyAccessNode(e0Ref, firstNameProp),
                    new ConstantNode("var1", "'var1'")
                },
                EdmCoreModel.Instance.GetBoolean(false));

            var friendsNavNode2 = new CollectionNavigationNode(friendsProp, e0Ref);
            var e1 = new EntityRangeVariable("e1", personTypeRef, friendsNavNode2);
            var e1Ref = new EntityRangeVariableReferenceNode("e1", e1);
            var fun2 = new SingleValueFunctionCallNode(
                "contains",
                new QueryNode[]
                {
                    new SingleValuePropertyAccessNode(e1Ref, lastNameProp),
                    new ConstantNode("var2", "'var2'")
                },
                EdmCoreModel.Instance.GetBoolean(false));

            // Actually $it also needed, but would not be used in UriBuilder, so omit it here.
            var any2 = new AnyNode(new Collection<RangeVariable> { e1 }, e1)
            {
                Body = fun2,
                Source = friendsNavNode2
            };

            var any1 = new AnyNode(new Collection<RangeVariable> { e0 }, e0)
            {
                Body = new BinaryOperatorNode(BinaryOperatorKind.And, fun1, any2),
                Source = friendsNavNode
            };

            var odataUri = new ODataUri
            {
                Path = new ODataPath(new EntitySetSegment(TripPinModel.PeopleSet)),
                ServiceRoot = TripPinRoot,
                Filter = new FilterClause(any1, topIt)
            };
            var builder = new ODataUriBuilder(ODataUrlConventions.Default, odataUri);
            Console.WriteLine(builder.BuildUri());

            // http://services.odata.org/V4/TripPinService/People?$filter=Friends%2Fany(
            // e0:startswith(e0%2FFirstName%2C'var1') and e0%2FFriends%2Fany(e1:contains(e1%2FLastName%2C'var2')))
        }
        /// <summary>
        /// Compares any query nodes.
        /// </summary>
        /// <param name="left">Left side of comparison</param>
        /// <param name="right">Right side of comparison</param>
        /// <returns>True if equal, otherwise false</returns>
        private bool Compare(AnyNode left, AnyNode right)
        {
            if (left.TypeReference != right.TypeReference) return false;
            if (!this.Compare(left.Body, right.Body)) return false;
            if (left.RangeVariables.Count() != right.RangeVariables.Count()) return false;
            for (int i = 0; i < left.RangeVariables.Count(); ++i)
            {
                if (!this.CompareParameters(left.RangeVariables.ElementAt(i), right.RangeVariables.ElementAt(i))) return false;
            }

            return this.Compare(left.Source, right.Source);
        }
 internal void    AddAny(XmlSchemaAny any) {
     ContentNode n = new AnyNode(any);
     if (stack.Count > 0) {
         InternalNode inNode = (InternalNode)stack.Pop();
         if (inNode != null) {
             inNode.RightNode = n;
             n.ParentNode = inNode;
             n = inNode;
         }
     }
     stack.Push( n );
     isPartial = true;
     abnormalContent = true;
 }
 public override void ValidateAnyNode(AnyNode anyQueryNode, ODataValidationSettings settings)
 {
     IncrementCount("ValidateAnyQueryNode");
     base.ValidateAnyNode(anyQueryNode, settings);
 }
Exemple #42
0
 /// <summary>
 /// Creates an AnyNode or an AllNode from the given 
 /// </summary>
 /// <param name="state">State of binding.</param>
 /// <param name="parent">Parent node to the lambda.</param>
 /// <param name="lambdaExpression">Bound Lambda expression.</param>
 /// <param name="newRangeVariable">The new range variable being added by this lambda node.</param>
 /// <param name="queryTokenKind">Token kind.</param>
 /// <returns>A new LambdaNode bound to metadata.</returns>
 internal static LambdaNode CreateLambdaNode(
     BindingState state,
     CollectionNode parent,                                           
     SingleValueNode lambdaExpression, 
     RangeVariable newRangeVariable,
     QueryTokenKind queryTokenKind)
 {
     LambdaNode lambdaNode;
     if (queryTokenKind == QueryTokenKind.Any)
     {
         lambdaNode = new AnyNode(new Collection<RangeVariable>(state.RangeVariables.ToList()), newRangeVariable)
             {
                 Body = lambdaExpression,
                 Source = parent,
             };
     }
     else
     {
         Debug.Assert(queryTokenKind == QueryTokenKind.All, "LambdaQueryNodes must be Any or All only.");
         lambdaNode = new AllNode(new Collection<RangeVariable>(state.RangeVariables.ToList()), newRangeVariable)
             {
                 Body = lambdaExpression,
                 Source = parent,
             };
     }
     
     return lambdaNode;
 }
            void ParseInternal()
            {
                this.mainBlock = new BlockNode(null);
                this.stack = new Stack<BlockNode>();
                this.errors = new List<TemplateError>(); 
                PushBlock(mainBlock);

                var matches = TemplateUtils.KeywordsRegex.Matches(text);

                if (matches.Count == 0)
                {
                    stack.Peek().Nodes.Add(new LiteralNode { Text = text });
                    stack.Pop();
                    return;
                }

                int index = 0;
                foreach (Match match in matches)
                {
                    if (index < match.Index)
                    {
                        stack.Peek().Nodes.Add(new LiteralNode { Text = text.Substring(index, match.Index - index) });
                    }
                    var type = match.Groups["type"].Value;
                    var token = match.Groups["token"].Value;
                    var keyword = match.Groups["keyword"].Value;
                    var dec = match.Groups["dec"].Value;
                    switch (keyword)
                    {
                        case "":
                        case "raw":
                            var tok = TemplateUtils.TokenFormatRegex.Match(token);
                            if (!tok.Success)
                                AddError(true, "{0} has invalid format".FormatWith(token));
                            else
                            {
                                var t = TryParseValueProvider(type, tok.Groups["token"].Value, dec);

                                stack.Peek().Nodes.Add(new ValueNode(t, tok.Groups["format"].Value.DefaultText(null), isRaw: keyword.Contains("raw")));

                                DeclareVariable(t);
                            }
                            break;
                        case "declare":
                            {
                                var t = TryParseValueProvider(type, token, dec);

                                stack.Peek().Nodes.Add(new DeclareNode(t, this.AddError));

                                DeclareVariable(t);
                            }
                            break;
                        case "any":
                            {
                                AnyNode any;
                                ValueProviderBase vp;
                                var filter = TemplateUtils.TokenOperationValueRegex.Match(token);
                                if (!filter.Success)
                                {
                                    vp = TryParseValueProvider(type, token, dec);

                                    any = new AnyNode(vp);
                                }
                                else
                                {
                                    vp = TryParseValueProvider(type, filter.Groups["token"].Value, dec);
                                    var comparer = filter.Groups["comparer"].Value;
                                    var value = filter.Groups["value"].Value;
                                    any = new AnyNode(vp, comparer, value, this.AddError);

                                }
                                stack.Peek().Nodes.Add(any);
                                PushBlock(any.AnyBlock);

                                DeclareVariable(vp);
                                break;
                            }
                        case "notany":
                            {
                                var an = (AnyNode)PopBlock(typeof(AnyNode)).owner;
                                if (an != null)
                                    PushBlock(an.CreateNotAny());
                                break;
                            }
                        case "endany":
                            {
                                PopBlock(typeof(AnyNode));
                                break;
                            }
                        case "foreach":
                            {
                                ValueProviderBase vp = TryParseValueProvider(type, token, dec);
                                var fn = new ForeachNode(vp);
                                stack.Peek().Nodes.Add(fn);
                                PushBlock(fn.Block);
                                vp.IsForeach = true;
                                DeclareVariable(vp);
                                break;
                            }
                        case "endforeach":
                            {
                                PopBlock(typeof(ForeachNode));
                            }
                            break;
                        case "if":
                            {
                                IfNode ifn;
                                ValueProviderBase vp;
                                var filter = TemplateUtils.TokenOperationValueRegex.Match(token);
                                if (!filter.Success)
                                {
                                    vp = TryParseValueProvider(type, token, dec);
                                    ifn = new IfNode(vp, this);
                                }
                                else
                                {
                                    vp = TryParseValueProvider(type, filter.Groups["token"].Value, dec);
                                    var comparer = filter.Groups["comparer"].Value;
                                    var value = filter.Groups["value"].Value;
                                    ifn = new IfNode(vp, comparer, value, this.AddError);
                                }
                                stack.Peek().Nodes.Add(ifn);
                                PushBlock(ifn.IfBlock);
                                DeclareVariable(vp);
                                break;
                            }
                        case "else":
                            {
                                var ifn = (IfNode)PopBlock(typeof(IfNode)).owner;
                                if (ifn != null)
                                    PushBlock(ifn.CreateElse());
                                break;
                            }
                        case "endif":
                            {
                                PopBlock(typeof(IfNode));
                                break;
                            }
                        default :
                            AddError(true, "'{0}' is deprecated".FormatWith(keyword));
                            break;
                    }
                    index = match.Index + match.Length;
                }

                if (stack.Count != 1)
                    AddError(true, "Last block is not closed: {0}".FormatWith(stack.Peek()));

                var lastM = matches.Cast<Match>().LastOrDefault();
                if (lastM != null && lastM.Index + lastM.Length < text.Length)
                    stack.Peek().Nodes.Add(new LiteralNode { Text = text.Substring(lastM.Index + lastM.Length) });

                stack.Pop();
            }
        /// <summary>
        /// Override this method to restrict the 'any' query inside the filter query.
        /// </summary>
        /// <remarks>
        /// This method is intended to be called from method overrides in subclasses. This method also supports unit-testing scenarios and is not intended to be called from user code.
        /// Call the Validate method to validate a <see cref="FilterQueryOption"/> instance.
        /// </remarks>
        /// <param name="anyNode"></param>
        /// <param name="settings"></param>
        public virtual void ValidateAnyNode(AnyNode anyNode, ODataValidationSettings settings)
        {
            if (anyNode == null)
            {
                throw Error.ArgumentNull("anyNode");
            }

            if (settings == null)
            {
                throw Error.ArgumentNull("settings");
            }

            ValidateFunction("any", settings);
            EnterLambda(settings);

            try
            {
                ValidateQueryNode(anyNode.Source, settings);

                if (anyNode.Body != null && anyNode.Body.Kind != QueryNodeKind.Constant)
                {
                    ValidateQueryNode(anyNode.Body, settings);
                }
            }
            finally
            {
                ExitLambda();
            }
        }
Exemple #45
0
		private Node ParseFactor()
		{
			Node n;
			Token t = GetToken();
			switch (t)
			{
			case Token.Byte: 
				n = new ByteNode(this.b, positions.Count);
				positions.Add(n);
				AddCharacterClass(b);
				break;
			case Token.Dot:
				n = new AnyNode(positions.Count);
				positions.Add(n);
				break;
			case Token.LParen: 
				n = Parse();
				Expect(Token.RParen);
				break;
			default:
				return SyntaxError();
			}
			return n;
		}