/// <summary> /// Parse queries such as: /// "aggregate(Amount with sum as Total)" and "aggregate(Amount mul Product/TaxRate with sum as Tax)" /// </summary> /// <param name="apply"></param> /// <param name="query"></param> /// <param name="oDataUriParserConfiguration"></param> /// <param name="edmType"></param> /// <param name="edmNavigationSource"></param> /// <returns></returns> private static ApplyAggregateClause ParseAggregate(ApplyClause apply, string query, ODataUriParserConfiguration oDataUriParserConfiguration, IEdmType edmType, IEdmNavigationSource edmNavigationSource) { query = IsolateQuery(query, UriQueryConstants.AggregateTransformation); string aggregatableProperty; string aggregationMethod; string alias; aggregatableProperty = GetAggregatableProperty(query, true, out alias, out aggregationMethod); //create an projection Expression to the property var AggregatablePropertyExpression = ODataQueryOptionParser.ParseExpressionImplementation( aggregatableProperty, oDataUriParserConfiguration, edmType, edmNavigationSource); return(new ApplyAggregateClause() { AggregatablePropertyExpression = AggregatablePropertyExpression, Alias = alias, AggregationMethod = aggregationMethod, AggregatableProperty = aggregatableProperty, Apply = apply }); }
/// <summary> /// Parse queries such as : "groupby(Customer/Name,Customer/ID,Product/Name,Account)" or "groupby((Customer/Country,Product/Name), aggregate(Amount with sum as Total))" /// </summary> /// <param name="apply"></param> /// <param name="query"></param> /// <param name="oDataUriParserConfiguration"></param> /// <param name="edmType"></param> /// <param name="edmNavigationSource"></param> /// <returns></returns> private static ApplyGroupbyClause ParseGroupBy(ApplyClause apply, string query, ODataUriParserConfiguration oDataUriParserConfiguration, IEdmType edmType, IEdmNavigationSource edmNavigationSource) { string selectQuery; ApplyAggregateClause aggregateClause = null; query = IsolateQuery(query, UriQueryConstants.GroupbyTransformation); if (query.StartsWith("(") && query.EndsWith(")")) { query = query.TrimOne('(', ')'); } var p = query.IndexOf(UriQueryConstants.AggregateTransformation + '('); if (p == -1) { if (query.StartsWith("(") && query.EndsWith(")")) { query = query.TrimOne('(', ')'); } selectQuery = query; } else { selectQuery = query.Substring(0, p).Trim().Trim(',').TrimOne('(', ')'); aggregateClause = ParseAggregate(apply, query.Substring(p), oDataUriParserConfiguration, edmType, edmNavigationSource); } var selectedStatements = selectQuery.Split(','); var withIndex = selectQuery.IndexOf("with"); if (withIndex > 0) { selectedStatements = selectQuery.Substring(0, withIndex).Split(','); var withStatement = selectQuery.Substring(withIndex, selectQuery.Length - withIndex); selectedStatements[selectedStatements.Count() - 1] = selectedStatements[selectedStatements.Count() - 1] + withStatement; } string aggregationMethod, alias; List <ExpressionClause> aggregatablePropertyExpressions = null; try { aggregatablePropertyExpressions = selectedStatements.Select(statement => ODataQueryOptionParser.ParseExpressionImplementation( GetAggregatableProperty(statement, false, out alias, out aggregationMethod), oDataUriParserConfiguration, edmType, edmNavigationSource)).ToList(); } catch (Exception) { //parsing of some expressions (like property on enum such as DateTimeOffset/Minute) are not supported so ODataQueryOptionParser.ParseExpressionImplementation will fail aggregatablePropertyExpressions = null; } return(new ApplyGroupbyClause() { SelectedStatements = selectedStatements, SelectedPropertiesExpressions = aggregatablePropertyExpressions, Aggregate = aggregateClause, Apply = apply }); }