示例#1
0
 public QueryStringParameterScopeParser(IResourceContextProvider resourceContextProvider, FieldChainRequirements chainRequirements,
                                        Action <ResourceFieldAttribute, ResourceContext, string> validateSingleFieldCallback = null)
     : base(resourceContextProvider)
 {
     _chainRequirements           = chainRequirements;
     _validateSingleFieldCallback = validateSingleFieldCallback;
 }
        protected QueryExpression ParseCountOrField(FieldChainRequirements chainRequirements)
        {
            CountExpression count = TryParseCount();

            if (count != null)
            {
                return(count);
            }

            return(ParseFieldChain(chainRequirements, "Count function or field name expected."));
        }
示例#3
0
        protected ResourceFieldChainExpression ParseFieldChain(FieldChainRequirements chainRequirements, string alternativeErrorMessage)
        {
            if (TokenStack.TryPop(out Token token) && token.Kind == TokenKind.Text)
            {
                var chain = OnResolveFieldChain(token.Value, chainRequirements);
                if (chain.Any())
                {
                    return(new ResourceFieldChainExpression(chain));
                }
            }

            throw new QueryParseException(alternativeErrorMessage ?? "Field name expected.");
        }
        protected QueryExpression ParseCountOrConstantOrNullOrField(FieldChainRequirements chainRequirements)
        {
            CountExpression count = TryParseCount();

            if (count != null)
            {
                return(count);
            }

            IdentifierExpression constantOrNull = TryParseConstantOrNull();

            if (constantOrNull != null)
            {
                return(constantOrNull);
            }

            return(ParseFieldChain(chainRequirements, "Count function, value between quotes, null or field name expected."));
        }
示例#5
0
        protected ComparisonExpression ParseComparison(string operatorName)
        {
            var comparisonOperator = Enum.Parse <ComparisonOperator>(operatorName.Pascalize());

            EatText(operatorName);
            EatSingleCharacterToken(TokenKind.OpenParen);

            // Allow equality comparison of a HasOne relationship with null.
            FieldChainRequirements leftChainRequirements = comparisonOperator == ComparisonOperator.Equals
                ? FieldChainRequirements.EndsInAttribute | FieldChainRequirements.EndsInToOne
                : FieldChainRequirements.EndsInAttribute;

            QueryExpression leftTerm = ParseCountOrField(leftChainRequirements);

            EatSingleCharacterToken(TokenKind.Comma);

            QueryExpression rightTerm = ParseCountOrConstantOrNullOrField(FieldChainRequirements.EndsInAttribute);

            EatSingleCharacterToken(TokenKind.CloseParen);

            if (leftTerm is ResourceFieldChainExpression leftChain)
            {
                if (leftChainRequirements.HasFlag(FieldChainRequirements.EndsInToOne) && !(rightTerm is NullConstantExpression))
                {
                    // Run another pass over left chain to have it fail when chain ends in relationship.
                    OnResolveFieldChain(leftChain.ToString(), FieldChainRequirements.EndsInAttribute);
                }

                PropertyInfo leftProperty = leftChain.Fields.Last().Property;

                if (leftProperty.Name == nameof(Identifiable.Id) && rightTerm is LiteralConstantExpression rightConstant)
                {
                    string id = DeObfuscateStringId(leftProperty.ReflectedType, rightConstant.Value);
                    rightTerm = new LiteralConstantExpression(id);
                }
            }

            return(new ComparisonExpression(comparisonOperator, leftTerm, rightTerm));
        }
示例#6
0
 /// <summary>
 /// Takes a dotted path and walks the resource graph to produce a chain of fields.
 /// </summary>
 protected abstract IReadOnlyCollection <ResourceFieldAttribute> OnResolveFieldChain(string path, FieldChainRequirements chainRequirements);
        protected override IReadOnlyCollection <ResourceFieldAttribute> OnResolveFieldChain(string path, FieldChainRequirements chainRequirements)
        {
            var field = ChainResolver.GetField(path, _resourceContext, path);

            _validateSingleFieldCallback?.Invoke(field, _resourceContext, path);

            return(new[] { field });
        }
        protected override IReadOnlyCollection <ResourceFieldAttribute> OnResolveFieldChain(string path, FieldChainRequirements chainRequirements)
        {
            if (chainRequirements == FieldChainRequirements.EndsInToMany)
            {
                return(ChainResolver.ResolveToOneChainEndingInToMany(_resourceContextInScope, path, _validateSingleFieldCallback));
            }

            if (chainRequirements == FieldChainRequirements.EndsInAttribute)
            {
                return(ChainResolver.ResolveToOneChainEndingInAttribute(_resourceContextInScope, path, _validateSingleFieldCallback));
            }

            if (chainRequirements.HasFlag(FieldChainRequirements.EndsInAttribute) &&
                chainRequirements.HasFlag(FieldChainRequirements.EndsInToOne))
            {
                return(ChainResolver.ResolveToOneChainEndingInAttributeOrToOne(_resourceContextInScope, path, _validateSingleFieldCallback));
            }

            throw new InvalidOperationException($"Unexpected combination of chain requirement flags '{chainRequirements}'.");
        }
 protected override IReadOnlyCollection <ResourceFieldAttribute> OnResolveFieldChain(string path, FieldChainRequirements chainRequirements)
 {
     return(ChainResolver.ResolveToManyChain(_resourceContextInScope, path, _validateSingleFieldCallback));
 }
        protected override IReadOnlyCollection <ResourceFieldAttribute> OnResolveFieldChain(string path, FieldChainRequirements chainRequirements)
        {
            var attribute = ChainResolver.GetAttribute(path, _resourceContextInScope, path);

            _validateSingleAttributeCallback?.Invoke(attribute, _resourceContextInScope, path);

            return(new[] { attribute });
        }
示例#11
0
        protected override IReadOnlyCollection <ResourceFieldAttribute> OnResolveFieldChain(string path, FieldChainRequirements chainRequirements)
        {
            if (chainRequirements == FieldChainRequirements.EndsInToMany)
            {
                // The mismatch here (ends-in-to-many being interpreted as entire-chain-must-be-to-many) is intentional.
                return(ChainResolver.ResolveToManyChain(_resourceContextInScope, path, _validateSingleFieldCallback));
            }

            if (chainRequirements == FieldChainRequirements.IsRelationship)
            {
                return(ChainResolver.ResolveRelationshipChain(_resourceContextInScope, path, _validateSingleFieldCallback));
            }

            throw new InvalidOperationException($"Unexpected combination of chain requirement flags '{chainRequirements}'.");
        }
 protected override IReadOnlyCollection <ResourceFieldAttribute> OnResolveFieldChain(string path, FieldChainRequirements chainRequirements)
 {
     throw new NotSupportedException();
 }