如何在辅助视图中使用 HtmlHelper 扩展
How to use HtmlHelper extensions in helper views
我想创建一个 Razor 助手来减少我需要编写的代码量。我在我的项目中添加了一个 App_Code 文件夹并添加了一个名为 MyHelpers.cshtml 的文件,其中包含以下内容(用于说明目的的简单示例)...
@using System.Web.Mvc
@using System.Web.Mvc.Html
@helper HomeLink() {
@Html.ActionLink("Home", "Index", "Home")
}
但是,这给出了一个编译器异常,表示 Html.ActionLink 没有一个需要三个字符串的重载。 ActionLink 代码是从 Razor 页面复制的,它工作正常。当我尝试在我自己的助手中使用任何其他标准助手时,我遇到了类似的问题。
如果我尝试使用 Telerik 的 KendoUI 的 MVC 包装器,它们被引用为 @Html.Kendo.ComboBox... 然后我在 Html 下得到一条红线,其中包含一条消息 "Cannot convert instance type System.Web.WebPages.Html.HtmlHelper to System.Web.Mvc.HtmlHelper"
根据本博客末尾的说明 post,这是 MVC3 的一个已知问题,但应该在下一个版本中添加...
http://weblogs.asp.net/scottgu/asp-net-mvc-3-and-the-helper-syntax-within-razor
根据此 UserVoice 页面,该问题实际上已在 VS2013 中修复...
我在一个全新的 MVC5 项目中使用 VS2013 Update 4,但似乎无法正常工作。我已经尝试了很多在这里找到的解决方法,但 none 有所帮助。
有人有什么想法吗?
呃。视野内的帮手是可憎的。微软甚至不应该创造这种可能性。做这样的事情的真正方法是创建扩展或使用部分。
分机
public static class HtmlHelperExtensions
{
public static MvcHtmlString HomeLink(this HtmlHelper helper, string linkText = "Home")
{
return helper.ActionLink(linkText, "Index", "Home");
}
}
那么,在你看来:
@Html.HomeLink()
或
@Html.HomeLink("This is my awesome Home link.")
部分
在Views\Shared\_HomeLink.cshtml
中:
@Html.ActionLink("Home", "Index", "Home")
那么在你看来:
@Html.Partial("_HomeLink")
此方法允许覆盖。例如,假设您希望主页 link 转到您网站商店部分的 "homepage" 商店部分内的视图,您可以添加一个新的局部视图,Views\Store\_HomeLink.cshtml
:
@Html.ActionLink("Home", "Index", "Store")
对于 Views\Store
中的任何视图,此视图将优先于 Views\Shared
中的视图。
但是,对于这样的事情,这两种方法都太过分了。不要过分追求 DRY。您可以使用行号作为粗略指南。如果您的抽象与要抽象的代码一样多行,那么您应该非常 仔细看看它是否值得。抽象的代码可能会改变吗?它有复杂的逻辑吗?调用 Html.ActionLink
之类的东西非常简单,并且不太可能通过将其抽象化来提供任何真正的投资回报率。
测试是查看此问题的另一种方式,因为 DRY 的目的实际上是减少需要测试的代码量。从这个角度来看,Html.ActionLink
已经由 Microsoft 进行了全面测试。除了完全破坏方法签名(Intellisense 会立即警告您)之外,您无法真正破坏它。但是,通过创建辅助程序、部分程序等,您现在 引入了 复杂性。这是新代码,可能由于多种原因而失败。如果您的抽象引入了原本不需要的复杂性和新测试。然后,再一次,你应该退后一步,真正考虑一下是否值得。
我想创建一个 Razor 助手来减少我需要编写的代码量。我在我的项目中添加了一个 App_Code 文件夹并添加了一个名为 MyHelpers.cshtml 的文件,其中包含以下内容(用于说明目的的简单示例)...
@using System.Web.Mvc
@using System.Web.Mvc.Html
@helper HomeLink() {
@Html.ActionLink("Home", "Index", "Home")
}
但是,这给出了一个编译器异常,表示 Html.ActionLink 没有一个需要三个字符串的重载。 ActionLink 代码是从 Razor 页面复制的,它工作正常。当我尝试在我自己的助手中使用任何其他标准助手时,我遇到了类似的问题。
如果我尝试使用 Telerik 的 KendoUI 的 MVC 包装器,它们被引用为 @Html.Kendo.ComboBox... 然后我在 Html 下得到一条红线,其中包含一条消息 "Cannot convert instance type System.Web.WebPages.Html.HtmlHelper to System.Web.Mvc.HtmlHelper"
根据本博客末尾的说明 post,这是 MVC3 的一个已知问题,但应该在下一个版本中添加...
http://weblogs.asp.net/scottgu/asp-net-mvc-3-and-the-helper-syntax-within-razor
根据此 UserVoice 页面,该问题实际上已在 VS2013 中修复...
我在一个全新的 MVC5 项目中使用 VS2013 Update 4,但似乎无法正常工作。我已经尝试了很多在这里找到的解决方法,但 none 有所帮助。
有人有什么想法吗?
呃。视野内的帮手是可憎的。微软甚至不应该创造这种可能性。做这样的事情的真正方法是创建扩展或使用部分。
分机
public static class HtmlHelperExtensions
{
public static MvcHtmlString HomeLink(this HtmlHelper helper, string linkText = "Home")
{
return helper.ActionLink(linkText, "Index", "Home");
}
}
那么,在你看来:
@Html.HomeLink()
或
@Html.HomeLink("This is my awesome Home link.")
部分
在Views\Shared\_HomeLink.cshtml
中:
@Html.ActionLink("Home", "Index", "Home")
那么在你看来:
@Html.Partial("_HomeLink")
此方法允许覆盖。例如,假设您希望主页 link 转到您网站商店部分的 "homepage" 商店部分内的视图,您可以添加一个新的局部视图,Views\Store\_HomeLink.cshtml
:
@Html.ActionLink("Home", "Index", "Store")
对于 Views\Store
中的任何视图,此视图将优先于 Views\Shared
中的视图。
但是,对于这样的事情,这两种方法都太过分了。不要过分追求 DRY。您可以使用行号作为粗略指南。如果您的抽象与要抽象的代码一样多行,那么您应该非常 仔细看看它是否值得。抽象的代码可能会改变吗?它有复杂的逻辑吗?调用 Html.ActionLink
之类的东西非常简单,并且不太可能通过将其抽象化来提供任何真正的投资回报率。
测试是查看此问题的另一种方式,因为 DRY 的目的实际上是减少需要测试的代码量。从这个角度来看,Html.ActionLink
已经由 Microsoft 进行了全面测试。除了完全破坏方法签名(Intellisense 会立即警告您)之外,您无法真正破坏它。但是,通过创建辅助程序、部分程序等,您现在 引入了 复杂性。这是新代码,可能由于多种原因而失败。如果您的抽象引入了原本不需要的复杂性和新测试。然后,再一次,你应该退后一步,真正考虑一下是否值得。