如何将主 ID 传递给详细外键?
How do I pass master id to detail foreign key?
我有一个主从编辑没有按预期工作。
TaBarHeader
- master 和 TaBarBody
- detail,一对多关系:
public partial class TaBarHeader
{
[Key]
public int Id { get; set; }
public string ListaOtf { get; set; }
public IEnumerable<TaBarBody> TaBarBodies { get; set; }
public IEnumerable<TaBarTelegrama> TaBarTelegramas { get; set; }
}
public partial class TaBarBody
{
[Key]
public int Id { get; set; }
public string Codstatie1 { get; set; }
public int BarHeaderId { get; set; }
[ForeignKey("BarHeaderId")]
public TaBarHeader BarHeaderFk { get; set; }
}
HeaderTelegrama/Details.cshtml
:
@model TraficAlert.Models.ViewModels.HeaderTelegramaViewModel
<dt class="col-sm-2">
@Html.DisplayNameFor(model => model.TaBarHeader.ListaOtf)
</dt>
<dd class="col-sm-10">
@Html.DisplayFor(model => model.TaBarHeader.ListaOtf)
</dd>
(...)
<th>
@Html.DisplayNameFor(model => model.TaBarBody.Codstatie1)
</th>
@foreach (var item in Model.TaBarHeader.TaBarBodies)
{
<tr>
<td>
@Html.DisplayFor(modelItem => item.Codstatie1)
</td>
<a asp-controller="BodyTelegrama" asp-action="Edit" asp-route-id="@item.Id">Edit</a>
BodyTelegrama/Edit.cshtml
:
@model TraficAlert.Models.ViewModels.BodyTelegramaViewModel
@{
ViewData["Title"] = "Edit";
}
<h1>Edit</h1>
<h4>TaBarBody</h4>
<hr />
<div class="row">
<div class="col-md-4">
<form asp-action="Edit">
<div asp-validation-summary="ModelOnly" class="text-danger"></div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.Codstatie1" class="control-label">Cod Statie 1</label>
<input asp-for="@Model.TaBarBody.Codstatie1" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.Codstatie1" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.Codstatie2" class="control-label">Cod Statie 2</label>
<input asp-for="@Model.TaBarBody.Codstatie2" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.Codstatie2" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.DtIniP" class="control-label">Data Ini P</label>
<input asp-for="@Model.TaBarBody.DtIniP" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.DtIniP" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.DtFinP" class="control-label">Data Fin P</label>
<input asp-for="@Model.TaBarBody.DtFinP" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.DtFinP" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.DtIniR" class="control-label">Data Ini R</label>
<input asp-for="@Model.TaBarBody.DtIniR" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.DtFinP" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.DtFinR" class="control-label">Data Fin R</label>
<input asp-for="@Model.TaBarBody.DtFinR" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.DtFinR" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.KmIni" class="control-label">Km Ini</label>
<input asp-for="@Model.TaBarBody.KmIni" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.KmIni" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.KmFin" class="control-label">Km Fin</label>
<input asp-for="@Model.TaBarBody.KmFin" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.KmFin" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.LiniaFir" class="control-label">Linia Fir</label>
<input asp-for="@Model.TaBarBody.LiniaFir" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.LiniaFir" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.NomImpactId" class="control-label">Impact</label>
<select asp-for="@Model.TaBarBody.NomImpactId" class="form-control" asp-items="ViewBag.NomImpactId"></select>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.NomAnulatId" class="control-label">Anulat</label>
<select asp-for="@Model.TaBarBody.NomAnulatId" class="form-control" asp-items="ViewBag.NomAnulatId"></select>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.MotivAnulare" class="control-label">Motiv Anulare</label>
<input asp-for="@Model.TaBarBody.MotivAnulare" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.MotivAnulare" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.Ruta" class="control-label">Ruta</label>
<input asp-for="@Model.TaBarBody.Ruta" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.Ruta" class="text-danger"></span>
</div>
<div class="form-group">
<input type="submit" asp-route-id="@ViewBag.TelegramaId" value="Save" />
</div>
</form>
</div>
</div>
<div>
<a asp-action="Index">Back to List</a>
</div>
BodyTelegramaController
:
// GET
public IActionResult Edit(int id, int HeaderTelegramaId)
{
BodyTelegramaViewModel bodyTelegramaViewModel = new BodyTelegramaViewModel();
bodyTelegramaViewModel.TaBarBody = new TaBarBody();
bodyTelegramaViewModel.TaBarBody.BarHeaderFk = new TaBarHeader();
bodyTelegramaViewModel.TaBarBody = _unitofwork.BarBody.DetailsBarB(id);
bodyTelegramaViewModel.TaBarBody.BarHeaderFk = _unitofwork.BarHeader.DetailsBarHB(id);
ViewData["TelegramaId"] = HeaderTelegramaId;
if (bodyTelegramaViewModel.TaBarBody == null)
{
return NotFound();
}
ViewData["NomImpactId"] = new SelectList(_unitofwork.NomImpact.GetAll(), "Id", "Nume");
ViewData["NomAnulatId"] = new SelectList(_unitofwork.NomAnulat.GetAll(), "Id", "Nume");
return View(bodyTelegramaViewModel);
}
// POST
public IActionResult Edit(int id, BodyTelegramaViewModel bodyTelegramaViewModel)
{
if (id != bodyTelegramaViewModel.TaBarBody.Id)
{
return NotFound();
}
if (ModelState.IsValid)
{
try
{
bodyTelegramaViewModel.TaBarBody.BarHeaderId = id;
_unitofwork.BarBody.Update(bodyTelegramaViewModel.TaBarBody);
_unitofwork.Save();
}
catch (DbUpdateConcurrencyException)
{
if (!TaBarBodyExists(bodyTelegramaViewModel.TaBarBody.Id))
{
return NotFound();
}
else
{
throw;
}
}
return RedirectToAction("Index");
}
return View(bodyTelegramaViewModel);
}
每次我编辑记录时,我的外键 - BarHeaderId - 将其值更改为 0。
我试过 bodyTelegramaViewModel.TaBarBody.BarHeaderId = bodyTelegramaViewModel.TaBarHeader.Id;
但我收到错误 'Object reference not set to an instance of an object.'
如何获取 TaBarHeader.Id
值并将其放入 TaBarBody.BarHeaderId
?
更新:
视图模型:
public class HeaderTelegramaViewModel
{
public TaBarHeader TaBarHeader { get; set; }
public IEnumerable<TaBarHeader> taBarHeader { get; set; }
public TaBarBody TaBarBody { get; set; }
public IEnumerable<TaBarBody> taBarBody { get; set; }
}
public class BodyTelegramaViewModel
{
public TaBarBody TaBarBody { get; set; }
public IEnumerable<TaBarBody> taBarBody { get; set; }
}
HeaderTelegramaController:
public IActionResult Details(int id)
{
HeaderTelegramaViewModel headerTelegramaViewModel = new HeaderTelegramaViewModel();
headerTelegramaViewModel.TaBarHeader = _unitofwork.BarHeaderRepository.DetailsBarHB(id);
if (headerTelegramaViewModel == null)
{
return NotFound();
}
return View(headerTelegramaViewModel);
}
BodyTelegramaController:
// GET
public IActionResult Edit(int id)
{
BodyTelegramaViewModel bodyTelegramaViewModel = new BodyTelegramaViewModel();
bodyTelegramaViewModel.TaBarBody = new TaBarBody();
bodyTelegramaViewModel.TaBarBody.BarHeaderFk = new TaBarHeader();
bodyTelegramaViewModel.TaBarBody = _unitofwork.BarBodyRepository.DetailsBarB(id);
bodyTelegramaViewModel.TaBarBody.BarHeaderFk = _unitofwork.BarHeaderRepository.DetailsBarHB(id);
return View(bodyTelegramaViewModel);
}
这些是方法 DetailsBarB()
和 DetailsBarHB()
:
public TaBarBody DetailsBarB(int id)
{
return _db.TaBarBodies
.Include(t => t.BarHeaderFk)
.FirstOrDefault(m => m.Id == id);
}
public TaBarHeader DetailsBarHB(int id)
{
return _db.TaBarHeaders
.Include(x => x.TaBarBodies).ThenInclude(x => x.BarHeaderFk.CategoriaFk)
.FirstOrDefault(m => m.Id == id);
}
您可以进行以下更改以获取 TaBarHeader
ID。
在您的 Details View
中,将其更改为:
<a asp-controller="BodyTelegrama" asp-action="Edit" asp-route-id="@item.Id" asp-route-HeaderTelegramaId="@Model.TaBarHeader.Id">Edit</a>
在您的 Edit
操作中,将其更改为:
public IActionResult Edit(int id,int HeaderTelegramaId)
{
BodyTelegramaViewModel bodyTelegramaViewModel = new BodyTelegramaViewModel();
bodyTelegramaViewModel.TaBarBody = new TaBarBody();
bodyTelegramaViewModel.TaBarBody.BarHeaderFk = new TaBarHeader();
bodyTelegramaViewModel.TaBarBody = _unitofwork.BarBodyRepository.DetailsBarB(id);
bodyTelegramaViewModel.TaBarBody.BarHeaderFk = _unitofwork.BarHeaderRepository.DetailsBarHB(id);
ViewData["TelegramaId"] = HeaderTelegramaId;
return View(bodyTelegramaViewModel);
}
[HttpPost]
public IActionResult Edit(int id, BodyTelegramaViewModel bodyTelegramaViewModel)
{
bodyTelegramaViewModel.TaBarBody.BarHeaderId = id;
_unitofwork.BarBodyRepository.Update(bodyTelegramaViewModel.TaBarBody);
_unitofwork.Save();
return View(bodyTelegramaViewModel);
}
然后在您的 Edit View
中将其更改为:
<form asp-action="Edit">
<div asp-validation-summary="ModelOnly" class="text-danger"></div>
<div class="form-group">
<input type="hidden" asp-for="@Model.TaBarBody.Id" />
<label asp-for="@Model.TaBarBody.Codstatie1" class="control-label">Cod Statie 1</label>
<input asp-for="@Model.TaBarBody.Codstatie1" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.Codstatie1" class="text-danger"></span>
</div>
<div>
<input type="submit" asp-route-id="@ViewBag.TelegramaId" value="Save"/>
</div>
</form>
然后在你的 Edit
post 操作中,id
将是 TaBarHeader.Id
。
测试结果:
我有一个主从编辑没有按预期工作。
TaBarHeader
- master 和 TaBarBody
- detail,一对多关系:
public partial class TaBarHeader
{
[Key]
public int Id { get; set; }
public string ListaOtf { get; set; }
public IEnumerable<TaBarBody> TaBarBodies { get; set; }
public IEnumerable<TaBarTelegrama> TaBarTelegramas { get; set; }
}
public partial class TaBarBody
{
[Key]
public int Id { get; set; }
public string Codstatie1 { get; set; }
public int BarHeaderId { get; set; }
[ForeignKey("BarHeaderId")]
public TaBarHeader BarHeaderFk { get; set; }
}
HeaderTelegrama/Details.cshtml
:
@model TraficAlert.Models.ViewModels.HeaderTelegramaViewModel
<dt class="col-sm-2">
@Html.DisplayNameFor(model => model.TaBarHeader.ListaOtf)
</dt>
<dd class="col-sm-10">
@Html.DisplayFor(model => model.TaBarHeader.ListaOtf)
</dd>
(...)
<th>
@Html.DisplayNameFor(model => model.TaBarBody.Codstatie1)
</th>
@foreach (var item in Model.TaBarHeader.TaBarBodies)
{
<tr>
<td>
@Html.DisplayFor(modelItem => item.Codstatie1)
</td>
<a asp-controller="BodyTelegrama" asp-action="Edit" asp-route-id="@item.Id">Edit</a>
BodyTelegrama/Edit.cshtml
:
@model TraficAlert.Models.ViewModels.BodyTelegramaViewModel
@{
ViewData["Title"] = "Edit";
}
<h1>Edit</h1>
<h4>TaBarBody</h4>
<hr />
<div class="row">
<div class="col-md-4">
<form asp-action="Edit">
<div asp-validation-summary="ModelOnly" class="text-danger"></div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.Codstatie1" class="control-label">Cod Statie 1</label>
<input asp-for="@Model.TaBarBody.Codstatie1" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.Codstatie1" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.Codstatie2" class="control-label">Cod Statie 2</label>
<input asp-for="@Model.TaBarBody.Codstatie2" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.Codstatie2" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.DtIniP" class="control-label">Data Ini P</label>
<input asp-for="@Model.TaBarBody.DtIniP" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.DtIniP" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.DtFinP" class="control-label">Data Fin P</label>
<input asp-for="@Model.TaBarBody.DtFinP" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.DtFinP" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.DtIniR" class="control-label">Data Ini R</label>
<input asp-for="@Model.TaBarBody.DtIniR" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.DtFinP" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.DtFinR" class="control-label">Data Fin R</label>
<input asp-for="@Model.TaBarBody.DtFinR" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.DtFinR" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.KmIni" class="control-label">Km Ini</label>
<input asp-for="@Model.TaBarBody.KmIni" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.KmIni" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.KmFin" class="control-label">Km Fin</label>
<input asp-for="@Model.TaBarBody.KmFin" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.KmFin" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.LiniaFir" class="control-label">Linia Fir</label>
<input asp-for="@Model.TaBarBody.LiniaFir" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.LiniaFir" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.NomImpactId" class="control-label">Impact</label>
<select asp-for="@Model.TaBarBody.NomImpactId" class="form-control" asp-items="ViewBag.NomImpactId"></select>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.NomAnulatId" class="control-label">Anulat</label>
<select asp-for="@Model.TaBarBody.NomAnulatId" class="form-control" asp-items="ViewBag.NomAnulatId"></select>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.MotivAnulare" class="control-label">Motiv Anulare</label>
<input asp-for="@Model.TaBarBody.MotivAnulare" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.MotivAnulare" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="@Model.TaBarBody.Ruta" class="control-label">Ruta</label>
<input asp-for="@Model.TaBarBody.Ruta" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.Ruta" class="text-danger"></span>
</div>
<div class="form-group">
<input type="submit" asp-route-id="@ViewBag.TelegramaId" value="Save" />
</div>
</form>
</div>
</div>
<div>
<a asp-action="Index">Back to List</a>
</div>
BodyTelegramaController
:
// GET
public IActionResult Edit(int id, int HeaderTelegramaId)
{
BodyTelegramaViewModel bodyTelegramaViewModel = new BodyTelegramaViewModel();
bodyTelegramaViewModel.TaBarBody = new TaBarBody();
bodyTelegramaViewModel.TaBarBody.BarHeaderFk = new TaBarHeader();
bodyTelegramaViewModel.TaBarBody = _unitofwork.BarBody.DetailsBarB(id);
bodyTelegramaViewModel.TaBarBody.BarHeaderFk = _unitofwork.BarHeader.DetailsBarHB(id);
ViewData["TelegramaId"] = HeaderTelegramaId;
if (bodyTelegramaViewModel.TaBarBody == null)
{
return NotFound();
}
ViewData["NomImpactId"] = new SelectList(_unitofwork.NomImpact.GetAll(), "Id", "Nume");
ViewData["NomAnulatId"] = new SelectList(_unitofwork.NomAnulat.GetAll(), "Id", "Nume");
return View(bodyTelegramaViewModel);
}
// POST
public IActionResult Edit(int id, BodyTelegramaViewModel bodyTelegramaViewModel)
{
if (id != bodyTelegramaViewModel.TaBarBody.Id)
{
return NotFound();
}
if (ModelState.IsValid)
{
try
{
bodyTelegramaViewModel.TaBarBody.BarHeaderId = id;
_unitofwork.BarBody.Update(bodyTelegramaViewModel.TaBarBody);
_unitofwork.Save();
}
catch (DbUpdateConcurrencyException)
{
if (!TaBarBodyExists(bodyTelegramaViewModel.TaBarBody.Id))
{
return NotFound();
}
else
{
throw;
}
}
return RedirectToAction("Index");
}
return View(bodyTelegramaViewModel);
}
每次我编辑记录时,我的外键 - BarHeaderId - 将其值更改为 0。
我试过 bodyTelegramaViewModel.TaBarBody.BarHeaderId = bodyTelegramaViewModel.TaBarHeader.Id;
但我收到错误 'Object reference not set to an instance of an object.'
如何获取 TaBarHeader.Id
值并将其放入 TaBarBody.BarHeaderId
?
更新:
视图模型:
public class HeaderTelegramaViewModel
{
public TaBarHeader TaBarHeader { get; set; }
public IEnumerable<TaBarHeader> taBarHeader { get; set; }
public TaBarBody TaBarBody { get; set; }
public IEnumerable<TaBarBody> taBarBody { get; set; }
}
public class BodyTelegramaViewModel
{
public TaBarBody TaBarBody { get; set; }
public IEnumerable<TaBarBody> taBarBody { get; set; }
}
HeaderTelegramaController:
public IActionResult Details(int id)
{
HeaderTelegramaViewModel headerTelegramaViewModel = new HeaderTelegramaViewModel();
headerTelegramaViewModel.TaBarHeader = _unitofwork.BarHeaderRepository.DetailsBarHB(id);
if (headerTelegramaViewModel == null)
{
return NotFound();
}
return View(headerTelegramaViewModel);
}
BodyTelegramaController:
// GET
public IActionResult Edit(int id)
{
BodyTelegramaViewModel bodyTelegramaViewModel = new BodyTelegramaViewModel();
bodyTelegramaViewModel.TaBarBody = new TaBarBody();
bodyTelegramaViewModel.TaBarBody.BarHeaderFk = new TaBarHeader();
bodyTelegramaViewModel.TaBarBody = _unitofwork.BarBodyRepository.DetailsBarB(id);
bodyTelegramaViewModel.TaBarBody.BarHeaderFk = _unitofwork.BarHeaderRepository.DetailsBarHB(id);
return View(bodyTelegramaViewModel);
}
这些是方法 DetailsBarB()
和 DetailsBarHB()
:
public TaBarBody DetailsBarB(int id)
{
return _db.TaBarBodies
.Include(t => t.BarHeaderFk)
.FirstOrDefault(m => m.Id == id);
}
public TaBarHeader DetailsBarHB(int id)
{
return _db.TaBarHeaders
.Include(x => x.TaBarBodies).ThenInclude(x => x.BarHeaderFk.CategoriaFk)
.FirstOrDefault(m => m.Id == id);
}
您可以进行以下更改以获取 TaBarHeader
ID。
在您的 Details View
中,将其更改为:
<a asp-controller="BodyTelegrama" asp-action="Edit" asp-route-id="@item.Id" asp-route-HeaderTelegramaId="@Model.TaBarHeader.Id">Edit</a>
在您的 Edit
操作中,将其更改为:
public IActionResult Edit(int id,int HeaderTelegramaId)
{
BodyTelegramaViewModel bodyTelegramaViewModel = new BodyTelegramaViewModel();
bodyTelegramaViewModel.TaBarBody = new TaBarBody();
bodyTelegramaViewModel.TaBarBody.BarHeaderFk = new TaBarHeader();
bodyTelegramaViewModel.TaBarBody = _unitofwork.BarBodyRepository.DetailsBarB(id);
bodyTelegramaViewModel.TaBarBody.BarHeaderFk = _unitofwork.BarHeaderRepository.DetailsBarHB(id);
ViewData["TelegramaId"] = HeaderTelegramaId;
return View(bodyTelegramaViewModel);
}
[HttpPost]
public IActionResult Edit(int id, BodyTelegramaViewModel bodyTelegramaViewModel)
{
bodyTelegramaViewModel.TaBarBody.BarHeaderId = id;
_unitofwork.BarBodyRepository.Update(bodyTelegramaViewModel.TaBarBody);
_unitofwork.Save();
return View(bodyTelegramaViewModel);
}
然后在您的 Edit View
中将其更改为:
<form asp-action="Edit">
<div asp-validation-summary="ModelOnly" class="text-danger"></div>
<div class="form-group">
<input type="hidden" asp-for="@Model.TaBarBody.Id" />
<label asp-for="@Model.TaBarBody.Codstatie1" class="control-label">Cod Statie 1</label>
<input asp-for="@Model.TaBarBody.Codstatie1" class="form-control" />
<span asp-validation-for="@Model.TaBarBody.Codstatie1" class="text-danger"></span>
</div>
<div>
<input type="submit" asp-route-id="@ViewBag.TelegramaId" value="Save"/>
</div>
</form>
然后在你的 Edit
post 操作中,id
将是 TaBarHeader.Id
。
测试结果: