Facing issue the usage of Data Annotations in .Net 6 - asp.net

**Hi, I'm using .Net 6 & visual studio 2022 community.
My Model validations through Data Annotations are working for all HTML tags, i want to use only for some fields..**
Code:
public class Student
{
public int Id { get; set; }
[Display(Name="Student Name")]
[System.ComponentModel.DataAnnotations.Required(ErrorMessage = "Please provide a value for Name field")]
public string Name { get; set; }
public string Email{ get; set; }
public string Department{ get; set; }
}
}
HTML:
I'm using Tag helpers to render HTML code.
#model MiddleWareComponents.Models.Student
#{
ViewBag.Title = "Student";
}
<form asp-controller="home" asp-action="student" method="post" class="mt-3">
<div class="form-group row">
<label asp-for="#Model.Name" class="col-sm-2 col-form-label"></label>
<div class="col-sm-10">
<input asp-for="#Model.Name" class="form-control" placeholder="Name">
<span asp-validation-for="#Model.Name" class="text-danger"></span>
</div>
</div>
<div class="form-group row">
<label asp-for="#Model.Department" class="col-sm-2 col-form-label"></label>
<div class="col-sm-10">
<input asp-for="#Model.Department" class="form-control" placeholder="department">
</div>
</div>
<div class="form-group row">
<label asp-for="#Model.Email" class="col-sm-2 col-form-label"></label>
<div class="col-sm-10">
<input asp-for="#Model.Email" class="form-control" placeholder="Email">
</div>
</div>
<div class="form-group row">
<div class="col-sm-10">
<button type="submit" class="btn btn-primary">Create</button>
</div>
</div>
</form>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.6.0/jquery.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery-validate/1.19.3/jquery.validate.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery-validation-unobtrusive/3.2.12/jquery.validate.unobtrusive.js"></script>
**When we run the code, all html fields are required necessary to fill up , otherwise these fields are giving error and submit button not going to server. But there is only Name field is Required & mentioned in the model. **
Please give me a solution, how i can restrict some of the fields required to fill up , & some fields are not required. Thanks

Accroding to your decription,I think you could check if you have referred the js files and if the js files are in the correct order,you could check this document related for more details:
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.6.0/jquery.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery-validate/1.19.3/jquery.validate.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery-validation-unobtrusive/3.2.12/jquery.validate.unobtrusive.js"></script>

If your model state is not valid you want to return the view with the view-model instead of the empty string:
[HttpPost]
public string Student(Student student)
{
if (ModelState.IsValid)
{
return RedirectToAction("yourAction", "yourController");
}
else
{
return View(student);
}
}

Related

Razor pages client site validation not working

I'm trying to use client-side validation in my razor pages app but it's not working for the views.
It does work on the register page that is located under the identity area.
Create.cshtml
#model Toolbox.Models.ProjectsModel.Assignment
#{
ViewData["Title"] = "Create";
}
<h1>Nieuwe taak maken</h1>
<h4>Taak</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="Name" class="control-label"></label>
<input asp-for="Name" class="form-control" />
<span asp-validation-for="Name" class="text-danger"></span>
</div>
<div class="form-group">
<label asp-for="Fase" class="control-label"></label>
<input asp-for="Fase" class="form-control" />
<span asp-validation-for="Fase" class="text-danger"></span>
</div>
<div class="form-group">
<input type="submit" value="Maak nieuwe taak" class="btn btn-primary my-2"/>
</div>
</form>
</div>
</div>
<div>
<a asp-action="Index" class="btn btn-primary">Terug</a>
</div>
Assignment.cs
using System.ComponentModel.DataAnnotations;
using Toolbox.Interfaces;
namespace Toolbox.Models.ProjectsModel
{
public class Assignment : IAssignment
{
[Key]
public int Id { get; set; }
[Display(Name = "Naam")]
[Required]
public string Name { get; set; }
[Required]
public string Fase { get; set; }
public List<SubAssignment> SubAssignment { get; set; }
}
}
_ViewImports.cshtml
#using Toolbox
#using Toolbox.Models
#addTagHelper *, Microsoft.AspNetCore.Mvc.TagHelpers
_viewStart.cshtml
#{
Layout = "_Layout";
}
Program.cs
app.UseEndpoints(endpoints =>
{
endpoints.MapControllerRoute(name: "default",
pattern: "{controller=Home}/{action=Index}");
endpoints.MapRazorPages();
});
Does anybody know how I need to solve this problem?
You need to include the _ValidationScriptsPartial file in the Razor page. Add the following to the bottom of the page/view:
#section scripts{
<partial name="_ValidationScriptsPartial" />
}

