简短描述:向数据库添加条目时,模型被标记为无效,但代码调用
return View(order);
属性的验证错误(未填写,带有 Id 的字段已填写):
public Product Product { get; set; }
public Employee Employee { get; set; }
public Customer Customer { get; set; }
查看代码
@using Bakery.Models
@model Bakery.Models.Order
@{
ViewBag.Title = "Добавить заказ";
}
@helper FIOEmployee(List<Employee> empCollection)
{
<select id="EmployeeId" name="EmployeeId">
@foreach (var item in empCollection)
{
<option value="@item.Id">@string.Format("{0} {1} {2} {3}", item.IdentificationNumber, item.Surname, item.Name, item.Patronymic)</option>
}
</select>
}
<h2>Добавить заказ</h2>
@using (Html.BeginForm())
{
@Html.AntiForgeryToken()
<div class="form-horizontal">
<h4>Order</h4>
<hr />
@Html.ValidationSummary(true, "", new { @class = "text-danger" })
<div class="form-group">
@Html.LabelFor(model => model.ProductId, htmlAttributes: new { @class = "control-label col-md-2" })
<div class="col-md-10">
@Html.DropDownListFor(model => model.ProductId, ViewBag.Products as SelectList)
@Html.ValidationMessageFor(model => model.ProductId, "", new { @class = "text-danger" })
</div>
</div>
<div class="form-group">
@Html.LabelFor(model => model.CustomerId, htmlAttributes: new { @class = "control-label col-md-2" })
<div class="col-md-10">
@Html.DropDownListFor(model => model.CustomerId, ViewBag.Customers as SelectList)
@Html.ValidationMessageFor(model => model.CustomerId, "", new { @class = "text-danger" })
</div>
</div>
<div class="form-group">
@Html.LabelFor(model => model.EmployeeId, htmlAttributes: new { @class = "control-label col-md-2" })
<div class="col-md-10">
@FIOEmployee(ViewBag.Employees as List<Employee>)
@Html.ValidationMessageFor(model => model.EmployeeId, "", new { @class = "text-danger" })
</div>
</div>
<div class="form-group">
@Html.LabelFor(model => model.Count, htmlAttributes: new { @class = "control-label col-md-2" })
<div class="col-md-10">
@Html.EditorFor(model => model.Count, new { htmlAttributes = new { @class = "form-control" } })
@Html.ValidationMessageFor(model => model.Count, "", new { @class = "text-danger" })
</div>
</div>
<div class="form-group">
@Html.LabelFor(model => model.Price, htmlAttributes: new { @class = "control-label col-md-2" })
<div class="col-md-10">
@Html.EditorFor(model => model.Price, new { htmlAttributes = new { @class = "form-control" } })
@Html.ValidationMessageFor(model => model.Price, "", new { @class = "text-danger" })
</div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" value="Create" class="btn btn-default" />
</div>
</div>
</div>
}
<div>
@Html.ActionLink("Назад к списку", "Index")
</div>
控制器代码:
using System;
using System.Collections.Generic;
using System.Data;
using System.Data.Entity;
using System.Linq;
using System.Threading.Tasks;
using System.Net;
using System.Web;
using System.Web.Mvc;
using Bakery.Models;
namespace Bakery.Controllers
{
public class OrderController : Controller
{
private BakeryContext db = new BakeryContext();
// GET: Orders
public async Task<ActionResult> Index()
{
var orders = db.Orders.Include(p => p.Product).Include(p => p.Customer).Include(p => p.Employee);
return View(await orders.ToListAsync());
}
// GET: Orders/Create
public ActionResult Create()
{
SelectList products = new SelectList(db.Products, "Id", "Name");
var employees = db.Employees.ToList();
SelectList customers = new SelectList(db.Customers, "Id", "Name");
ViewBag.Products = products;
ViewBag.Employees = employees;
ViewBag.Customers = customers;
return View();
}
// POST: Orders/Create
// To protect from overposting attacks, please enable the specific properties you want to bind to, for
// more details see http://go.microsoft.com/fwlink/?LinkId=317598.
[HttpPost]
[ValidateAntiForgeryToken]
public async Task<ActionResult> Create([Bind(Include = "Id,Product,ProductId,Employee,EmployeeId,Customer,CustomerId,Count,Price")] Order order)
{
SelectList products = new SelectList(db.Products, "Id", "Name");
var employees = db.Employees.ToList();
SelectList customers = new SelectList(db.Customers, "Id", "Name");
ViewBag.Products = products;
ViewBag.Employees = employees;
ViewBag.Customers = customers;
order.Customer = db.Customers.Find(order.CustomerId);
order.Employee = db.Employees.Find(order.EmployeeId);
order.Product = db.Products.Find(order.ProductId);
if (ModelState.IsValid)
{
order.Id = Guid.NewGuid();
db.Orders.Add(order);
await db.SaveChangesAsync();
return RedirectToAction("Index");
}
return View(order);
}
// GET: Orders/Edit/5
public async Task<ActionResult> Edit(Guid? id)
{
if (id == null)
{
return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
}
Order order = await db.Orders.FindAsync(id);
if (order == null)
{
return HttpNotFound();
}
return View(order);
}
// POST: Orders/Edit/5
// To protect from overposting attacks, please enable the specific properties you want to bind to, for
// more details see http://go.microsoft.com/fwlink/?LinkId=317598.
[HttpPost]
[ValidateAntiForgeryToken]
public async Task<ActionResult> Edit([Bind(Include = "Id,Count,Price")] Order order)
{
if (ModelState.IsValid)
{
db.Entry(order).State = EntityState.Modified;
await db.SaveChangesAsync();
return RedirectToAction("Index");
}
return View(order);
}
// GET: Orders/Delete/5
public async Task<ActionResult> Delete(Guid? id)
{
if (id == null)
{
return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
}
Order order = await db.Orders.FindAsync(id);
if (order == null)
{
return HttpNotFound();
}
return View(order);
}
// POST: Orders/Delete/5
[HttpPost, ActionName("Delete")]
[ValidateAntiForgeryToken]
public async Task<ActionResult> DeleteConfirmed(Guid id)
{
Order order = await db.Orders.FindAsync(id);
db.Orders.Remove(order);
await db.SaveChangesAsync();
return RedirectToAction("Index");
}
protected override void Dispose(bool disposing)
{
if (disposing)
{
db.Dispose();
}
base.Dispose(disposing);
}
}
}
型号代码
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
using System.Linq;
using System.Web;
namespace Bakery.Models
{
public class Order
{
public Order()
{
}
public Order(Employee employee, Product product, Customer customer, Double count, Double price)
{
Id = Guid.NewGuid();
Employee = employee;
Product = product;
Customer = customer;
Count = count;
Price = price;
}
/// <summary>
/// Код
/// </summary>
[Key]
public Guid Id { get; set; }
/// <summary>
/// Сотрудник
/// </summary>
[DisplayName("Сотрудник")]
[Required]
public Employee Employee { get; set; }
[System.Web.Mvc.HiddenInput(DisplayValue = false)]
public Guid? EmployeeId { get; set; }
/// <summary>
/// Изделие
/// </summary>
[DisplayName("Изделие")]
[Required]
public Product Product { get; set; }
[System.Web.Mvc.HiddenInput(DisplayValue = false)]
public Guid? ProductId { get; set; }
/// <summary>
/// Заказчик
/// </summary>
[DisplayName("Покупатель")]
[Required]
public Customer Customer { get; set; }
[System.Web.Mvc.HiddenInput(DisplayValue = false)]
public Guid? CustomerId { get; set; }
/// <summary>
/// Количество заказанных изделий
/// </summary>
[DisplayName("Количество изделий (шт.)")]
[Required]
[Range(1, Double.MaxValue, ErrorMessage = "Количество не может быть меньше 1")]
public double Count { get; set; }
/// <summary>
/// Цена
/// </summary>
[DisplayName("Цена (руб.)")]
[Required]
[Range(0.1, Double.MaxValue, ErrorMessage = "Цена не может быть меньше 0.1")]
public double Price { get; set; }
}
}
在 Create 的 Get 方法中,你有这个集合:
但它不在 Post 方法中,我们必须记住,对于每个新请求,模型都是新的,因此必须重新填充员工和产品