简体   繁体   中英

How to populate dropdown list from nested Models? (Asp.net Core MVC)

I have a nested model and I use one model named (BootstrapTool) to make the view strongly typed.

I use ViewBag to populate a dropdown list with the nested Model named (BootstrapCategory). But my problem is when I select from it always returns validation null exception.

BootstrapTool Model

public class BootstrapTool
{
    public Guid Id { get; set; }

    [MaxLength(100,ErrorMessage ="Max 100")]
    [Required]
    public string tool { get; set; }

    [MaxLength(300, ErrorMessage = "Max 300")]
    [Required]
    public string descreption { get; set; }

    [Required]
    public string html { get; set; }

    [Required] // here where nisting the other Model BootstrapCategory 
    public BootstrapCategory category { get; set; }
    
}

BootstrapCategory Model

public class BootstrapCategory
{
    [Key]
    public Guid Id { get; set; }

    [MaxLength(20)]
    [Required]
    public string Category { get; set; }
}

The Controller

    public IActionResult Create()
    {
        List<BootstrapCategory> bootstrapCategories = _context.bootstrapCategories.ToList();
        ViewBag.bpCategories = new SelectList(bootstrapCategories, "Id", "Category");

        return View();
    }

    [HttpPost]
    [ValidateAntiForgeryToken]
    public async Task<IActionResult> Create(BootstrapTool bootstrapTool)
    {
        if (ModelState.IsValid)
        {
            bootstrapTool.Id = Guid.NewGuid();
            _context.Add(bootstrapTool);
            await _context.SaveChangesAsync();
            return RedirectToAction(nameof(Index));
        }

        return View(bootstrapTool);
    }

Here where the dropdown list is to display BootstrapCategory
The View

@model BootstrapTool

<div class="row">
    <div class="col-10 offset-1">
        <form asp-action="Create">
            <div asp-validation-summary="ModelOnly" class="text-danger"></div>
            <div class="gap-2 d-flex justify-content-between">
                <div class="form-group w-50">
                    <label asp-for="tool" class="control-label"></label>
                    <input asp-for="tool" class="form-control" />
                    <span asp-validation-for="tool" class="text-danger"></span>
                </div>
                <div class="form-group w-50">
                    <label class="control-label">category</label>
                    <select asp-for="category.Id" class="form-control" asp-items="@ViewBag.bpCategories">
                        <option value="" disabled hidden selected>Select Section ...</option>
                    </select>
                    <span asp-validation-for="category" class="text-danger"></span>
                    @*<select asp-for="Id" asp-items="@Html.GetEnumSelectList<Enum>()" class="form-control">
                        <option value="" hidden disabled selected> -- please selecgt -- </option>
                    </select>*@
                </div>
            </div>
            <div class="form-group">
                <label asp-for="descreption" class="control-label"></label>
                <textarea asp-for="descreption" class="form-control" rows="2"></textarea>
                <span asp-validation-for="descreption" class="text-danger"></span>
            </div>
            <div class="form-group mb-2">
                <label asp-for="html" class="control-label"></label>
                <textarea asp-for="html" class="form-control" rows="5"></textarea>
                <span asp-validation-for="html" class="text-danger"></span>
            </div>

            <div class="form-group mt-3">
                <input type="submit" value="Create" class="btn btn-primary d-grid col-6 mx-auto" />
            </div>
        </form>
    </div>
</div>

Add CategoryId

public class BootstrapTool
{
    [Key]
    public Guid Id { get; set; }

    [Required] 
    public Guid? CategoryId { get; set; }
     [ForeignKey(nameof(CategoryId))]
    [InverseProperty("BootstrapTools")]
     public BootstrapCategory Category { get; set; }
    
}

public class BootstrapCategory
{
    [Key]
    public Guid Id { get; set; }

    [MaxLength(20)]
    [Required]
    public string Category { get; set; }

    [InverseProperty(nameof(BootstrapTool.Category))]
    public virtual ICollection<BootstrapTool> BootstrapTools { get; set; }
}

and fix the view

<select asp-for="CategoryId" class="form-control" asp-items="@ViewBag.bpCategories">
 </select>
```

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM