aspnet / Mvc

[Archived] ASP.NET Core MVC is a model view controller framework for building dynamic web sites with clean separation of concerns, including the merged MVC, Web API, and Web Pages w/ Razor. Project moved to https://github.com/aspnet/AspNetCore
Apache License 2.0
5.62k stars 2.14k forks source link

<form> tag helper not work for Area that the view file not in Areas folder #8720

Closed yqszt closed 5 years ago

yqszt commented 5 years ago

Is this a Bug or Feature request?:

Bug

Steps to reproduce (preferably a link to a GitHub repo with a repro project):

Description of the problem:

i have a controller and view not in areas folder, but i apply a Area attribute in the controller, like this: [Area("Manage")] public class GroupController : Controller when i create a form using tag-helper in this view:

<form asp-controller="Group" asp-area="Manage" asp-action="Create" method="post" class="form-horizontal" id="addForm">

=>>

<form method="post" class="form-horizontal" id="addForm" action="/Group/Create?area=Manage"> the area will in query string. and the url can't match route.

so how can i make it work.

BTW, if the controller and view in the areas folder, it will be working fine. is this a bug?

Version of Microsoft.AspNetCore.Mvc or Microsoft.AspNetCore.App or Microsoft.AspNetCore.All:

Microsoft.AspNetCore.Mvc: 2.1.1

mkArtakMSFT commented 5 years ago

Thanks for contacting us, @yqszt. @NTaylorMullen, can you please look into this? Thanks!

NTaylorMullen commented 5 years ago

@yqszt you should be able to do that. Have you added an area route in your Startup? I.e.:

routes.MapRoute(
    name: "areaRoute",
    template: "{area:exists}/{controller=Home}/{action=Index}/{id?}");
yqszt commented 5 years ago

@NTaylorMullen i created a demo here: https://github.com/yqszt/AreaDemo.git. it still has is issue. you can run this demo and access http://localhost:5000/manage/group/create, the page has a <form> tag, and the tag's action attribute still is "/Group/Create?area=Manage"

poke commented 5 years ago

As per the documentation, you need to have the route mappings in the following order:

routes.MapRoute(
    name: "default_area",
    template: "{area:exists}/{controller=Home}/{action=Index}/{id?}");
routes.MapRoute(
    name: "default",
    template: "{controller=Home}/{action=Index}/{id?}");

That way, routes that do have an area will pick the default_are one, while the other ones will pick the default mapping. If you have the order reversed, then routes that include an area will still pick the default one since that is also a valid match for the route parameters (that’s because controller, action and area are internally passed as normal route parameters).

yqszt commented 5 years ago

Thanks a lot for your answer. @poke I'm clear for the link generation now, and solved my issue. ;)