【问题标题】:Form not submitting and no error is being produced with MVC表单未提交且 MVC 未产生错误
【发布时间】:2009-09-25 13:20:42
【问题描述】:

我的 MVC 应用程序中有一个表单,理论上应该使用 Repository 类将数据提交回我的数据库。

但是,当我提交表单 (http://localhost:1028/Admin/NewUser/) 时,URL 会更改为表单应提交到的位置,这很好 (http://localhost:1028/Admin/NewUser/Submit) ,但一旦提交,它应该将用户发送到确认页面。

据我所知,我正在正确浏览所有页面,直到提交,它再次显示表单但在 /Admin/NewUser/Submit 下,数据是没有插入到数据库中。

这是我正在使用的 ActionResult:

Public Function Submit() As ActionResult
         Try
            Dim user = New hdUser() With { _
                .userLogon = Request.Form("UserLogin"), _
                .userPass = Request.Form("UserPassword"), _
                .userEmail = Request.Form("UserEmail"), _
                .RealName = Request.Form("UserFullName"), _
                .isLive = 1, _
                .avatar = "noavatar.gif" _
             }
            userRepository.Add(user)
            userRepository.Save()

            Return Redirect("/Admin/NewUser/Confirm")
        Catch ex As Exception
            ModelState.AddModelError("Error", ex)
        End Try
        Return View()
    End Function

我对 MVC 还很陌生,所以我不完全确定上述内容是否正确。

在我的数据存储库类UserRepository.vb中,我使用的两个函数是:

Public Sub Add(ByVal user As hdUser) Implements IUserRepository.Add
            db.hdUsers.InsertOnSubmit(user)
        End Sub

Public Sub Save() Implements IUserRepository.Save
            db.SubmitChanges()
        End Sub

我创建的表格是:

<form action="/Admin/NewUser/Submit" method="post">
                <table border="0" cellpadding="0" cellspacing="2">
                    <tr>
                        <td><strong>User's Full Name</strong> <br />
                         <%=Html.TextBox("UserFullName")%>
                            </td>
                    </tr>
                    <tr>
                        <td><strong>User Login</strong> <br />
                         <%=Html.TextBox("UserLogin")%>
                            </td>
                    </tr>
                    <tr>
                        <td><strong>Password</strong> <br />
                         <%=Html.Password("UserPassword")%>
                           </td>
                    </tr>
                    <tr>
                        <td><strong>Email Address</strong> <br />
                         <%=Html.TextBox("UserEmail")%>
                         </td>
                    </tr>
                    <tr>
                        <td align="right"><input type="submit" value="Create" /></td>
                    </tr>
                </table>
        </form>

代码没有产生任何错误,但似乎也没有提交到数据库。所以我不完全确定我哪里出错了。

对于更有经验的人来说可能很明显,但我真的不知道这一点。

这是我的代码导致问题还是其他错误?

提前感谢您的帮助。


编辑:根据 Zhaph - Ben Duguid 的评论,我做了以下编辑:

AdminController.vb

<AcceptVerbs(HttpVerbs.Post)> _
    Public Function NewUser(ByVal formValues As FormCollection) As ActionResult
        Try
            Dim user = New hdUser()
            user.userLogon = Request.Form("UserLogin")
            user.userPass = Request.Form("UserPassword")
            user.userEmail = Request.Form("UserEmail")
            user.RealName = Request.Form("UserFullName")
            user.isLive = 1
            user.avatar = "noavatar.gif"
            UpdateModel(user)
            userRepository.Add(user)
            userRepository.Save()
        Catch ex As Exception
            ModelState.AddModelError("Error", ex)
        End Try
        Return View()
    End Function

NewUser.aspx

<%Html.BeginForm()%>
            <%=Html.ValidationMessage("Error")%>
                  <table border="0" cellpadding="0" cellspacing="2">
                    <tr>
                        <td><strong>User's Full Name</strong> <br />
                         <%=Html.TextBox("UserFullName")%>
                            <%=Html.ValidationMessage("Name", "*")%></td>
                    </tr>
                    <tr>
                        <td><strong>User Login</strong> <br />
                         <%=Html.TextBox("UserLogin")%>
                            <%=Html.ValidationMessage("Username", "*")%></td>
                    </tr>
                    <tr>
                        <td><strong>Password</strong> <br />
                         <%=Html.Password("UserPassword")%>
                            <%=Html.ValidationMessage("Password", "*")%></td>
                    </tr>
                    <tr>
                        <td><strong>Email Address</strong> <br />
                         <%=Html.TextBox("UserEmail")%>
                         <%=Html.ValidationMessage("Email", "*")%></td>
                    </tr>
                    <tr>
                        <td align="right"><input type="submit" value="Create" /></td>
                    </tr>
                </table>
                <% Html.EndForm() %>

现在会产生 值 '' 无效。 对我来说。

这是否意味着表单值没有正确传递给控制器​​?


编辑:我已经进行了这些编辑以响应 Zhaph - Ben Duguid 的编辑,并且我已将表单元素更改为数据库字段名称(至少用于测试)。现在,当页面提交时,名称、登录名和电子邮件都已填写,密码为空(我假设这是密码框的预期行为)但我仍然收到 “值''无效” 错误。

【问题讨论】:

  • 你从哪里得到错误?你能发布一个堆栈跟踪吗?
  • 因为我不在办公室,所以要等到星期一才行。
  • 没问题,我会保留;)