How to POST in .Net Core MVC

i have a login page with Username and Password inputs and also a submit button. I want to call a method in my Controller that checks if the data matches and shows the result. how do i call that method? I tried the following but it didnt work it passes those as parameters
#using (Html.BeginForm("Logmein", "LoginController", FormMethod.Post))
{
<form method="post">
<div class="input-group mt-3">
<div class="input-group-prepend">
</div>
<input type="text" class="form-control" placeholder="Username" asp-for="Userusername">
</div>
<div id="login_usernametxt" class="input-group mt-2">
<input id="login_passwordtxt" type="password" class="form-control" placeholder="Password" asp-for="Userpassword">
</div>
<button id="login_signinbtn" class="mt-3 btn bg-warning text-light" style="float: right;" formmethod="post">Sign in</button>
</form>
}
here is my controller.
public class LoginController : Controller
{
public LoginInfo Logininformation { get; set; }
public IActionResult Userlogin()
{
return View();
}
[HttpPost]
public IActionResult Logmein()
{
//checks if the data matches....
return RedirectToPage("/Home/Index");
}
}
Tyr to include model with following properties Userusername,Userpassword in Logmein() method
Also u can remove html helper method ( #using (Html.BeginForm("Logmein", "LoginController", FormMethod.Post)))
Ex:
<form method = "post" asp-controller = "Login" asp-action = "Logmein" >
<div class="input-group mt-3">
<div class="input-group-prepend">
</div>
<input type="text" class="form-control" placeholder="Username" asp-for="Userusername">
</div>
<div id="login_usernametxt" class="input-group mt-2">
<input id="login_passwordtxt" type="password" class="form-control" placeholder="Password" asp-for="Userpassword">
</div>
<input type = "submit" value = "Login" />
</form>
Model Class
public class Login
{
public string Userusername { get; set; }
public string Userpassword { get; set; }
}
Controller Method:
[HttpPost]
public IActionResult Logmein(LoginModel login)
{
//checks if the data matches....
return RedirectToPage("/Home/Index");
}

How can I create registration page without refreshing in Asp.Net MVC with Razor?

I need to get advice about in Registration Page in Asp.net MVC5 and razor page.
what is the best way for it:
My scenario is I have a registration process in three-step :
In the First Step, the client enters a username and captcha.
In the Second Phase client Enter the Phone number and send SMS by Identity.
If the Entered validation code was code the confirmation message and welcome page appears.
An easy way is we can make a three action result by the separate razor view.
But the problem is I need to do the noted process without any page refreshing.
what is the best way to do it?
Thanks a lot.
I would solve your task with following steps
Download jquery.unobtrusive-ajax.js from here and add a link in your layout.cshtml
create a Components folder in your pages folder
create a Register folder in your Components folder
add a file for your dto
RegisterDto.cs
public class RegisterDto
{
public string Email { get; set; }
public string FirstName { get; set; }
public string SurName { get; set; }
public string Phone { get; set; }
public string Validation { get; set; }
}
create your first form.
I created a new form in the index.cshtml. Here you can see, that I'm using ajax for handling the form. Use a container for replacing with your viewcomponents. In my example, my DOM Object is "content".
index.cshtml
<div id="content">
<div class="col-6">
<form method="post" data-ajax="true" data-ajax-method="post" asp-page="/Index" asp-page-handler="SubPage1" data-ajax-update="#content">
<div class="form-group">
<label asp-for="RegisterDto.Email"></label>
<input asp-for="RegisterDto.Email" class="form-control" />
</div>
<div class="form-group">
<label asp-for="RegisterDto.FirstName"></label>
<input asp-for="RegisterDto.FirstName" class="form-control" />
</div>
<div class="form-group">
<label asp-for="RegisterDto.SurName"></label>
<input asp-for="RegisterDto.SurName" class="form-control" />
</div>
<button class="btn btn-success" type="submit">next</button>
</form>
</div>
Create a new ViewComponentClass. Over the page-parameter you can switch between pages, and the registerDto is your model you can pass between pages.
RegisterViewComponent.cs
public class RegisterViewComponent : ViewComponent
{
public async Task<IViewComponentResult> InvokeAsync(string Page, RegisterDto registerDto)
{
return View(Page, registerDto);
}
}
create your views in your viewcomponent.
SubPage1.cshtml
<div class="col-6">
<form method="post" data-ajax="true" data-ajax-method="post" asp-page-handler="SubPage2" data-ajax-update="#content">
<div class="form-group">
<label asp-for="Email"></label>
<input asp-for="Email" class="form-control disabled" />
</div>
<div class="form-group">
<label asp-for="FirstName"></label>
<input asp-for="FirstName" class="form-control disabled" />
</div>
<div class="form-group">
<label asp-for="SurName"></label>
<input asp-for="SurName" class="form-control disabled" />
</div>
<div class="form-group">
<label asp-for="Phone"></label>
<input asp-for="Phone" class="form-control" />
</div>
<button class="btn btn-success" type="submit">next</button>
</form>
SubPage2.cshtml
<div class="col-6">
<form method="post" data-ajax="true" data-ajax-method="post" asp-page-handler="SubPage3" data-ajax-update="#content">
<div class="form-group">
<label asp-for="Email"></label>
<input asp-for="Email" class="form-control disabled" />
</div>
<div class="form-group">
<label asp-for="FirstName"></label>
<input asp-for="FirstName" class="form-control disabled" />
</div>
<div class="form-group">
<label asp-for="SurName"></label>
<input asp-for="SurName" class="form-control disabled" />
</div>
<div class="form-group">
<label asp-for="Phone"></label>
<input asp-for="Phone" class="form-control disabled" />
</div>
<div class="form-group">
<label asp-for="Validation"></label>
<input asp-for="Validation" class="form-control" />
</div>
<button class="btn btn-success" type="submit">Done</button>
</form>
</div>
default.cshtml
<h1>done</h1>
done!

Blazor Simple Arithmetic Example

I made an example to learn Blazor. The example is to multiply the weight and the center of gravity to get the moment.
The goal is to perform calculation when the weight or center of gravity changes.
I get the following error.
The attribute 'onchange' is used two or more times for this element. Attributes must be unique (case-insensitive). The attribute 'onchange' is used by the '#bind' directive attribute.
Can you help me to achieve the goal?
<h3>MomentBasicCalc</h3>
<div class="container">
<div class="row">
<div class="col-sm">
<label for="weight">Weights</label>
<input type="text" class="form-control" id="weight"
#onchange="Calc" #bind="#Weight" />
</div>
<div class="col-sm">
<label for="CG">CG</label>
<input type="text" class="form-control" id="CG"
#onchange="Calc" #bind=#Cg />
</div>
<div class="col-sm">
<label for="Moment">Moment</label>
<input type="text" class="form-control" id="Moment" value=#Moment readonly />
</div>
</div>
</div>
#code {
public double Weight { get; set; }
public double Cg { get; set; }
public double Moment { get; set; }
void Calc()
{
Moment = Weight * Cg;
}
}
It's not supported to attach multiple event handlers on a single event.
You should do something like this:
<div class="container">
<div class="row">
<div class="col-sm">
<label for="weight">Weights</label>
<input type="text" class="form-control" id="weight"
**value="#Weight**
#onchange="SetWeight" "/>
</div>
<div class="col-sm">
<label for="CG">CG</label>
<input type="text" class="form-control" id="CG"
**value=#Cg**
#onchange="SetCG" />
</div>
<div class="col-sm">
<label for="Moment">Moment</label>
<input type="text" class="form-control" id="Moment" value=#Moment readonly />
</div>
</div>
</div>
#code
{
void SetWeight(UIChangeEventArgs e)
{
Weight = (string) e.Value;
Calc();
}
void SetCG(UIChangeEventArgs e)
{
CG = (string) e.Value;
Calc();
}
}

