标签: attributerouting

使用AttributeRouting在WebAPI中指定默认控制器/操作路由

如何设置使用AttributeRouting时使用的默认控制器,而不是WebAPI使用的默认RouteConfiguration.即删除注释的代码部分,因为使用AttribteRouting时这是多余的

    public class RouteConfig
    {
       public static void RegisterRoutes(RouteCollection routes)
       {
        routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
        //routes.MapRoute(
        //    name: "Default",
        //    url: "{controller}/{action}/{id}",
        //    defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }
        //);

       }
     }
Run Code Online (Sandbox Code Playgroud)

如果我评论上面的部分并尝试运行webapi应用程序,我会收到以下错误,因为没有定义默认的Home控制器/操作. HTTP错误403.14 - 禁止Web服务器配置为不列出此目录的内容.

如何通过归属控制器/操作的属性路由指定路由?

编辑:代码示例:

 public class HomeController : Controller
{
    [GET("")]
    public ActionResult Index()
    {
        return View();
    }

    public ActionResult Help()
    {
        var explorer = GlobalConfiguration.Configuration.Services.GetApiExplorer();
        return View(new ApiModel(explorer));
    }
}
Run Code Online (Sandbox Code Playgroud)

c# asp.net-web-api attributerouting

8
推荐指数
2
解决办法
2万
查看次数

AttributeRouting不能与HttpConfiguration对象一起编写集成测试

我按照此处列出的想法创建了一些集成测试:http: //www.strathweb.com/2012/06/asp-net-web-api-integration-testing-with-in-memory-hosting/

当我尝试从手工制作的HttpConfiguration对象注册路由时,我收到以下错误:"路由模板'api/Contacts/{id}'的路径上的约束条目'inboundHttpMethod'必须具有字符串值或者是一种实现'IHttpRouteConstraint'的类型."

