首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何将多个参数传递给Odata 4操作( Web 2.2项目的一部分)

如何将多个参数传递给Odata 4操作( Web 2.2项目的一部分)
EN

Stack Overflow用户
提问于 2017-03-10 18:55:23
回答 3查看 10.4K关注 0票数 1

我正在尝试使用odata -4(在WebAPI2.2项目中)创建一个odata端点,其中我需要在odata控制器中有一个GET操作来接受多个字符串参数(它们是自定义搜索属性,除了创建odata控制器的实体中的属性外)。

但是,到目前为止,我已经做了所有的尝试,在浏览器中访问特定的操作时,我总是遇到一个或另一个错误。到目前为止,我还没有得到流/语法的工作组合,因此在这里获得关于如何在odata-4 中实现将多个param传递给odata操作的建议,因此可以在这里获得关于如何修复错误的建议。

代码如下:

package.config:

代码语言:javascript
复制
<?xml version="1.0" encoding="utf-8"?>
<packages>
  <package id="Microsoft.AspNet.Mvc" version="5.1.2" targetFramework="net45" />
  <package id="Microsoft.AspNet.OData" version="5.3.1" targetFramework="net45" />
  <package id="Microsoft.AspNet.Razor" version="3.1.2" targetFramework="net45" />
  <package id="Microsoft.AspNet.WebApi" version="5.2.3" targetFramework="net45" />
  <package id="Microsoft.AspNet.WebApi.Client" version="5.2.3" targetFramework="net45" />
  <package id="Microsoft.AspNet.WebApi.Core" version="5.2.3" targetFramework="net45" />
  <package id="Microsoft.AspNet.WebApi.OData" version="5.1.2" targetFramework="net45" />
  <package id="Microsoft.AspNet.WebApi.WebHost" version="5.2.3" targetFramework="net45" />
  <package id="Microsoft.AspNet.WebPages" version="3.1.2" targetFramework="net45" />
  <package id="Microsoft.Data.Edm" version="5.6.0" targetFramework="net45" />
  <package id="Microsoft.Data.OData" version="5.6.0" targetFramework="net45" />
  <package id="Microsoft.OData.Core" version="6.5.0" targetFramework="net45" />
  <package id="Microsoft.OData.Edm" version="6.5.0" targetFramework="net45" />
</packages>

WebApiConfig:

