在web api中使用可选的interger参数

时间:2018-01-03 11:48:51

标签: c# asp.net-web-api routing

我正在用C#编写通用报告web api,我希望有一个可选参数,因为有些报告只需要报告ID和主要ID,有时我需要报告ID,主要ID和次要ID。

然而目前这有效: http://localhost:50505/api/report/4/9981/0

但这不是: http://localhost:50505/api/report/4/9981

我不想传递零,因为该参数不用于id 4的报告。

这是代码:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web.Http;
using System.Web.Http.Description;
using IPD_Report.Api.Interfaces.Factories;
using IPD_Report.Dtos.RequestModels;
using IPD_Report.Dtos.ResponseModels;
using IPD_Report.SoapService.Attributes;
using IPD_Report.SoapService.Commands;
using IPD_Report.SoapService.Interfaces.Commands;

namespace IPD_Report.Api.Controllers
{
    /// <summary>
    /// This controller is used to generate reports based on report ID.
    /// </summary>
    [RoutePrefix("api/report")]
    public class ReportController : ApiController
    {
        private readonly IReportCommands _reportCommands;
        private readonly IDtoFactory _dtoFactory;

        public ReportController(IReportCommands reportCommands, IDtoFactory dtoFactory)
        {
            _reportCommands = reportCommands;
            _dtoFactory = dtoFactory;
        }

        /// <summary>
        /// Generic GET request for returning report.
        /// </summary>
        /// <param name="reportId"></param>
        /// <param name="primaryId"></param>
        /// <param name="secondaryId"></param>
        /// byte[]
        [Route("{reportId}/{primaryId}/{secondaryId}")]
        [ResponseType(typeof(byte[]))]
        [HttpGet]
        public IHttpActionResult Get(int reportId, int primaryId, int? secondaryId = 0)
        {
            var dto = _dtoFactory.GenerateModel(reportId, primaryId, secondaryId);

            var stuff = GetAttribute(reportId, dto);

            return Ok(stuff);
        }

        /// <summary>
        /// Returns a list of available methods as a string list containing the method ID, method name, and returned filetype
        /// </summary>
        /// <returns>List&lt;List&lt;string&gt;&gt;</returns>
        [Route("getReportList")]
        [ResponseType(typeof(IEnumerable<ReportTypeModel>))]
        [HttpGet]
        public IHttpActionResult GetReportList()
        {
            var methodInfo = typeof(ReportCommands).GetMethods()
                .Where(x => x.GetCustomAttributes(false).OfType<MethodId>().Any())
                .Select(x => x.GetCustomAttributesData().Select(y => y.ConstructorArguments)).ToList();


            var methodList = new List<ReportTypeModel>();
            for(var i =0;i<methodInfo.Count;i++)
            {
                var annotation = (methodInfo.ToList()[i]?.ToList().FirstOrDefault() ?? throw new InvalidOperationException()).ToList();

                methodList.Add(new ReportTypeModel
                {
                    Id = int.Parse(annotation[0].Value.ToString()),
                    Name = annotation[1].Value.ToString(),
                    Format = annotation[2].Value.ToString()

                });
            }

            return Ok(methodList);
        }

        private object GetAttribute(int id, BaseModel baseModel)
        {
            var methodInfo = typeof(ReportCommands).
                GetMethods()
                .Where(x => x.GetCustomAttributes(false).OfType<MethodId>().Any())
                .First(x => x.GetCustomAttributes(false).OfType<MethodId>().First().Id == id);


            return methodInfo.Invoke(_reportCommands, new object[] { baseModel });
        }
    }
}

我需要一些帮助建议:

public IHttpActionResult Get(int reportId,int primaryId,int?secondaryId = 0)

我将辅助ID作为可选参数编​​写,但如果我尝试调用此网址:http://localhost:50505/api/report/4/9981

我得到了404。

有什么建议吗?

尼克

1 个答案:

答案 0 :(得分:0)

只需更改路由参数并使其可以为空;

    mSearchView = findViewById(R.id.search_view);

    mSearchView.setOnCloseListener(new SearchView.OnCloseListener() {
        @Override
        public boolean onClose() {
            RelativeLayout.LayoutParams param = (RelativeLayout.LayoutParams) mSearchView.getLayoutParams();
            param.removeRule(RelativeLayout.ALIGN_PARENT_LEFT);
            //set layout params to cause layout update
            mSearchView.setLayoutParams(param);
            return false;
        }
    });
    mSearchView.setOnSearchClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {
            RelativeLayout.LayoutParams param = (RelativeLayout.LayoutParams) mSearchView.getLayoutParams();
            param.addRule(RelativeLayout.ALIGN_PARENT_LEFT);
            //set layout params to cause layout update
            mSearchView.setLayoutParams(param);
        }
    });