/// <summary> /// Create a new RangeVariableToken /// </summary> /// <param name="name">The name of the visitor for the Any/All query.</param> public RangeVariableToken(string name) { ExceptionUtils.CheckArgumentNotNull(name, "visitor"); this.name = name; }
/// <summary> /// Accept a <see cref="IPathSegmentTokenVisitor{T}"/> to walk a tree of <see cref="PathSegmentToken"/>s. /// </summary> /// <typeparam name="T">Type that the visitor will return after visiting this token.</typeparam> /// <param name="visitor">An implementation of the visitor interface.</param> /// <returns>An object whose type is determined by the type parameter of the visitor.</returns> public override T Accept <T>(IPathSegmentTokenVisitor <T> visitor) { ExceptionUtils.CheckArgumentNotNull(visitor, "visitor"); return(visitor.Visit(this)); }
/// <summary> /// Translate a <see cref="PropertySegment"/> using an instance of <see cref="PathSegmentTranslator{T}"/>/>. /// </summary> /// <typeparam name="T">Type that the translator will return after visiting this token.</typeparam> /// <param name="translator">An implementation of the translator interface.</param> /// <returns>An object whose type is determined by the type parameter of the translator.</returns> /// <exception cref="System.ArgumentNullException">Throws if the input translator is null.</exception> public override T TranslateWith <T>(PathSegmentTranslator <T> translator) { ExceptionUtils.CheckArgumentNotNull(translator, "translator"); return(translator.Translate(this)); }
/// <summary> /// Accept a <see cref="QueryNodeVisitor{T}"/> to walk a tree of <see cref="QueryNode"/>s. /// </summary> /// <typeparam name="T">Type that the visitor will return after visiting this token.</typeparam> /// <param name="visitor">An implementation of the visitor interface.</param> /// <returns>An object whose type is determined by the type parameter of the visitor.</returns> /// <exception cref="System.ArgumentNullException">Throws if the input visitor is null.</exception> public override T Accept <T>(QueryNodeVisitor <T> visitor) { ExceptionUtils.CheckArgumentNotNull(visitor, "visitor"); return(visitor.Visit(this)); }
/// <summary> /// Accept a <see cref="QueryNodeVisitor{T}"/> that walks a tree of <see cref="QueryNode"/>s. /// </summary> /// <typeparam name="T">Type that the visitor will return after visiting this token.</typeparam> /// <param name="visitor">An implementation of the visitor interface.</param> /// <returns>An object whose type is determined by the type parameter of the visitor.</returns> /// <exception cref="System.ArgumentNullException">Throws if the input visitor is null.</exception> public override T Accept<T>(QueryNodeVisitor<T> visitor) { DebugUtils.CheckNoExternalCallers(); ExceptionUtils.CheckArgumentNotNull(visitor, "visitor"); return visitor.Visit(this); }
internal static object CoerceNumericType(object primitiveValue, IEdmPrimitiveType targetEdmType) { // This is implemented to match TypePromotionUtils and MetadataUtilsCommon.CanConvertPrimitiveTypeTo() ExceptionUtils.CheckArgumentNotNull(primitiveValue, "primitiveValue"); ExceptionUtils.CheckArgumentNotNull(targetEdmType, "targetEdmType"); Type fromType = primitiveValue.GetType(); TypeCode fromTypeCode = ODataPlatformHelper.GetTypeCode(fromType); EdmPrimitiveTypeKind targetPrimitiveKind = targetEdmType.PrimitiveKind; switch (fromTypeCode) { case TypeCode.SByte: switch (targetPrimitiveKind) { case EdmPrimitiveTypeKind.SByte: return(primitiveValue); case EdmPrimitiveTypeKind.Int16: return(Convert.ToInt16((SByte)primitiveValue)); case EdmPrimitiveTypeKind.Int32: return(Convert.ToInt32((SByte)primitiveValue)); case EdmPrimitiveTypeKind.Int64: return(Convert.ToInt64((SByte)primitiveValue)); case EdmPrimitiveTypeKind.Single: return(Convert.ToSingle((SByte)primitiveValue)); case EdmPrimitiveTypeKind.Double: return(Convert.ToDouble((SByte)primitiveValue)); case EdmPrimitiveTypeKind.Decimal: return(Convert.ToDecimal((SByte)primitiveValue)); } break; case TypeCode.Byte: switch (targetPrimitiveKind) { case EdmPrimitiveTypeKind.Byte: return(primitiveValue); case EdmPrimitiveTypeKind.Int16: return(Convert.ToInt16((Byte)primitiveValue)); case EdmPrimitiveTypeKind.Int32: return(Convert.ToInt32((Byte)primitiveValue)); case EdmPrimitiveTypeKind.Int64: return(Convert.ToInt64((Byte)primitiveValue)); case EdmPrimitiveTypeKind.Single: return(Convert.ToSingle((Byte)primitiveValue)); case EdmPrimitiveTypeKind.Double: return(Convert.ToDouble((Byte)primitiveValue)); case EdmPrimitiveTypeKind.Decimal: return(Convert.ToDecimal((Byte)primitiveValue)); } break; case TypeCode.Int16: switch (targetPrimitiveKind) { case EdmPrimitiveTypeKind.Int16: return(primitiveValue); case EdmPrimitiveTypeKind.Int32: return(Convert.ToInt32((Int16)primitiveValue)); case EdmPrimitiveTypeKind.Int64: return(Convert.ToInt64((Int16)primitiveValue)); case EdmPrimitiveTypeKind.Single: return(Convert.ToSingle((Int16)primitiveValue)); case EdmPrimitiveTypeKind.Double: return(Convert.ToDouble((Int16)primitiveValue)); case EdmPrimitiveTypeKind.Decimal: return(Convert.ToDecimal((Int16)primitiveValue)); } break; case TypeCode.Int32: switch (targetPrimitiveKind) { case EdmPrimitiveTypeKind.Int32: return(primitiveValue); case EdmPrimitiveTypeKind.Int64: return(Convert.ToInt64((Int32)primitiveValue)); case EdmPrimitiveTypeKind.Single: return(Convert.ToSingle((Int32)primitiveValue)); case EdmPrimitiveTypeKind.Double: return(Convert.ToDouble((Int32)primitiveValue)); case EdmPrimitiveTypeKind.Decimal: return(Convert.ToDecimal((Int32)primitiveValue)); } break; case TypeCode.Int64: switch (targetPrimitiveKind) { case EdmPrimitiveTypeKind.Int64: return(primitiveValue); case EdmPrimitiveTypeKind.Single: return(Convert.ToSingle((Int64)primitiveValue)); case EdmPrimitiveTypeKind.Double: return(Convert.ToDouble((Int64)primitiveValue)); case EdmPrimitiveTypeKind.Decimal: return(Convert.ToDecimal((Int64)primitiveValue)); } break; case TypeCode.Single: switch (targetPrimitiveKind) { case EdmPrimitiveTypeKind.Single: return(primitiveValue); case EdmPrimitiveTypeKind.Double: /*to string then to double, avoid losing precision like "(double)123.001f" which is 123.00099945068359, instead of 123.001d.*/ return(double.Parse(((Single)primitiveValue).ToString("R", CultureInfo.InvariantCulture), CultureInfo.InvariantCulture)); case EdmPrimitiveTypeKind.Decimal: return(Convert.ToDecimal((Single)primitiveValue)); } break; case TypeCode.Double: switch (targetPrimitiveKind) { case EdmPrimitiveTypeKind.Double: return(primitiveValue); case EdmPrimitiveTypeKind.Decimal: // TODO: extract these convertion steps to an individual function decimal doubleToDecimalR; // To keep the full presion of the current value, which if necessary is all 17 digits of precision supported by the Double type. if (decimal.TryParse(((Double)primitiveValue).ToString("R", CultureInfo.InvariantCulture), out doubleToDecimalR)) { return(doubleToDecimalR); } return(Convert.ToDecimal((Double)primitiveValue)); } break; case TypeCode.Decimal: switch (targetPrimitiveKind) { case EdmPrimitiveTypeKind.Decimal: return(primitiveValue); } break; default: break; } return(null); }
/// <summary> /// Creates a <see cref="SearchClause"/>. /// </summary> /// <param name="expression">The filter expression - this should evaluate to a single boolean value. Cannot be null.</param> /// <exception cref="System.ArgumentNullException">Throws if the input expression or rangeVariable is null.</exception> public SearchClause(SingleValueNode expression) { ExceptionUtils.CheckArgumentNotNull(expression, "expression"); this.expression = expression; }
/// <summary> /// Provide additional serialization information to the <see cref="ODataWriter"/> for <paramref name="entry"/>. /// </summary> /// <param name="entry">The instance to set the serialization info.</param> /// <param name="serializationInfo">The serialization info to set.</param> public static void SetSerializationInfo(this ODataEntry entry, ODataFeedAndEntrySerializationInfo serializationInfo) { ExceptionUtils.CheckArgumentNotNull(entry, "entry"); entry.SerializationInfo = serializationInfo; }
/// <summary> /// Provide additional serialization information to the <see cref="ODataWriter"/> for <paramref name="property"/>. /// </summary> /// <param name="property">The instance to set the serialization info.</param> /// <param name="serializationInfo">The serialization info to set.</param> public static void SetSerializationInfo(this ODataProperty property, ODataPropertySerializationInfo serializationInfo) { ExceptionUtils.CheckArgumentNotNull(property, "property"); property.SerializationInfo = serializationInfo; }
/// <summary> /// Check if this segment is equal to another segment. /// </summary> /// <param name="other">the other segment to check.</param> /// <returns>true if the other segment is equal.</returns> /// <exception cref="System.ArgumentNullException">throws if the input other is null.</exception> internal override bool Equals(ODataPathSegment other) { ExceptionUtils.CheckArgumentNotNull(other, "other"); return(other is CountSegment); }
/// <summary> /// Provide additional serialization information to the <see cref="ODataWriter"/> for <paramref name="feed"/>. /// </summary> /// <param name="feed">The instance to set the serialization info.</param> /// <param name="serializationInfo">The serialization info to set.</param> public static void SetSerializationInfo(this ODataFeed feed, ODataFeedAndEntrySerializationInfo serializationInfo) { ExceptionUtils.CheckArgumentNotNull(feed, "feed"); feed.SerializationInfo = serializationInfo; }
/// <summary> /// Write the literal token as URI part to this builder. /// </summary> /// <param name="literal">To write as URI part.</param> protected virtual void WriteLiteral(LiteralQueryToken literal) { ExceptionUtils.CheckArgumentNotNull(literal, "literal"); WriteClrLiteral(this.builder, literal.Value); }
/// <summary> /// Write the descriptor token as URI part to this builder. /// </summary> /// <param name="queryDescriptor">To write as URI part.</param> public virtual void WriteQueryDescriptor(QueryDescriptorQueryToken queryDescriptor) { ExceptionUtils.CheckArgumentNotNull(queryDescriptor, "queryDescriptor"); this.WriteQuery(queryDescriptor.Path); bool writeQueryPrefix = true; if (queryDescriptor.Filter != null) { this.WriteQueryPrefixOrSeparator(writeQueryPrefix); writeQueryPrefix = false; this.builder.Append(UriQueryConstants.FilterQueryOption); this.builder.Append(ExpressionConstants.SymbolEqual); this.WriteQuery(queryDescriptor.Filter); } if (queryDescriptor.Select != null && queryDescriptor.Select.Properties.Count() > 0) { this.WriteQueryPrefixOrSeparator(writeQueryPrefix); writeQueryPrefix = false; this.WriteSelect(queryDescriptor.Select); } if (queryDescriptor.Expand != null && queryDescriptor.Expand.Properties.Count() > 0) { this.WriteQueryPrefixOrSeparator(writeQueryPrefix); writeQueryPrefix = false; this.WriteExpand(queryDescriptor.Expand); } if (queryDescriptor.OrderByTokens.Count() > 0) { this.WriteQueryPrefixOrSeparator(writeQueryPrefix); writeQueryPrefix = false; this.builder.Append(UriQueryConstants.OrderByQueryOption); this.builder.Append(ExpressionConstants.SymbolEqual); this.WriteOrderBys(queryDescriptor.OrderByTokens); } foreach (QueryOptionQueryToken queryOption in queryDescriptor.QueryOptions) { this.WriteQueryPrefixOrSeparator(writeQueryPrefix); writeQueryPrefix = false; this.WriteQueryOption(queryOption); } if (queryDescriptor.Top != null) { this.WriteQueryPrefixOrSeparator(writeQueryPrefix); writeQueryPrefix = false; this.builder.Append(UriQueryConstants.TopQueryOption); this.builder.Append(ExpressionConstants.SymbolEqual); this.builder.Append(queryDescriptor.Top); } if (queryDescriptor.Skip != null) { this.WriteQueryPrefixOrSeparator(writeQueryPrefix); writeQueryPrefix = false; this.builder.Append(UriQueryConstants.SkipQueryOption); this.builder.Append(ExpressionConstants.SymbolEqual); this.builder.Append(queryDescriptor.Skip); } if (queryDescriptor.Format != null) { this.WriteQueryPrefixOrSeparator(writeQueryPrefix); writeQueryPrefix = false; this.builder.Append(UriQueryConstants.FormatQueryOption); this.builder.Append(ExpressionConstants.SymbolEqual); this.builder.Append(queryDescriptor.Format); } if (queryDescriptor.InlineCount.HasValue) { this.WriteQueryPrefixOrSeparator(writeQueryPrefix); writeQueryPrefix = false; this.builder.Append(UriQueryConstants.InlineCountQueryOption); this.builder.Append(ExpressionConstants.SymbolEqual); this.builder.Append(queryDescriptor.InlineCount.Value.ToText()); } }
/// <summary> /// Create a AggregateTransformationNode. /// </summary> /// <param name="expressions">A list of <see cref="AggregateExpression"/>.</param> public AggregateTransformationNode(IEnumerable <AggregateExpression> expressions) { ExceptionUtils.CheckArgumentNotNull(expressions, "expressions"); this.expressions = expressions; }
/// <summary> /// Build a new System Token /// </summary> /// <param name="identifier">the identifier for this token.</param> /// <param name="nextToken">the next token in the path</param> public SystemToken(string identifier, PathSegmentToken nextToken) : base(nextToken) { ExceptionUtils.CheckArgumentNotNull(identifier, "identifier"); this.identifier = identifier; }
/// <summary> /// Provide additional serialization information to the <see cref="ODataCollectionWriter"/> for <paramref name="collectionStart"/>. /// </summary> /// <param name="collectionStart">The instance to set the serialization info.</param> /// <param name="serializationInfo">The serialization info to set.</param> public static void SetSerializationInfo(this ODataCollectionStart collectionStart, ODataCollectionStartSerializationInfo serializationInfo) { ExceptionUtils.CheckArgumentNotNull(collectionStart, "collectionStart"); collectionStart.SerializationInfo = serializationInfo; }
/// <summary> /// Binds an end path token into a PropertyAccessToken, OpenPropertyToken, or FunctionCallToken. /// </summary> /// <param name="endPathToken">The property access token to bind.</param> /// <returns>A Query node representing this endpath token, bound to metadata.</returns> internal QueryNode BindEndPath(EndPathToken endPathToken) { ExceptionUtils.CheckArgumentNotNull(endPathToken, "EndPathToken"); ExceptionUtils.CheckArgumentStringNotNullOrEmpty(endPathToken.Identifier, "EndPathToken.Identifier"); // Set the parent (get the parent type, so you can check whether the Identifier inside EndPathToken really is legit offshoot of the parent type) QueryNode parent = this.DetermineParentNode(endPathToken); QueryNode boundFunction; SingleValueNode singleValueParent = parent as SingleValueNode; if (singleValueParent != null) { if (endPathToken.Identifier == ExpressionConstants.QueryOptionCount) { return(new CountVirtualPropertyNode()); } if (state.IsCollapsed && !IsAggregatedProperty(endPathToken)) { throw new ODataException(ODataErrorStrings.ApplyBinder_GroupByPropertyNotPropertyAccessValue(endPathToken.Identifier)); } // Now that we have the parent type, can find its corresponding EDM type IEdmStructuredTypeReference structuredParentType = singleValueParent.TypeReference == null ? null : singleValueParent.TypeReference.AsStructuredOrNull(); IEdmProperty property = structuredParentType == null ? null : this.Resolver.ResolveProperty(structuredParentType.StructuredDefinition(), endPathToken.Identifier); if (property != null) { return(GeneratePropertyAccessQueryNode(singleValueParent as SingleResourceNode, property, state)); } if (functionCallBinder.TryBindEndPathAsFunctionCall(endPathToken, singleValueParent, state, out boundFunction)) { return(boundFunction); } return(GeneratePropertyAccessQueryForOpenType(endPathToken, singleValueParent)); } // Collection with any or all expression is already supported and handled separately. // Add support of collection with $count segment. CollectionNode colNode = parent as CollectionNode; if (colNode != null && endPathToken.Identifier.Equals(UriQueryConstants.CountSegment, System.StringComparison.Ordinal)) { // create a collection count node for collection node property. return(new CountNode(colNode)); } CollectionNavigationNode collectionParent = parent as CollectionNavigationNode; if (collectionParent != null) { IEdmEntityTypeReference parentType = collectionParent.EntityItemType; IEdmProperty property = this.Resolver.ResolveProperty(parentType.StructuredDefinition(), endPathToken.Identifier); if (property.PropertyKind == EdmPropertyKind.Structural && !property.Type.IsCollection() && this.state.InEntitySetAggregation) { return(new AggregatedCollectionPropertyNode(collectionParent, property)); } } if (functionCallBinder.TryBindEndPathAsFunctionCall(endPathToken, parent, state, out boundFunction)) { return(boundFunction); } throw new ODataException(ODataErrorStrings.MetadataBinder_PropertyAccessSourceNotSingleValue(endPathToken.Identifier)); }
/// <summary> /// Provide additional serialization information to the <see cref="ODataDeltaWriter"/> for <paramref name="deltaFeed"/>. /// </summary> /// <param name="deltaFeed">The instance to set the serialization info.</param> /// <param name="serializationInfo">The serialization info to set.</param> public static void SetSerializationInfo(this ODataDeltaFeed deltaFeed, ODataDeltaFeedSerializationInfo serializationInfo) { ExceptionUtils.CheckArgumentNotNull(deltaFeed, "deltaFeed"); deltaFeed.SerializationInfo = serializationInfo; }
/// <summary> /// Constructs a <see cref="BindingState"/> with the given <paramref name="configuration"/>. /// </summary> /// <param name="configuration">The configuration used for binding.</param> internal BindingState(ODataUriParserConfiguration configuration) { ExceptionUtils.CheckArgumentNotNull(configuration, "configuration"); this.configuration = configuration; this.BindingRecursionDepth = 0; }
/// <summary> /// Provide additional serialization information to the <see cref="ODataDeltaWriter"/> for <paramref name="deltaDeletedEntry"/>. /// </summary> /// <param name="deltaDeletedEntry">The instance to set the serialization info.</param> /// <param name="serializationInfo">The serialization info to set.</param> public static void SetSerializationInfo(this ODataDeltaDeletedEntry deltaDeletedEntry, ODataDeltaSerializationInfo serializationInfo) { ExceptionUtils.CheckArgumentNotNull(deltaDeletedEntry, "deltaDeletedEntry"); deltaDeletedEntry.SerializationInfo = serializationInfo; }
/// <summary> /// Generate an expand item (and a select item for the implicit nav prop if necessary) based on an ExpandTermToken /// </summary> /// <param name="tokenIn">the expandTerm token to visit</param> /// <returns>the expand item for this expand term token.</returns> private SelectItem GenerateExpandItem(ExpandTermToken tokenIn) { ExceptionUtils.CheckArgumentNotNull(tokenIn, "tokenIn"); PathSegmentToken currentToken = tokenIn.PathToNavigationProp; IEdmStructuredType currentLevelEntityType = this.EdmType; List <ODataPathSegment> pathSoFar = new List <ODataPathSegment>(); PathSegmentToken firstNonTypeToken = currentToken; if (currentToken.IsNamespaceOrContainerQualified()) { pathSoFar.AddRange(SelectExpandPathBinder.FollowTypeSegments(currentToken, this.Model, this.Settings.SelectExpandLimit, this.configuration.Resolver, ref currentLevelEntityType, out firstNonTypeToken)); } IEdmProperty edmProperty = this.configuration.Resolver.ResolveProperty(currentLevelEntityType, firstNonTypeToken.Identifier); if (edmProperty == null) { throw new ODataException(ODataErrorStrings.MetadataBinder_PropertyNotDeclared(currentLevelEntityType.FullTypeName(), currentToken.Identifier)); } IEdmNavigationProperty currentNavProp = edmProperty as IEdmNavigationProperty; IEdmStructuralProperty currentComplexProp = edmProperty as IEdmStructuralProperty; if (currentNavProp == null && currentComplexProp == null) { throw new ODataException(ODataErrorStrings.ExpandItemBinder_PropertyIsNotANavigationPropertyOrComplexProperty(currentToken.Identifier, currentLevelEntityType.FullTypeName())); } if (currentComplexProp != null) { currentNavProp = ParseComplexTypesBeforeNavigation(currentComplexProp, ref firstNonTypeToken, pathSoFar); } // ensure that we're always dealing with proper V4 syntax if (firstNonTypeToken.NextToken != null && firstNonTypeToken.NextToken.NextToken != null) { throw new ODataException(ODataErrorStrings.ExpandItemBinder_TraversingMultipleNavPropsInTheSamePath); } bool isRef = false; if (firstNonTypeToken.NextToken != null) { // lastly... make sure that, since we're on a NavProp, that the next token isn't null. if (firstNonTypeToken.NextToken.Identifier == UriQueryConstants.RefSegment) { isRef = true; } else { throw new ODataException(ODataErrorStrings.ExpandItemBinder_TraversingMultipleNavPropsInTheSamePath); } } // Add the segments in select and expand to parsed segments this.parsedSegments.AddRange(pathSoFar); IEdmNavigationSource targetNavigationSource = null; if (this.NavigationSource != null) { IEdmPathExpression bindingPath; targetNavigationSource = this.NavigationSource.FindNavigationTarget(currentNavProp, BindingPathHelper.MatchBindingPath, this.parsedSegments, out bindingPath); } NavigationPropertySegment navSegment = new NavigationPropertySegment(currentNavProp, targetNavigationSource); pathSoFar.Add(navSegment); this.parsedSegments.Add(navSegment); // Add the navigation property segment to parsed segments for future usage. ODataExpandPath pathToNavProp = new ODataExpandPath(pathSoFar); // call MetadataBinder to build the filter clause FilterClause filterOption = null; if (tokenIn.FilterOption != null) { MetadataBinder binder = this.BuildNewMetadataBinder(targetNavigationSource); FilterBinder filterBinder = new FilterBinder(binder.Bind, binder.BindingState); filterOption = filterBinder.BindFilter(tokenIn.FilterOption); } // call MetadataBinder again to build the orderby clause OrderByClause orderbyOption = null; if (tokenIn.OrderByOptions != null) { MetadataBinder binder = this.BuildNewMetadataBinder(targetNavigationSource); OrderByBinder orderByBinder = new OrderByBinder(binder.Bind); orderbyOption = orderByBinder.BindOrderBy(binder.BindingState, tokenIn.OrderByOptions); } SearchClause searchOption = null; if (tokenIn.SearchOption != null) { MetadataBinder binder = this.BuildNewMetadataBinder(targetNavigationSource); SearchBinder searchBinder = new SearchBinder(binder.Bind); searchOption = searchBinder.BindSearch(tokenIn.SearchOption); } ComputeClause computeOption = null; if (tokenIn.ComputeOption != null) { MetadataBinder binder = this.BuildNewMetadataBinder(targetNavigationSource); ComputeBinder computeBinder = new ComputeBinder(binder.Bind); computeOption = computeBinder.BindCompute(tokenIn.ComputeOption); } ApplyClause applyOption = null; if (tokenIn.ApplyOptions != null) { MetadataBinder binder = this.BuildNewMetadataBinder(targetNavigationSource); ApplyBinder applyBinder = new ApplyBinder(binder.Bind, binder.BindingState); applyOption = applyBinder.BindApply(tokenIn.ApplyOptions); } if (isRef) { return(new ExpandedReferenceSelectItem(pathToNavProp, targetNavigationSource, filterOption, orderbyOption, tokenIn.TopOption, tokenIn.SkipOption, tokenIn.CountQueryOption, searchOption, computeOption, applyOption)); } SelectExpandClause subSelectExpand; if (tokenIn.ExpandOption != null) { subSelectExpand = this.GenerateSubExpand(tokenIn); } else { subSelectExpand = BuildDefaultSubExpand(); } subSelectExpand = this.DecorateExpandWithSelect(subSelectExpand, currentNavProp, tokenIn.SelectOption); LevelsClause levelsOption = ParseLevels(tokenIn.LevelsOption, currentLevelEntityType, currentNavProp); return(new ExpandedNavigationSelectItem(pathToNavProp, targetNavigationSource, subSelectExpand, filterOption, orderbyOption, tokenIn.TopOption, tokenIn.SkipOption, tokenIn.CountQueryOption, searchOption, levelsOption, computeOption, applyOption)); }
/// <summary> /// Provide additional serialization information to the <see cref="ODataDeltaWriter"/> for <paramref name="deltalink"/>. /// </summary> /// <param name="deltalink">The instance to set the serialization info.</param> /// <param name="serializationInfo">The serialization info to set.</param> public static void SetSerializationInfo(this ODataDeltaLinkBase deltalink, ODataDeltaSerializationInfo serializationInfo) { ExceptionUtils.CheckArgumentNotNull(deltalink, "deltalink"); deltalink.SerializationInfo = serializationInfo; }
/// <summary> /// Visits a <see cref="QueryToken"/> in the lexical tree and binds it to metadata producing a semantic <see cref="QueryNode"/>. /// </summary> /// <param name="token">The query token on the input.</param> /// <returns>The bound query node output.</returns> protected internal QueryNode Bind(QueryToken token) { ExceptionUtils.CheckArgumentNotNull(token, "token"); this.BindingState.RecurseEnter(); QueryNode result; switch (token.Kind) { case QueryTokenKind.Any: result = this.BindAnyAll((AnyToken)token); break; case QueryTokenKind.All: result = this.BindAnyAll((AllToken)token); break; case QueryTokenKind.InnerPath: result = this.BindInnerPathSegment((InnerPathToken)token); break; case QueryTokenKind.Literal: result = this.BindLiteral((LiteralToken)token); break; case QueryTokenKind.StringLiteral: result = this.BindStringLiteral((StringLiteralToken)token); break; case QueryTokenKind.BinaryOperator: result = this.BindBinaryOperator((BinaryOperatorToken)token); break; case QueryTokenKind.UnaryOperator: result = this.BindUnaryOperator((UnaryOperatorToken)token); break; case QueryTokenKind.EndPath: result = this.BindEndPath((EndPathToken)token); break; case QueryTokenKind.FunctionCall: result = this.BindFunctionCall((FunctionCallToken)token); break; case QueryTokenKind.DottedIdentifier: result = this.BindCast((DottedIdentifierToken)token); break; case QueryTokenKind.RangeVariable: result = this.BindRangeVariable((RangeVariableToken)token); break; case QueryTokenKind.FunctionParameterAlias: result = this.BindParameterAlias((FunctionParameterAliasToken)token); break; case QueryTokenKind.FunctionParameter: result = this.BindFunctionParameter((FunctionParameterToken)token); break; default: throw new ODataException(ODataErrorStrings.MetadataBinder_UnsupportedQueryTokenKind(token.Kind)); } if (result == null) { throw new ODataException(ODataErrorStrings.MetadataBinder_BoundNodeCannotBeNull(token.Kind)); } this.BindingState.RecurseLeave(); return(result); }
/// <summary> /// Constructs a SingleNavigationNode. /// </summary> /// <param name="source">The previous node in the path.</param> /// <param name="navigationProperty">The navigation property this node represents.</param> /// <param name="bindingPath">The binding path of navigation property</param> /// <exception cref="System.ArgumentNullException">Throws if the input navigationProperty or source is null.</exception> /// <exception cref="ArgumentException">Throws if the input navigationProperty targets more than one entity.</exception> public SingleNavigationNode(SingleResourceNode source, IEdmNavigationProperty navigationProperty, IEdmPathExpression bindingPath) : this(ExceptionUtils.CheckArgumentNotNull(source, "source").NavigationSource, navigationProperty, bindingPath) { this.source = source; }
/// <summary> /// Constructor /// </summary> /// <param name="parameterAliasValueExpressions">The parameter alias value expressions from uri.</param> public ParameterAliasValueAccessor(IDictionary <string, string> parameterAliasValueExpressions) { ExceptionUtils.CheckArgumentNotNull(parameterAliasValueExpressions, "parameterAliasValueExpressions"); this.ParameterAliasValueExpressions = new Dictionary <string, string>(parameterAliasValueExpressions, StringComparer.Ordinal); this.ParameterAliasValueNodesCached = new Dictionary <string, SingleValueNode>(StringComparer.Ordinal); }
/// <summary> /// Constructs a SingleNavigationNode. /// </summary> /// <param name="source">he previous node in the path.</param> /// <param name="navigationProperty">The navigation property this node represents.</param> /// <param name="segments">The path segments parsed in path and query option.</param> internal SingleNavigationNode(SingleResourceNode source, IEdmNavigationProperty navigationProperty, List <ODataPathSegment> segments) : this(ExceptionUtils.CheckArgumentNotNull(source, "source").NavigationSource, navigationProperty, segments) { this.source = source; }
/// <summary> /// Accept a <see cref="IPathSegmentTokenVisitor"/> to walk a tree of <see cref="PathSegmentToken"/>s. /// </summary> /// <param name="visitor">An implementation of the visitor interface.</param> public override void Accept(IPathSegmentTokenVisitor visitor) { ExceptionUtils.CheckArgumentNotNull(visitor, "visitor"); visitor.Visit(this); }
/// <summary> /// Creates an OrderByBinder /// </summary> /// <param name="bindMethod">Method to use to visit the token tree and bind the tokens recursively.</param> internal OrderByBinder(MetadataBinder.QueryTokenVisitor bindMethod) { ExceptionUtils.CheckArgumentNotNull(bindMethod, "bindMethod"); this.bindMethod = bindMethod; }
/// <summary> /// Handle a <see cref="PropertySegment"/> using an instance of <see cref="PathSegmentHandler"/>. /// </summary> /// <param name="handler">An implementation of the handler interface.</param> /// <exception cref="System.ArgumentNullException">Throws if the input handler is null.</exception> public override void HandleWith(PathSegmentHandler handler) { ExceptionUtils.CheckArgumentNotNull(handler, "handler"); handler.Handle(this); }
/// <summary> /// Find any related keys from the parent key segment, if it exists, and add them to the raw key values that /// we already have from the uri. /// </summary> /// <param name="rawKeyValuesFromUri">The raw key values as we've parsed them from the uri.</param> /// <param name="targetEntityKeyProperties">The list of key properties on the target entity.</param> /// <param name="currentNavigationProperty">The current navigation property that we're trying to follow using the raw key values</param> /// <param name="keySegmentOfParentEntity">The key segment of the parent entity in this path, if it exists. Null otherwise</param> /// <returns>A new SegmentArgumentParser with any keys that were found added to its list of NamedValues.</returns> /// <throws>Thorws if the input currentNavigationProperty is null.</throws> public static SegmentArgumentParser FindAndUseKeysFromRelatedSegment(SegmentArgumentParser rawKeyValuesFromUri, IEnumerable <IEdmStructuralProperty> targetEntityKeyProperties, IEdmNavigationProperty currentNavigationProperty, KeySegment keySegmentOfParentEntity) { ExceptionUtils.CheckArgumentNotNull(currentNavigationProperty, "currentNavigationProperty"); ExceptionUtils.CheckArgumentNotNull(rawKeyValuesFromUri, "rawKeyValuesFromUri"); ReadOnlyCollection <IEdmStructuralProperty> targetKeyPropertyList = targetEntityKeyProperties != null ? new ReadOnlyCollection <IEdmStructuralProperty>(targetEntityKeyProperties.ToList()) : new ReadOnlyCollection <IEdmStructuralProperty>(new List <IEdmStructuralProperty>()); // should only get here if the number of raw parameters from the uri is different than the number of key properties for the target entity. Debug.Assert(rawKeyValuesFromUri.ValueCount < targetKeyPropertyList.Count(), "rawKeyValuesFromUri.ValueCount < targetEntityKeyProperties.Count()"); // if the raw key from the uri has positional values, there must be only one of them // its important to cache this value here because we'll change it when we add new // named values below (the implementation of AreValuesNamed is just namedValues !=null) bool hasPositionalValues = !rawKeyValuesFromUri.AreValuesNamed; if (hasPositionalValues && rawKeyValuesFromUri.ValueCount > 1) { return(rawKeyValuesFromUri); } if (keySegmentOfParentEntity == null) { return(rawKeyValuesFromUri); } // TODO: p2 merge the below 2 pieces of codes // find out if any target entity key properties have referential constraints that link them to the previous rawKeyValuesFromUri. List <EdmReferentialConstraintPropertyPair> keysFromReferentialIntegrityConstraint = ExtractMatchingPropertyPairsFromNavProp(currentNavigationProperty, targetKeyPropertyList).ToList(); foreach (EdmReferentialConstraintPropertyPair keyFromReferentialIntegrityConstraint in keysFromReferentialIntegrityConstraint) { KeyValuePair <string, object> valueFromParent = keySegmentOfParentEntity.Keys.SingleOrDefault(x => x.Key == keyFromReferentialIntegrityConstraint.DependentProperty.Name); if (valueFromParent.Key != null) { // if the key from the referential integrity constraint is one of the target key properties // and that key property isn't already populated in the raw key values from the uri, then // we set that value to the value from the parent key segment. if (targetKeyPropertyList.Any(x => x.Name == keyFromReferentialIntegrityConstraint.PrincipalProperty.Name)) { rawKeyValuesFromUri.AddNamedValue( keyFromReferentialIntegrityConstraint.PrincipalProperty.Name, ConvertKeyValueToUriLiteral(valueFromParent.Value, rawKeyValuesFromUri.KeyAsSegment)); } } } // also need to look to see if any nav props exist in the target set that refer back to this same set, which might have // referential constraints also. keysFromReferentialIntegrityConstraint.Clear(); IEdmNavigationProperty reverseNavProp = currentNavigationProperty.Partner; if (reverseNavProp != null) { keysFromReferentialIntegrityConstraint.AddRange(ExtractMatchingPropertyPairsFromReversedNavProp(reverseNavProp, targetKeyPropertyList)); } foreach (EdmReferentialConstraintPropertyPair keyFromReferentialIntegrityConstraint in keysFromReferentialIntegrityConstraint) { KeyValuePair <string, object> valueFromParent = keySegmentOfParentEntity.Keys.SingleOrDefault(x => x.Key == keyFromReferentialIntegrityConstraint.PrincipalProperty.Name); if (valueFromParent.Key != null) { // if the key from the referential integrity constraint is one of the target key properties // and that key property isn't already populated in the raw key values from the uri, then // we set that value to the value from the parent key segment. if (targetKeyPropertyList.Any(x => x.Name == keyFromReferentialIntegrityConstraint.DependentProperty.Name)) { rawKeyValuesFromUri.AddNamedValue( keyFromReferentialIntegrityConstraint.DependentProperty.Name, ConvertKeyValueToUriLiteral(valueFromParent.Value, rawKeyValuesFromUri.KeyAsSegment)); } } } // if we had a positional value before, then we need to add that value as a new named value. // the name that we choose will be the only value from the target entity key properties // that isn't already set in the NamedValues list. if (hasPositionalValues) { if (rawKeyValuesFromUri.NamedValues != null) { List <IEdmStructuralProperty> unassignedProperties = targetKeyPropertyList.Where(x => !rawKeyValuesFromUri.NamedValues.ContainsKey(x.Name)).ToList(); if (unassignedProperties.Count == 1) { rawKeyValuesFromUri.AddNamedValue(unassignedProperties[0].Name, rawKeyValuesFromUri.PositionalValues[0]); } else { return(rawKeyValuesFromUri); } // clear out the positional value so that we keep a consistent state in the // raw keys from uri. rawKeyValuesFromUri.PositionalValues.Clear(); } else { return(rawKeyValuesFromUri); } } return(rawKeyValuesFromUri); }