将参数从@ Html.ActionLink MVC 4传递给控制器


109

在这一行:

@Html.ActionLink("Reply", "BlogReplyCommentAdd", "Blog",
         new { blogPostId = blogPostId, replyblogPostmodel = Model,
         captchaValid = Model.AddNewComment.DisplayCaptcha })

我在blogPostId上收到以下运行时错误:

参数字典包含方法'System.Web.Mvc.ActionResult BlogReplyCommentAdd(Int32,Nop.Web.Models.Blogs.BlogPostModel,Boolean)'中非空类型'System.Int32'的参数'blogPostId'的空条目'Nop.Web.Controllers.BlogController'。可选参数必须是引用类型,可为空的类型,或者必须声明为可选参数。参数名称:参数

我已经为此分配了一个值,例如

    @{         
        var blogPostId = Model.Id;          
     }

我的控制器:

 public ActionResult BlogReplyCommentAdd(int blogPostId, BlogPostModel model, bool captchaValid)
    {}

难道我做错了什么?请给我一个例子。

Answers:


257

您正在使用错误的Html.ActionLink帮助程序重载。您认为routeValues实际上是htmlAttributes!只需查看生成的HTML,您将看到此锚点的href属性看起来并不像您期望的那样。

这是您正在使用的:

@Html.ActionLink(
    "Reply",                                                  // linkText
    "BlogReplyCommentAdd",                                    // actionName
    "Blog",                                                   // routeValues
    new {                                                     // htmlAttributes
        blogPostId = blogPostId, 
        replyblogPostmodel = Model, 
        captchaValid = Model.AddNewComment.DisplayCaptcha 
    }
)

这是您应该使用的:

@Html.ActionLink(
    "Reply",                                                  // linkText
    "BlogReplyCommentAdd",                                    // actionName
    "Blog",                                                   // controllerName
    new {                                                     // routeValues
        blogPostId = blogPostId, 
        replyblogPostmodel = Model, 
        captchaValid = Model.AddNewComment.DisplayCaptcha 
    },
    null                                                      // htmlAttributes
)

另外,您的代码还有另一个非常严重的问题。以下routeValue:

replyblogPostmodel = Model

您不可能在ActionLink中传递像这样的复杂对象。因此,摆脱它,并BlogPostModel从控制器操作中删除该参数。您应该使用该blogPostId参数从持久化该模型的任何地方检索模型,或者如果希望从GET操作中从检索模型的任何地方检索模型:

public ActionResult BlogReplyCommentAdd(int blogPostId, bool captchaValid)
{
    BlogPostModel model = repository.Get(blogPostId);
    ...
}

至于您最初的问题是关于错误的重载,我建议您使用命名参数编写帮助程序:

@Html.ActionLink(
    linkText: "Reply",
    actionName: "BlogReplyCommentAdd",
    controllerName: "Blog",
    routeValues: new {
        blogPostId = blogPostId, 
        captchaValid = Model.AddNewComment.DisplayCaptcha
    },
    htmlAttributes: null
)

现在,不仅您的代码更具可读性,而且您永远不会对Microsoft为这些助手提供的成千上万的重载感到困惑。


您需要更改注释,controllerName以及actionName
webdeveloper

@DarinDimitrov:如何将模型作为参数传递?
NetraSW

1
@ DarinDimitrov,@ webdeveloper:我需要在actionresult上提及[httppost]吗?
NetraSW

@NetraSW,您不应该[HttpPost]在操作中,因为链接正在发送GET请求。[HttpPost]表示您的控制器操作仅可通过POST请求访问。
Darin Dimitrov

@DarinDimitrov:我怎么能做到这一点?模型将属性值发送为空。请指导我。
NetraSW

12

我必须传递两个参数,例如:

/ Controller / Action / Param1Value / Param2Value

这条路:

@Html.ActionLink(
    linkText,
    actionName,
    controllerName,
    routeValues: new {
        Param1Name= Param1Value, 
        Param2Name = Param2Value 
    },
    htmlAttributes: null
)

会产生这个网址

/ Controller / Action / Param1Value?Param2Name = Param2Value

我通过在参数一中合并参数二来使用一种变通方法,我得到了想要的结果:

@Html.ActionLink(
    linkText,
    actionName,
    controllerName,
    routeValues: new {
        Param1Name= "Param1Value / Param2Value" ,      
    },
    htmlAttributes: null
)

我得到:

/ Controller / Action / Param1Value / Param2Value


显然,这是在Param1Value为null时发生的。我刚遇到同样的问题。
AFract

3

您可以使用以下方法传递值。

@Html.ActionLink("About", "About", "Home",new { name = ViewBag.Name }, htmlAttributes:null )

控制器:

public ActionResult About(string name)
        {
            ViewBag.Message = "Your application description page.";
            ViewBag.NameTransfer = name;
            return View();
        }

URL看起来像

http://localhost:50297/Home/About?name=My%20Name%20is%20Vijay

0

问题必须出在值Model.Id上,该值为空。您可以通过分配一个值来确认,例如

@{         
     var blogPostId = 1;          
 }

如果错误消失了,那么您需要在将其模型ID传递给视图之前确保其模型ID有一个值


1
不,那不是问题。
Darin Dimitrov
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.