Form Validation not working in Blazor 3.1

I am using EF to save data in DB and so far farm works fine and saves the data, but when i try to add validation to form it doesnt work & doesnt show any error message or save any data in database.
Example of working & non working code.
Below code without validation
Employee.cs
using System.ComponentModel.DataAnnotations;
namespace BlazorSPA1.Data
{
public class Employee
{
[MaxLength(50)]
public string Id { get; set; }
[MaxLength(50)]
public string Name { get; set; }
[MaxLength(50)]
public string Department { get; set; }
[MaxLength(100)]
public string Designation { get; set; }
[MaxLength(100)]
public string Company { get; set; }
[MaxLength(100)]
public string City { get; set; }
}
}
AddEmployee.razor
#page "/addemployee"
#inject NavigationManager NavigationManager
#inject IEmployeeService EmployeeService
<h2>Create Employee</h2>
<hr />
<form>
<div class="row">
<div class="col-md-8">
<div class="form-group">
<label for="Name" class="control-label">Name</label>
<input for="Name" class="form-control" #bind="#employee.Name" />
</div>
<div class="form-group">
<label for="Department" class="control-label">Department</label>
<input for="Department" class="form-control" #bind="#employee.Department" />
</div>
<div class="form-group">
<label for="Designation" class="control-label">Designation</label>
<input for="Designation" class="form-control" #bind="#employee.Designation" />
</div>
<div class="form-group">
<label for="Company" class="control-label">Company</label>
<input for="Company" class="form-control" #bind="#employee.Company" />
</div>
<div class="form-group">
<label for="City" class="control-label">City</label>
<input for="City" class="form-control" #bind="#employee.City" />
</div>
</div>
</div>
<div class="row">
<div class="col-md-4">
<div class="form-group">
<input type="button" class="btn btn-primary" #onclick="#CreateEmployee" value="Save" />
<input type="button" class="btn" #onclick="#Cancel" value="Cancel" />
</div>
</div>
</div>
</form>
#code {
Employee employee = new Employee();
protected async Task CreateEmployee()
{
await EmployeeService.CreateEmployee(employee);
NavigationManager.NavigateTo("listemployees");
}
void Cancel()
{
NavigationManager.NavigateTo("listemployees");
}
}
Code which is not working after i made validation changes
Employee.cs
using System.ComponentModel.DataAnnotations;
namespace BlazorSPA1.Data
{
public class Employee
{
[MaxLength(50)]
public string Id { get; set; }
[Required]
[StringLength(20)]
public string Name { get; set; }
[Required]
[StringLength(20)]
public string Department { get; set; }
[MaxLength(100)]
public string Designation { get; set; }
[MaxLength(100)]
public string Company { get; set; }
[MaxLength(100)]
public string City { get; set; }
}
}
AddEmployeeValidation.razor
#page "/addemployeeValidation"
#inject NavigationManager NavigationManager
#inject IEmployeeService EmployeeService
<h2>Create Employee</h2>
<hr />
<EditForm Model="#employee" OnValidSubmit="#CreateEmployee">
<DataAnnotationsValidator />
<div class="row">
<div class="col-md-8">
<div class="form-group">
<label for="Name" class="control-label">Name</label>
<input for="Name" class="form-control" #bind="#employee.Name" />
<ValidationMessage For="#(()=> employee.Name)" />
</div>
<div class="form-group">
<label for="Department" class="control-label">Department</label>
<input for="Department" class="form-control" #bind="#employee.Department" />
</div>
<div class="form-group">
<label for="Designation" class="control-label">Designation</label>
<input for="Designation" class="form-control" #bind="#employee.Designation" />
</div>
<div class="form-group">
<label for="Company" class="control-label">Company</label>
<input for="Company" class="form-control" #bind="#employee.Company" />
</div>
<div class="form-group">
<label for="City" class="control-label">City</label>
<input for="City" class="form-control" #bind="#employee.City" />
</div>
</div>
</div>
<div class="row">
<div class="col-md-4">
<div class="form-group">
<input type="button" class="btn btn-primary" value="Save" />
<input type="button" class="btn" #onclick="#Cancel" value="Cancel" />
</div>
</div>
</div>
</EditForm>
#code {
Employee employee = new Employee();
protected async Task CreateEmployee()
{
await EmployeeService.CreateEmployee(employee);
NavigationManager.NavigateTo("listemployees");
}
void Cancel()
{
NavigationManager.NavigateTo("listemployees");
}
}
I am using below code example show in this example https://www.c-sharpcorner.com/article/visual-studio-extension-for-blazor-spa-with-ef-core-3-1/
When i add validation code, it open Add Employee page but nothing happens no validation message no form submit even no data is save in database. not sure where issue is
I had made a tiny mistake which went un-noticed, Validation started working when i changed the input type to submit
<input type="button" class="btn btn-primary" value="Save" />
Correct
<input type="submit" class="btn btn-primary" value="Save" />

Resources