标签: asp.net-mvc vb.net form-submit


【解决方案1】:

Response.Write 在你的控制器中不会对视图做任何事情。

您应该将模型返回到编辑页面,其中包含任何错误

ModelState.AddModelError();

Professional ASP.NET MVC 书籍的NerdDinner Chapter 中有一个很好的示例,说明了如何实现存储库模式,并利用 ASP.NET MVC 模型绑定功能等。

我有一个基于 Nerd Dinner 示例的示例控制器(恐怕是在 c# 中):

//
// POST: /AdminAlbums/Create

[AcceptVerbs(HttpVerbs.Post)]
public ActionResult Create(FormCollection collection)
{
  var album = new Album();

  // Method on System.Web.Mvc.Controller, that takes a form collection, and
  // using reflection on the Model, assigns values to it from the form.
  UpdateModel(album);

  if (album.IsValid)
  {
    // These methods are the same as yours
    m_PhotoRepository.Add(album);
    m_PhotoRepository.Save();

    // In this instance, I'm returning the user to a list view of Albums
    // for editing, probably ought to send them to the page to start 
    // uploading photos.
    return RedirectToAction("Index");
  }

  // Still here, so I'm going to set up some ViewData I need.
  ViewData["Title"] = "Create a new album";
  ViewData["Message"] = "Create Album";

  // I'm picking up errors from the model here.
  // RuleViolation is my own class, implemented in a partial on Album.
  foreach (RuleViolation violation in album.GetRuleViolations())
  {
    ModelState.AddModelError(violation.PropertyName, violation.ErrorMessage);
  }

  return View(album);
}

所以您可以看到,如果出现错误,我会将模型返回到主视图,以填充验证摘要。

视图的相关部分是:

<%= Html.ValidationSummary("Edit was unsuccessful. Please correct the errors and try again.") %>
<% using (Html.BeginForm()) {%>
  <fieldset>
    <legend>Album details</legend>
    <div class="form_row">
      <label for="Caption" class="left_label">Album caption:</label>
      <%= Html.TextBox("Caption", Model.Caption, new { @class = "textbox" })%>
      <%= Html.ValidationMessage("Caption", "*") %>
      <div class="cleaner">&nbsp;</div>
    </div>
    <div class="form_row">
      <label for="IsPublic" class="left_label">Is this album public:</label>
      <%= Html.CheckBox("IsPublic", Model.IsPublic) %>
    </div>
    <div class="form_row">
      <input type="submit" value="Save" />
    </div>
  </fieldset>
<% } %>

根据问题编辑进行编辑

对不起,我应该澄清一下:

其中很多都是基于使用 ASP.NET MVC 框架提供的 Helper 方法 - 你会注意到我使用像 Html.TextBox 这样的方法来生成我的字段,它们的名称/ID 从模型本身。这样,如果我在 ModelState 中加载带有 ModelErrors 的视图,帮助程序会将相关详细信息添加到呈现的 HTML 以包含以下标记

<label for="Caption" class="left_label">Caption:</label>
<input class="input-validation-error textbox" 
       id="Caption" name="Caption" type="text" value="" />
<span class="field-validation-error">*</span>

您可以选择的另一个选项是将消息添加到 ViewData 集合,如果它有值,则将其显示在您的视图中。


根据问题编辑进行编辑

需要记住的几点:

1) Form 元素和 Validation 控件的标识符应该相同:

<%= Html.TextBox("Caption", Model.Caption, new { @class = "textbox" })%>
<%= Html.ValidationMessage("Caption", "*") %>

(你有“UserEmail”和“Email”之类的东西)

2) 您应该在出错时将 hdUser 返回到视图 - 所以请尝试以下操作:

<AcceptVerbs(HttpVerbs.Post)> _
Public Function NewUser(ByVal formValues As FormCollection) As ActionResult
  Dim user = New hdUser()
  Try
    UpdateModel(user)
    user.isLive = 1
    user.avatar = "noavatar.gif"

    userRepository.Add(user)
    userRepository.Save()
  Catch ex As Exception
      ModelState.AddModelError("Error", ex)
  End Try
  Return View(user)
End Function

【讨论】:

  • 我已根据您评论的最新版本进行了编辑。
  • 表单元素的名称是否应该与数据库字段相同?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2016-06-25
  • 1970-01-01
  • 2022-01-07
  • 2015-05-07
  • 2015-07-19
  • 1970-01-01
  • 2014-03-13
相关资源
最近更新 更多