显示来自ASP.NET MVC中另一个控制器的视图


248

是否可以显示其他控制器的视图?

比如说我有CategoriesController一个Category/NotFound.aspx观点。在此期间CategoriesController,我可以轻松返回View("NotFound")

现在说我有一个ProductsController和一个动作,然后查看要添加产品。但是,此操作要求我们有一个类别来添加产品。例如,Products/Add/?catid=10

如果找不到基于的类别catid,则我想NotFound从Categories控制器显示视图,而不是CategoryNotFound在Products控制器下创建视图。

这是可能的还是我以错误的方式组织事情?有什么好方法吗?

Answers:


283

是。默认情况下,ASP.NET MVC首先签入\Views\[Controller_Dir]\,但之后,如果找不到视图,则签入\Views\Shared

共享目录专门用于在多个控制器之间共享视图。只需将“视图”添加到“共享”子目录即可。

如果您这样做,则return View("~/Views/Wherever/SomeDir/MyView.aspx")可以返回所需的任何视图。


谢谢,这听起来像是我应该使用的解决方案。我仍然想知道是否可以从另一个控制器显示视图。我猜这违反了MVC中的某些规则?
dtc

1
在上述情况下,可以,您应该使用共享文件夹。
乔纳森·弗里兰德

69
是的,那也是可能的。如果您确实返回View(“〜/ Views / Wherever / SomeDir / MyView.aspx”),则可以返回您想要的任何View。这本身并没有违反任何特定规则,但是,ASP.Net MVC的全部含义是“配置上的约定”。换句话说,该框架是为使用某些约定自动运行而构建的,您应尽可能使用它。
womp

1
感谢您的解释。我不知道Views可以这样称呼。共享目录当然可以完美运行:)
dtc

1
我不在控制器中,所以我不得不使用new ViewResult { ViewName = "~/Views/Error/Unauthorised.cshtml" };它并且起作用了
Nacht-恢复莫妮卡(Monica)

162

您可以使用:

return View("../Category/NotFound", model);

它已在ASP.NET MVC 3中进行了测试,但也应在ASP.NET MVC 2中工作。


3
可在MVC 2中使用,事实证明它是针对我正在处理的异常情况的最干净的解决方案。
Todd Menier

3
Resharper将报告该链接为错误,但仍然可以正常工作。
CodeMonkeyKing 2012年

1
@ CodeMonkeyKing-Resharper 7(在VS2012中)正确标识了格式为的路径"~/Views/Category/NotFound.cshtml"
理查德·伊夫

值得注意的是:此解决方案适用于显示模式,例如,如果您具有“ /Category/NotFound.Mobile.cshtml”视图。
BenWillkommen 2015年

55

是的,它有可能。返回这样的RedirectToAction()方法:

return RedirectToAction("ActionOrViewName", "ControllerName");

1
我认为这应该作为RedirectToAction(“ ActionOrView”,“ Controller”,null),否则第二个参数是routeValues
Zoran P.

但是在这种情况下,与View解决方案不同,您必须在控制器中实际编写操作。
tobbenb3

@ tobbenb3与对结果进行硬编码相比,这是一个更好的解决方案。无论哪种方式,您都不应传递路径字符串。
perustaja

34

你试过了RedirectToAction吗?


1
我想说的是,这是不希望在共享文件夹中查看视图的任何人的MVC,请注意,对于所有其他解决方案(例如使用直接路径),任何试图重构视图的人都不必记住它也在另一个控制器中使用,导致无法预测的行为
yoel halb 2012年

4
没有重定向怎么办?
Luckyy

比将视图移动到共享文件夹更好的解决方案
juFo 2014年

此解决方案需要对控制器执行操作,View(directPath)无需任何操作即可呈现输出。添加动作时,您需要考虑将其隐藏起来,使其无法通过url直接访问,这会在浏览器历史记录等中生成步骤。但是,是的,这是我的方法。
2014年

3
RedirectToAction将302响应代码发送到浏览器。当您尝试显示“ 404未找到”页面时,这是不合适的。也就是说,此解决方案似乎可以工作,但会使搜索引擎感到困惑。
NightOwl888

20

是的你可以。返回一个这样的动作:

return RedirectToAction("View", "Name of Controller");

一个例子:

return RedirectToAction("Details/" + id.ToString(), "FullTimeEmployees");

这种方法将调用GET方法

您也可以像这样将值传递给操作:

return RedirectToAction("Details/" + id.ToString(), "FullTimeEmployees", new {id = id.ToString(), viewtype = "extended" });

我将如何使用这种方法发送对象?
Djeroen '16

看看@Djeroen
ignacio chiazzo

5
您没有返回视图,而是在调用操作。
0014

最重要的是对我有帮助。
anil shrestha

5

您还可以从JavaScript / jQuery调用任何控制器。假设您有一个返回404或其他用户控件/页面的控制器。然后,从客户端代码执行一些操作,您可以调用一些地址,该地址将触发您的控制器并以HTML格式返回结果,您的客户端代码可以将返回的结果放入您想要放置在页面中的任何位置...


我不知道。听起来这是我将来可能会用到的东西。是的,MVC岩石:)
DTC

1

通过此代码,您可以获得任何控制器:

var controller = DependencyResolver.Current.GetService<ControllerB>();
controller.ControllerContext = new ControllerContext(this.Request.RequestContext, 
controller);

翻译:使用此代码,您可以获得任何控制器:[代码],问候,
Robert Columbia

3
尽管此代码可以回答问题,但提供有关如何和/或为什么解决问题的其他上下文将提高​​答案的长期价值。
Nic3500 '18
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.