代码语言:javascript
复制
public static class WebApiConfig
    {
        public static void Register(HttpConfiguration config)
        {
            config.MapHttpAttributeRoutes();

            ODataModelBuilder builder = new ODataConventionModelBuilder();

            builder.EntitySet<DocumentsModel>("SampleData");

            var function = builder.Function("SampleFunction");
            function.Parameter<string>("catGUIDOrText");
            function.Parameter<string>("type");
            function.Parameter<string>("isAutoCompSearch");
            function.ReturnsCollectionFromEntitySet<DocumentsModel>("SampleData");

            config.MapODataServiceRoute("odata", "odata", builder.GetEdmModel());

            config.Routes.MapHttpRoute(
                name: "DefaultApi",
                routeTemplate: "api/{controller}/{id}",
                defaults: new { id = RouteParameter.Optional }
            );
        }

Odata控制器:

代码语言:javascript
复制
[ODataRoutePrefix("SampleData")]
    public class SampleDataController : ODataController
    {
        [EnableQuery]
        [HttpGet]
        [ODataRoute("SampleFunction(catGUIDOrText={catGUIDOrText},type={type},isAutoCompSearch={isAutoCompSearch})")]
        public IEnumerable<DocumentsModel> GetSampleData([FromODataUri] string catGUIDOrText, [FromODataUri] string type, [FromODataUri] string isAutoCompSearch)
        {
            return new List<DocumentsModel>().AsQueryable<DocumentsModel>();
        }
    }

注释:- DocumentsModel是一个具有所有字符串属性的类。

错误详细信息

现在,当通过下面的URL在浏览器中访问此操作时,我收到了错误:

网址: http://localhost/VirtualDirectoryNameInIIS/odata/SampleData/SampleFunction(catGUIDOrText=

我得到的错误:

路径模板'SampleData/SampleFunction(catGUIDOrText={catGUIDOrText},type={type},isAutoCompSearch={isAutoCompSearch})‘在控制器'SampleData’中的动作'GetSampleData‘不是有效的OData路径模板。请求URI无效。由于段'SampleData‘指的是一个集合,这必须是请求URI中的最后一个段,或者后面必须有一个可以绑定到它的函数或操作,否则所有中间段都必须引用单个资源。

请帮助我的任何输入,您可能有围绕这一点,无论是在代码或在url我正在使用的访问给定的方法。谢谢。

为了解决这个问题,或者为了确保我遵循正确的方向/语法,我遵循了一些引用:

  1. Web和OData传递多个参数
  2. https://damienbod.com/2014/06/13/web-api-and-odata-v4-queries-functions-and-attribute-routing-part-2/
EN

回答 3

Stack Overflow用户

发布于 2017-07-26 19:17:27

编辑添加显式命名空间的WebApiConfig.cs

代码语言:javascript
复制
        builder.Namespace = "MyNamespace";
  • 如果不将其显化,默认名称空间为" default“:)

编辑更改函数声明的WebApiConfig.cs

代码语言:javascript
复制
        FunctionConfiguration function = builder.EntityType<DocumentsModel>().Collection.Function("SampleFunction");
        function.Parameter<string>("catGUIDOrText");
        function.Parameter<string>("type");
        function.Parameter<string>("isAutoCompSearch");
        function.ReturnsCollectionFromEntitySet<DocumentsModel>("SampleData");
  • 使用".EntityType()“以实体DocumentsModel的控制器为目标,该控制器已命名为"SampleData”
  • 使用".Collection“以实体的集合为目标;否则,如果省略,则针对单个实体

更改Odata

代码语言:javascript
复制
//[ODataRoutePrefix("SampleData")]
public class SampleDataController : ODataController
{
    //[ODataRoute("SampleData/MyNamespace.SampleFunction(catGUIDOrText={catGUIDOrText},type={type},isAutoCompSearch={isAutoCompSearch})")]
    [EnableQuery]
    [HttpGet]
    public IHttpActionResult SampleFunction(string catGUIDOrText, string type, string isAutoCompSearch)
    {
        return new List<DocumentsModel>().AsQueryable<DocumentsModel>();
    }
}
  • 您可以注释ODataRoutePrefix("SampleData"):命名约定的路由是_entitySetName_Controller,您可以在WebApiConfig上设置"builder.EntitySet("SampleData")“
  • 返回类型不能是IEnumerable;如果使用IHttpActionResult,就不会有问题。
  • 您可以注释ODataRoute,如果您使用命名约定

更改url,添加odata命名空间

http://localhost/VirtualDirectoryNameInIIS/odata/SampleData/MyNamespace.SampleFunction(catGUIDOrText='752',type='230',isAutoCompSearch='false')

在您的代码中,您已经声明了一个未绑定函数,但是您的调用就像一个绑定函数

你可以在这个教程中找到你需要的信息

票数 8
EN

Stack Overflow用户

发布于 2019-08-04 22:16:36

我试图实现类似的目标,但我直接使用ODataQueryOptions,因此我的控制器如下所示:

代码语言:javascript
复制
[HttpGet]
public ODataList<DTO> Get(ODataQueryOptions<POCO> options) {
    using (var db = new Entities()) {
        var param = Request.RequestUri.ParseQueryString().Get("CompanyCode");
        return _oData.Query<POCO, DTO>(options, db.POCO.AsQueryable());
    }
}

如果我试图在签名中添加其他参数,就会出现错误,因此我试图找到一种方法,将CompanyCode与所有OData参数一起传递,并且仍然要完成所有的分页/过滤/排序工作。

这对我来说很有魅力--我只是在请求中增加了额外的部分,比如:

api/DTO?CompanyCode=blah&$skip=50&$top=50

.NET OData的内容似乎忽略了我额外的param,没有问题--我只是手动解析param,而不是将它放在函数签名中。对我来说已经够好了!

票数 1
EN

Stack Overflow用户

发布于 2020-04-03 10:25:14

我可以通过以下方式解决这一问题:

  1. 将下面的代码添加到startup.cs 公共ConfigureServices(IServiceCollection服务){ //您的代码services.AddMvc();services.AddOData();}公共空配置(IApplicationBuilder app,IWebHostEnvironment env) { //您的代码app.UseRouting();app.UseEndpoints(端点=> {api“,"api",”api“,GetEdmModel();});}私有pullRequestsByProjectByContributor.Parameter("id").Required();IEdmModel GetEdmModel() { var edmBuilder =新的ODataConventionModelBuilder();edmBuilder.EntitySet(“学生”);var pullRequestsByProjectByContributor = edmBuilder.EntityType().Collection .Function("GetStudents") .ReturnsCollectionFromEntitySet("Students");
  2. 在控制器中 ODataRouting公共类StudentsController : ODataController { //http://localhost:5112/api/students/GetStudents(id=3,classId=6)?$orderby=id%20desc&$skip=1&$top=2 HttpGet ODataRoute("GetStudents(id={id},classId={classId})")公共异步任务GetStudents(int id,int classId,ODataQueryOptions options) {}
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/42725782

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档