C# Razor Pages:在创建过程中继承模型以添加字段
这些实体是我试图实现的虚拟等价物(现实中更复杂) 我只需要在创建文章时在表单中显示额外的字段(SendToSubscribers字段),而这些字段不是实体本身的一部分C# Razor Pages:在创建过程中继承模型以添加字段,c#,asp.net-mvc,asp.net-core,razor,C#,Asp.net Mvc,Asp.net Core,Razor,这些实体是我试图实现的虚拟等价物(现实中更复杂) 我只需要在创建文章时在表单中显示额外的字段(SendToSubscribers字段),而这些字段不是实体本身的一部分 public class Article { public string Title { get; set } } public class ArticleCreateForm : Article { public bool SendToSubscribers { get; set; } } 在要创建/更新的c
public class Article {
public string Title { get; set }
}
public class ArticleCreateForm : Article {
public bool SendToSubscribers { get; set; }
}
在要创建/更新的cshtml中,有:
@model Article
...
@if (string.IsNullOrEmpty(Model.Id))
{
<admin-input asp-for="SendToSubscribers" />
@模型文章
...
@if(string.IsNullOrEmpty(Model.Id))
{
不幸的是,这是我得到的错误:
“Article”不包含“SendToSubscribers”的定义,并且找不到接受“Article”类型的第一个参数的可访问扩展方法“SendToSubscribers”(是否缺少using指令或程序集引用?)
对不起,如果方法不好,在所有,我来自PHP的背景
我想这不是一个好的解决方案,那么我如何才能做到这一点呢?谢谢。您的解决方案有一种方法,它与设计模式有关 创建将占用两个模型的容器类:
public class MainArticleModel{
public Article article {get; set;}
public ArticleCreateForm articleCreateForm {get; set;}
}
然后您将能够使用它:
@model MainArticleModel
...
@if (string.IsNullOrEmpty(Model.Id))
{
<admin-input asp-for="SendToSubscribers" />
@model main文章模型
...
@if(string.IsNullOrEmpty(Model.Id))
{
这样,两个模型都将包含在一个视图中。您可以使用表单集合在视图中添加其他参数,这些参数在模型中不可用 查看
@model Article
ViewBag.Title = "Home Page";
}
@using (Html.BeginForm("submit", "Home", new { id = "form1" }, FormMethod.Post))
{
<p>Use this area to provide additional information.</p>
<input type="text" name="Title" value="est" />
<input type="checkbox" name="SendToSubscribers" value="true" />
<div class="col-md-offset-2 col-md-10">
<input type="button" id="btnLogOn" value="Save" class="btn btn-default" />
</div>
}
代码
还可以将formcollection转换为类对象
@{var m=(ArticleCreateForm)模型;
if(string.IsNullOrEmpty(m.Id))
{
}}
也许您不喜欢它,但通常,最干净的方法是为不同的视图创建不同的模型,并使这些模型与您的持久性模型不同
在这种方法中,您应该ArticleCreateModel
,它只具有创建文章所需的属性,包括SendToSubscribers
。但它不应该具有Id
属性,因为视图中不需要Id
。因此,这应该是模型:
public class Article
{
public string Id { get; set; }
public string Title { get; set; }
}
public class ArticleCreateModel
{
public string Title { get; set; }
public bool SendToSubscribers { get; set; }
}
然后在ArticleContoller
的Create
操作中,接收ArticleCreateModel
,然后要保存数据,您可以创建文章
并保存在存储器中,根据SendToSubscribers
的值,您还将决定将文章发送给订阅者:
public ActionResult Create(ArticleCreateModel model)
{
if(ModelState.IsValid())
{
ArticleBustinessLogic.Create(ArticleCreateModel model);
return RedirectToAction("Index");
// Or simply
// var article = new Article();
// article.Id = Guid.NewGuid().ToString();
// article.Title = model.Title();
// ArticleRepository.Create(article);
// ArticleSubcription.NotifySubscribers(article);
// return RedirectToAction("Index");
}
return View();
}
在这种方法中,视图
的模型应该是ArticleCreateModel
,您不需要任何if
语句:
@model ArticleCreateModel
...
<input asp-for="Title" />
<admin-input asp-for="SendToSubscribers" />
...
@model ArticleCreateModel
...
将视图模型映射到持久性模型更容易。您可以使用数据传输对象
型号:
public class Article
{
public int Id { get; set; }
[Required]
public string Title { get; set; }
}
控制员:我用
公共异步任务创建([Bind(“Title,SendToSubscribers”)]ArticleDto ArticleDto)
{
if(ModelState.IsValid)
{
var article=\u mapper.Map(articleDto);//此处自动映射
//在这里,您可以根据需要使用articleDto.SendToSubscribers
wait _articlepository.AddAsync(article);//示例
返回重定向到操作(名称(索引));
}
返回视图(文章);
}
视图:
@model WebApplication1.Models.ArticleDto
@{
ViewData["Title"] = "Create";
}
<h1>Create</h1>
<h4>ArticleDto</h4>
<hr />
<div class="row">
<div class="col-md-4">
<form asp-action="Create">
<div asp-validation-summary="ModelOnly" class="text-danger"></div>
<div class="form-group">
<label asp-for="Title" class="control-label"></label>
<input asp-for="Title" class="form-control" />
<span asp-validation-for="Title" class="text-danger"></span>
</div>
<div class="form-group form-check">
<label class="form-check-label">
<input class="form-check-input" asp-for="SendToSubscribers" /> @Html.DisplayNameFor(model => model.SendToSubscribers)
</label>
</div>
<div class="form-group">
<input type="submit" value="Create" class="btn btn-primary" />
</div>
</form>
</div>
</div>
<div>
<a asp-action="Index">Back to List</a>
</div>
@section Scripts {
@{await Html.RenderPartialAsync("_ValidationScriptsPartial");}
}
@model WebApplication1.Models.ArticleDto
@{
ViewData[“标题”]=“创建”;
}
创造
第条
@DisplayNameFor(model=>model.SendToSubscribers)
返回列表
@节脚本{
@{wait Html.RenderPartialAsync(“_validationScript”);}
}
无需创建另一个模型来隐藏标题字段,当razor页面呈现为html表单时,仅呈现razor页面中定义的字段。在这种情况下,它将不起作用,因为该字段是发送给订阅方的。c#不适用于此。@dctremblay请检查formcollection对象以传递c中的动态实体少女
public class Article
{
public int Id { get; set; }
[Required]
public string Title { get; set; }
}
public class ArticleDto
{
public int Id { get; set; }
[Required]
public string Title { get; set; }
public bool SendToSubscribers { get; set; }
}
public async Task<IActionResult> Create([Bind("Title,SendToSubscribers")] ArticleDto articleDto)
{
if (ModelState.IsValid)
{
var article =_mapper.Map<Article>(articleDto); // AutoMapper here
//Here you can use articleDto.SendToSubscribers as you want
await _articleRepository.AddAsync(article);//Example
return RedirectToAction(nameof(Index));
}
return View(article);
}
@model WebApplication1.Models.ArticleDto
@{
ViewData["Title"] = "Create";
}
<h1>Create</h1>
<h4>ArticleDto</h4>
<hr />
<div class="row">
<div class="col-md-4">
<form asp-action="Create">
<div asp-validation-summary="ModelOnly" class="text-danger"></div>
<div class="form-group">
<label asp-for="Title" class="control-label"></label>
<input asp-for="Title" class="form-control" />
<span asp-validation-for="Title" class="text-danger"></span>
</div>
<div class="form-group form-check">
<label class="form-check-label">
<input class="form-check-input" asp-for="SendToSubscribers" /> @Html.DisplayNameFor(model => model.SendToSubscribers)
</label>
</div>
<div class="form-group">
<input type="submit" value="Create" class="btn btn-primary" />
</div>
</form>
</div>
</div>
<div>
<a asp-action="Index">Back to List</a>
</div>
@section Scripts {
@{await Html.RenderPartialAsync("_ValidationScriptsPartial");}
}