在OData中使用带有参数的未绑定操作

时间:2016-12-01 07:05:06

标签: c# .net odata

使用未绑定的操作和参数解析OData URI时,会引发以下异常: The request URI is not valid. The segment 'TestAction' cannot include key predicates, however it may end with empty parenthesis。下面的代码再现了例外:

        var builder = new ODataConventionModelBuilder
        {
            Namespace = "Test",
            ContainerName = "Test"
        };

        var action = builder.Action("TestAction").Returns<long>();

        action.Parameter<int?>("x");
        action.Parameter<int?>("y");

        var model = builder.GetEdmModel();

        var parser = new ODataUriParser(model, new Uri("TestAction(x=1,y=2)", UriKind.Relative));

        var path = parser.ParsePath();

我调查了Microsoft.OData.Core源代码并在FunctionOverloadResolver类中找到了这个代码:

        try
        {
            if (parameterNames.Count > 0)
            {
                // In this case we have to return a function so filter out actions because the number of parameters > 0.
                candidateMatchingOperationImports = resolver.ResolveOperationImports(model, identifier).RemoveActionImports(out foundActionImportsWhenLookingForFunctions).FilterFunctionsByParameterNames(parameterNames, resolver.EnableCaseInsensitive).Cast<IEdmOperationImport>().ToList();
            }
            else
            {
                candidateMatchingOperationImports = resolver.ResolveOperationImports(model, identifier).ToList();
            }
        }
        catch (Exception exc)
        {
            if (!ExceptionUtils.IsCatchableExceptionType(exc))
            {
                throw;
            }

            throw new ODataException(ODataErrorStrings.FunctionOverloadResolver_FoundInvalidOperationImport(identifier), exc);
        }

        if (foundActionImportsWhenLookingForFunctions.Count > 0)
        {
            throw ExceptionUtil.CreateBadRequestError(ODataErrorStrings.RequestUriProcessor_SegmentDoesNotSupportKeyPredicates(identifier));
        }

为什么解析器类需要在操作有参数时过滤掉操作?

1 个答案:

答案 0 :(得分:1)

我终于找到了问题所在。操作参数应位于请求有效负载上。因此URI应该如下所示:

    var parser = new ODataUriParser(model, new Uri("TestAction", UriKind.Relative));