(C# ASP.NET Core) CRUD with a Dropdownlist in a Razor Form

This tutorial extends the FORM that we have implemented in the previous tutorial (see link below). Now we add a dropdownlist to that form and observe how easy is it to make an addition to a project that is already CRUD-ready! A dropdownlist must be backed by a C# collection of SelectListItem objects. We also explain how to add an empty required [-Select-] item to such a dropdownlist.

Categories | About |     |  

Parveen,

Objective of this Tutorial
(see the linked video for details)

This tutorial adds a dropdown to the form that we completed in the previous tutorial (C# ASP.NET Core) CRUD with a Radiobuttonlist in a Razor Form

Format of Items for the DropdownList

A dropdown is an html component.

The list of items is provided through a collection of C# SelectList objects. A SelectList item has two properties - Text for the display text, and Value for the value associated with each item.

A database query can be used to build a collection of SelectList items. In the snippet below we have hard-coded the collection.


// --- STARTING CODE NOT SHOWN --- 

@addTagHelper *, Microsoft.AspNetCore.Mvc.TagHelpers

@{

  // list that can be filled after some database query 
  var locations = new List<SelectListItem>()
  {
      new SelectListItem("[-Select-]", ""),
      new SelectListItem("Tokyo", "TYO"),
      new SelectListItem("Paris", "PRS"),
      new SelectListItem("Ankara", "ANK")
  };
}

// --- REMAINING CODE NOT SHOWN --- 

Video Explanation

Please watch the following youtube video:

How to Render a DropdownList in a Razor Page

Tag helper for <select> is used as shown below.


<select asp-for="Prod.ItemLocation" asp-items="@locations" required>

</select>

How to add an empty [-Select-] item

Insert a SelectListItem of Text = "[-Select-]" and Value = "" at index 0 of the collection, as we have done in the above snippet. Additionally, required attribute must be marked on the <select> tag on the razor page, as done above.

If a user doesn't make a selection, and tries to submit the form, then the required attribute will cause it to fail.

Step 1 of 2: Modify the Model

Add a field (ItemLocation below) for to your model class. Nothing else needs to be changed.

// Product.cs model class 
using Microsoft.EntityFrameworkCore;

using System;

using System.ComponentModel.DataAnnotations;

using System.ComponentModel.DataAnnotations.Schema;

namespace DBaseCon
{

  public class Product
  {

    // auto-increment Primary ID key 
    [Key]
    [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
    public int ID { get; set; }

    // textbox 
    public String Name { get; set; }

    // checkbox 
    public bool IsActive { get; set; }

    // enum for radiobuttonlist 
    public enum Quality
    {

      Superior = 0,
      Inferior = 1,
      Normal = 2,
    }


    // radio button property 
    public Quality ItemQuality { get; set; }

    // ADD THIS NOW ----for dropdown----- // 
    public String ItemLocation { get; set; }
  }

}

Step 2 of 2: Add markup to the Razor Page
(see the linked video for details)

Add the following markup to the razor page Index.cshtml.

Notice that a SelectListItem collection has been created first. Optionally, it could have been generated through a function call on the backing class, or after setting a property on the backing class, depending on the complexity/convenience of the project.

@page "{handler?}/{id?}"

@namespace DBaseCon

@model Modular.Pages.IndexModel

@addTagHelper *, Microsoft.AspNetCore.Mvc.TagHelpers

@{

  // list that can be filled after some database query 
  var locations = new List<SelectListItem>()
  {
      new SelectListItem("[-Select-]", ""),
      new SelectListItem("Tokyo", "TYO"),
      new SelectListItem("Paris", "PRS"),
      new SelectListItem("Ankara", "ANK")
  };

}

<form method="post">

  Name: <input asp-for="Prod.Name" />

  <input asp-for="Prod.ID" type="hidden" />

  <br />

  <label asp-for="Prod.IsActive">Active</label>

  <input asp-for="Prod.IsActive" />

  <br />

  <label>
    <input type="radio" asp-for="Prod.ItemQuality" value="-1" checked />
    None
  </label>

  @foreach (var item in System.Enum.GetValues(typeof(Product.Quality)))
  {
    <label>
      <input type="radio" asp-for="Prod.ItemQuality" value="@item" />
      @item
    </label>
  }

  <br />

  // ADD THIS NOW for the dropdown 

  <select asp-for="Prod.ItemLocation" asp-items="@locations" required>

  </select>

  <br />

  <input type="submit" />

</form>

<h1>Display of Data</h1>

@foreach (var prod in Model.Products)
{
<div>

  @prod.Name,
  @(prod.IsActive ? "Active" : "In-Active"),
  @prod.ItemQuality,
  @locations.FirstOrDefault(x => x.Value == prod.ItemLocation).Text

  |

  <a asp-route-id="@prod.ID"
     asp-page-handler="Delete">Delete</a>

  |

  <a asp-route-id="@prod.ID"
     asp-page-handler="Edit">Edit</a>

</div>

  <hr />
}

In this case of our tutorial simply delete your sqlite database file (mydb.db) and allow the DbContext to re-create it from the modified model class.

WHY WAS IT SO SIMPLE?

Ans: Right from the creation of database till the CRUD operations, the EF Core framework works on the basis of your model class. You just have to add a property to your model class + a corresponding input tag helper to your form, and make no change anywhere else. In simple words: The property travels everywhere with the model.


This Blog Post/Article "(C# ASP.NET Core) CRUD with a Dropdownlist in a Razor Form" by Parveen is licensed under a Creative Commons Attribution-NonCommercial-ShareAlike 4.0 International License.

Comments and Discussion