MVC 5属性路由 - 默认操作不在模板中

时间:2013-11-21 15:19:19

标签: asp.net-mvc attributerouting

我正在尝试在MVC 5中设置属性路由。我有一个默认操作的路由,但操作根本不在我的模板中。这是我的旧路线。

routes.MapRoute(null,
    "Article/{id}/{*path}",
    new { controller = "Article", action = "Index" , id = UrlParameter.Optional, path = UrlParameter.Optional }
  );

这将满足/ Articles / 1 / test的路线,而不必使用路径中的操作索引(即/ Articles / Index / 1 / test)。

我还有另一种方法,它将被默认的地图路线.... / Article / Items捕获。

我的问题是我无法弄清楚如何使用MVC 5中的新属性路由来设置此路由。以下代码类型有效,但我不想为每个方法添加路由。我希望在类的顶部添加一些能满足所有方法的东西,我只是在我的Index方法中添加其他内容。

[RoutePrefix("Article")]
public class ArticleController: BaseController
{
  [Route("{id?}/{*path?}")]
  public ActionResult Index(int id, string path)
  {

  }

  [Route("Items")]
  public ActionResult Items()
  {

  }

  [Route("TestMethod")]
  public ActionResult TestMethod()
  {

  }
}

我希望得到类似下面的内容。问题是我被迫把索引放在我的路径前面,就像这样... / Index / 1 / test。

[RoutePrefix("Article")]
[Route("{action=Index}")]
public class ArticleController : BaseController
{
  Route[("{id?}/{*path?}")]
  public ActionResult Index(int id, string path)
  {

  }

  public ActionResult Articles()
  {

  }

  public ActionResult TestMethod() 
  {

  }
}

1 个答案:

答案 0 :(得分:2)

以下是您可以实现上述方案的方法。 (您可以在代码中找到我的评论,这些评论描述了可能触及操作的网址。)

请注意,我对'id'路由变量使用了内联约束int。这是因为我们要确保路线'Article / {id?} / {* path}'不会捕获像'Article / TestMethod'这样的请求。理想情况下,您希望在属性路由上有一个Order属性来命令它们以避免上述情况,但我们在最后一刻删除了它,没有时间将其添加回来,因为我们希望确保正确执行就所有情况而言。 (实际上,您应该在预属性路由更改时遇到类似的问题...您能分享您的预属性路由配置的样子吗?)

我们默认订购我们将大多数特定路线放在通用路线之前的路线。所以在当前的情况下,由于一条路线'Article / {id:int?} / {* path}'有一个约束,它将放在通用路线'Article / {action}'之前,这就是它工作的原因目前。

在我们的下一个版本中,我们将重新引入Order属性,这可以为您提供更多灵活性。

[RoutePrefix("Article")]
[Route("{action}")]
public class ArticleController : Controller
{
    // GET /Article
    // GET /Article/10
    // GET /Article/10/abc/def
    [Route("{id:int?}/{*path}")]
    public ActionResult Index(int? id, string path)
    {
        return Content("Index:" + id + ":" + path);
    }

    // GET /Article/Articles
    public ActionResult Articles()
    {
        return Content("Articles");
    }

    // GET /Article/TestMethod
    public ActionResult TestMethod()
    {
        return Content("TestMethod");
    }
}