示例代码:控制器:

 [RoutePrefix("api")]
    public class ContactsController : ApiController
    {
        [GET("Contacts/{id}",RouteName="GetContactsById")]
        public ContactDTO Get(int id)
        {
      return new ContactDTO{ ID =1, Name="test"};
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

TestClass(MSTest):

 [TestClass]
    public class ContactsTest
    {
        private string _url = "http://myhost/api/";
        private static HttpConfiguration config = null;
        private static HttpServer server = null;
        private HttpRequestMessage createRequest(string url, string mthv, HttpMethod method)
        {
             var request = new HttpRequestMessage();
            request.RequestUri = new Uri(_url + url);
            request.Headers.Accept.Add(new MediaTypeWithQualityHeaderValue(mthv));
            request.Method = method;
            return request;
        }
        private …
Run Code Online (Sandbox Code Playgroud)

asp.net-web-api attributerouting asp.net-web-api-routing

8
推荐指数
1
解决办法
3911
查看次数

路由优先级与属性路由

在较旧的MVC版本中,使用AttributeRouting库,我可以有多个路由并指定优先级,因此在生成URL时选择最合适的路径:

[Route("", ActionPrecedence = 1)]
[Route("city/{citySlug}", ActionPrecedence = 2)]
Run Code Online (Sandbox Code Playgroud)

在MVC 5中,ActionPrecedence属性上没有属性.在这种情况下,如何指定路由优先级?

attributerouting asp.net-mvc-5

8
推荐指数
1
解决办法
5298
查看次数

是否可以在同一个控制器中使用属性路由和基于约定的路由?

我有一个控制器被调用HotelsController来插入和编辑酒店。

它具有以下设置(为简单起见删除了方法实现):

[RoutePrefix("{member_id:int}/hotels")]
public class HotelsController : ApplicationController
{
    [Route("delete/{id:int}", Name = NamedRoutes.HotelDelete)]
    public ActionResult Delete(int id)
    {
    }

    [Route("new", Name = NamedRoutes.HotelNew)]
    public ActionResult New()
    {
    }

    [HttpPost]
    [ValidateInput(false)]
    public ActionResult New(HotelDataEntry hotel)
    {
    }

    [Route("edit/{id:int}", Name = NamedRoutes.HotelEdit)]
    public ActionResult Edit(int id)
    {
    }

    [HttpPost]
    [ValidateInput(false)]
    public ActionResult Edit(HotelDataEntry hotel)
    {
    }
}
Run Code Online (Sandbox Code Playgroud)

如您所见,以下路由使用了属性路由:

  • 删除
  • 新建(无参数)
  • 编辑(不带参数)

以下路由不使用属性路由:

  • 新建(带参数)
  • 编辑(带参数)

路由在 Global.asax.cs 中设置如下:

    public static void RegisterRoutes(RouteCollection routes)
    {
        routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
        routes.IgnoreRoute("{resource}.aspx/{*pathInfo}");
        routes.IgnoreRoute("{resource}.ashx/{*pathInfo}");
        routes.IgnoreRoute("{resource}.asmx/{*pathInfo}");

        routes.MapMvcAttributeRoutes();

        routes.MapRoute(
            Routen.Standard.ToString(), …
Run Code Online (Sandbox Code Playgroud)

c# asp.net asp.net-mvc-routing attributerouting asp.net-mvc-5

7
推荐指数
1
解决办法
1943
查看次数

如何在MVC5中使用自定义属性路由重定向到路由

我不确定我尝试做的是否有效,因为我是C#/ ASP.NET/MVC堆栈的相对新手.

我在ModelController.cs中有这样的控制器动作

//Get
[Route("{vehiclemake}/models", Name = "NiceUrlForVehicleMakeLookup")]
public async Task<ActionResult> Index(string vehicleMake)
{
    // Code removed for readaility

    models = await db.VehicleModels.Where(make => make.VehicleMake.Make == vehicleMake).ToListAsync();

    return View(models);
}
Run Code Online (Sandbox Code Playgroud)

在另一个名为VehicleMakeController.cs的控制器中,我有以下内容:

[HttpPost]
[Route("VehicleMake/AddNiceName/{makeId}")]
public ActionResult AddNiceName(VehicleMake vehicleMake, int? makeId)
{
    if (ModelState.IsValid)
    {
        var vehicle = db.VehicleMakes.Find(makeId);
        vehicle.MakeNiceName = vehicleMake.MakeNiceName;
        db.SaveChanges();
        return RedirectToRoute("NiceUrlForVehicleMakeLookup");
    }
    VehicleMake make = vehicleMake;
    return View(make);
}
Run Code Online (Sandbox Code Playgroud)

我想做的是,当数据库更新成功时,我正在返回的地方,重定向到我定义的自定义路由(此部分: 返回RedirectToRoute("NiceUrlForVehicleMakeLookup");)

我正在使用的观点只是标准观点,这可以实现,还是我需要开始研究部分或区域?

提前致谢

c# asp.net-mvc asp.net-mvc-routing attributerouting asp.net-mvc-5

7
推荐指数
1
解决办法
5612
查看次数

有没有办法让RoutePrefix以可选参数开头?

我想用这些URL到达Bikes控制器:

/bikes     // (default path for US)
/ca/bikes  // (path for Canada)
Run Code Online (Sandbox Code Playgroud)

实现这一目标的一种方法是每个Action使用多个Route Attributes:

[Route("bikes")]
[Route("{country}/bikes")]
public ActionResult Index()
Run Code Online (Sandbox Code Playgroud)

为了保持DRY,我更喜欢使用RoutePrefix,但不允许使用多个Route Prefix:

[RoutePrefix("bikes")]
[RoutePrefix("{country}/bikes")] // <-- Error: Duplicate 'RoutePrefix' attribute    
public class BikesController : BaseController

    [Route("")]
    public ActionResult Index()
Run Code Online (Sandbox Code Playgroud)

我试过使用这个Route Prefix:

[RoutePrefix("{country}/bikes")]
public class BikesController : BaseController
Run Code Online (Sandbox Code Playgroud)

结果:/ ca /​​ bikes工作,/自行车404s.

我试过让国家选择:

[RoutePrefix("{country?}/bikes")]
public class BikesController : BaseController
Run Code Online (Sandbox Code Playgroud)

相同的结果:/ ca /​​ bikes工作,/自行车404s.

我试过给国家一个默认值:

[RoutePrefix("{country=us}/bikes")]
public class BikesController : BaseController
Run Code Online (Sandbox Code Playgroud)

相同的结果:/ ca /​​ bikes工作,/自行车404s.

有没有其他方法可以使用属性路由实现我的目标? (是的,我知道我可以通过在RouteConfig.cs中注册路由来完成这些工作,但这不是我在这里寻找的东西).

我正在使用Microsoft.AspNet.Mvc 5.2.2.

仅供参考:这些是简化示例 - 实际代码具有{country}值的IRouteConstraint,例如:

[Route("{country:countrycode}/bikes")]
Run Code Online (Sandbox Code Playgroud)

asp.net-mvc asp.net-mvc-routing attributerouting

7
推荐指数
1
解决办法
4730
查看次数

多个控制器具有相同的URL路由但不同的HTTP方法

我有以下两个控制器:

[RoutePrefix("/some-resources")
class CreationController : ApiController
{
    [HttpPost, Route]
    public ... CreateResource(CreateData input)
    {
        // ...
    }
}

[RoutePrefix("/some-resources")
class DisplayController : ApiController
{
    [HttpGet, Route]
    public ... ListAllResources()
    {
        // ...
    }

    [HttpGet, Route("{publicKey:guid}"]
    public ... ShowSingleResource(Guid publicKey)
    {
        // ...
    }
}
Run Code Online (Sandbox Code Playgroud)

所有这三个行动实际上都有三条不同的路线:

  • GET /some-resources
  • POST /some-resources
  • GET /some-resources/aaaaa-bbb-ccc-dddd

如果我将它们放入单个控制器中,一切正常,但是如果我将它们分开(如上所示),WebApi会抛出以下异常:

找到了与URL匹配的多种控制器类型.如果多个控制器上的属性路由与请求的URL匹配,则会发生这种情

这个消息很明显.在寻找适合控制器/操作的候选者时,WebApi似乎没有考虑HTTP方法.

我怎样才能实现预期的行为?


更新:我已经深入研究了Web API内部,我明白这是默认情况下的工作方式.我的目标是分离代码和逻辑 - 在现实世界中,这些控制器具有不同的依赖关系并且更复杂一些.为了维护,可测试性,项目组织等,它们应该是不同的对象(SOLID和东西).

我认为我可以覆盖一些WebAPI服务(IControllerSelector等),但这似乎是一个有点风险和非标准的方法,这个简单的 - 和我假设 - 常见的情况.

c# asp.net-web-api attributerouting asp.net-web-api-routing asp.net-web-api2

7
推荐指数
1
解决办法
7178
查看次数

如何在asp.net mvc中向属性路由添加默认参数

我正在尝试改变这个基于约定的路线:

routes.MapRoute(
    "MovieByReleaseDate",
    "movies/released/{year}/{month}",
    new { controller = "Movies", action = "ByReleasedDate" },
);
Run Code Online (Sandbox Code Playgroud)

属性路由:

[Route("movies/released/{year}/{month}")]
Run Code Online (Sandbox Code Playgroud)

但我不知道如何像第一种方式那样定义默认参数。

.net c# asp.net-mvc attributerouting

7
推荐指数
1
解决办法
6278
查看次数

ASP.NET MVC 5 属性路由:Url.Action 返回 null

我在重构我们的支付处理操作方法(由我们的第 3 方在线支付提供商调用)时遇到问题。我们有一个产品控制器,在类级别具有[Authorize][RoutePrefix("products")]属性,以及操作方法,包括以下内容:

  • Product(string contractNumber)具有路由属性[Route("{productCode}")]
  • MakePayment(string productCode, PaymentAmountType? amountSelection, decimal? amountValue)具有路由属性[Route("{productCode}")][HttpPost]属性
  • ProcessPayment(string productCode, string result)具有路由属性[Route("{productCode}")]

由于我们的支付网关需要能够ProcessPayment在访问者重定向到同一 URL 之前调用我们的操作,因此我们必须将其重构为不带该[Authorize]属性的单独控制器。(我们已经有防止重复记入付款的机制。)

在此重构之前,MakePayment操作方法在以下调用中正确地制定了正确的返回 URL Url.Action()

var rawCallbackUrl = Url.Action("ProcessPayment", new { productCode = productCode });
Run Code Online (Sandbox Code Playgroud)

现在,操作ProcessPayment方法已从产品控制器移出并移入新控制器 ,ExternalCallbackController该控制器没有属性(更不用说[Authorize]),以避免将 HTTP 401 响应返回给支付提供商。

现在,路线属性 onProcessPayment[Route("order-processing/{productCode}/process-payment")]为了避免与RoutePrefix产品控制器上的 发生冲突。对此更新的操作方法的所有引用均已更新以指定ExternalCallbackController.

手动浏览到该 URL 会导致内部设置的断点ProcessPayment被命中,因此该路由显然可以成功运行。 …

asp.net routes url-routing attributerouting asp.net-mvc-5

6
推荐指数
1
解决办法
1万
查看次数

分配给一个方法的多个路由,如何确定调用哪个路由?

我目前正在开发一个小型的ASP.NET MVC项目.该项目几个月前发布.但是现在应该针对可用性和SEO原因实施更改.我决定使用属性路由来创建干净的URL.

目前,产品页面通过以下方式调用:

hostname.tld /控制器/ GetArticle/1234

我定义了一个像这样的新Route:

[Route("Shop/Article/{id:int}/{title?}", Name = "GetArticle", Order = 0)]
public ActionResult GetArticle(int id, string title = null) {
    // Logic
}
Run Code Online (Sandbox Code Playgroud)

一切正常,但由于向后兼容性和SEO原因,旧的路线应该仍然可用.并使用HTTP状态代码301重定向到新URL.

我听说可以为一个动作分配多个路径,如下所示:

[Route("Shop/Article/{id:int}/{title?}", Name = "GetArticle", Order = 0)]
[Route("Controller/GetArticle/{id:int}", Name = "GetArticle_Old", Order = 1)]
public ActionResult GetArticle(int id, string title = null) {
    // Logic
}
Run Code Online (Sandbox Code Playgroud)

但我不知道这是一个很好的解决方案,或者如何确定调用哪条路线?

c# asp.net-mvc asp.net-mvc-routing attributerouting

6
推荐指数
2
解决办法
4376
查看次数