ASP NET MVC cannot accept Null Datetime - asp.net-mvc

So i have a view model like this
public class TestViewModel
{
public DateTime? StartDate { get; set; }
public DateTime StartDate2 { get; set; }
}
With that viewmodel I expect that if I send "NULL" to those properties via JSON from ajax, then value for those properties are StartDate = null and StartDate2 = {01/01/0001 00.00.00}
This works as expected in my local machine, but on my server it returns error Bad Request
I know my server return Bad Request because of the model binding thing
Why does my server behave differently with my local machine ?
And how do I fix this ?
EDIT :
By the way, if I change the StartDate and StartDate2 type to string. It has no error, the code works perfectly
Here's my action in controller
public ActionResult TestAction(List<TestViewModel> p_viewModel)
{
//The code actually does not reach here, because it fail on model binding ?
// bla bla bla some logic here
}
and here's my javascript
function getData()
{
let datas = [];
$("#tableListMeeting tbody tr").each(function (i, row) {
let rowItem = $(row);
let startDate = rowItem.find(`input[name$=".StartDate"]`).val();
//change date format
startDate = (startDate == "") ? null : moment(startDate, "DD-MM-YYYY").format("YYYY/MM/DD");
let item = {
StartDate: startDate
};
datas.push(item);
});
return datas;
}
function onButtonClick(){
let data = getData();
let URL_TO_ACTION = "......"; //url to my action
$.ajax({
url: URL_TO_ACTION,
type: 'post',
datatype: 'json',
data: JSON.stringify(data),
contentType: 'application/json; charset=utf-8',
success: function (response) {
console.log("ajax local event 'sucess'");
console.log(response);
},
error: function (jqXHR, ajaxOptions, thrownError) {
if (jqXHR.status == 400) {
let a = jqXHR.responseText;
//logic to print error message
} else {
alert("Something went wrong, please try again");
}
},
beforeSend: function () {
console.log("ajax local event 'beforeSend'");
}
}

You should show more code in order to find out what's wrong.
Here is the fiddle with the working example for your View model.
https://dotnetfiddle.net/Eu7ayF
Controller:
[HttpPost]
public JsonResult GetAnswer(TestViewModel data)
{
Console.WriteLine(data.StartDate);
return Json(data);
}
View with ajax post.
#model HelloWorldMvcApp.TestViewModel
#{
Layout = null;
}
<!DOCTYPE html>
<!-- template from http://getbootstrap.com/getting-started -->
<html lang="en">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Bootstrap 101 Template</title>
<!-- CSS Includes -->
<link rel="stylesheet" href="//netdna.bootstrapcdn.com/bootstrap/3.1.1/css/bootstrap.min.css">
<style type="text/css">
.field-validation-error {
color: #ff0000;
}
</style>
</head>
<body>
<div class="container">
<div class="col-md-6 col-md-offset-3">
<h1>Hello Stranger</h1>
#using (Html.BeginForm())
{
<div class="form-group">
#Html.LabelFor(m => m.StartDate)
#Html.TextBoxFor(model => model.StartDate, new {#class="form-control"})
#Html.ValidationMessageFor(model => model.StartDate)
</div>
<div class="form-group">
#Html.LabelFor(m => m.StartDate2)
#Html.TextBoxFor(model => model.StartDate2, new {#class="form-control"})
#Html.ValidationMessageFor(model => model.StartDate2)
</div>
<button type="button" class="btn btn-success submit">Post Ajax</button>
}
<br/><br/>
<div class="alert alert-warning fade">
<img src="http://entechprod.blob.core.windows.net/dotnetfiddle/morpheus.jpg" style="max-width:100%;"/><br/><br/>
<strong><span class="alert-content"></span></strong>
</div>
</div>
</div>
<!-- JS includes -->
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.11.0/jquery.min.js"></script>
<script src="//netdna.bootstrapcdn.com/bootstrap/3.1.1/js/bootstrap.min.js"></script>
<script src="//ajax.aspnetcdn.com/ajax/jquery.validate/1.11.1/jquery.validate.min.js"></script>
<script src="//ajax.aspnetcdn.com/ajax/mvc/4.0/jquery.validate.unobtrusive.min.js"></script>
<script type="text/javascript">
$(function(){
$('.submit').click(function(){
if($('form').valid()) {
$.ajax({
url: '#Url.RouteUrl(new{ action="GetAnswer", controller="Home"})',
data: {startDate2: $('#startDate2').val(), startDate: $('#startDate').val()},
type: 'POST',
dataType: 'json',
contentType: "application/json; charset=utf-8",
success: function(resp) {
alert(resp.StartDate);
alert(resp.StartDate2);
}});
}
});
});
</script>
</body>
</html>

Related

How to Bind Html Form attribute to Uppy?

I'm trying to get the ImageUrl attribute from Uppy but can't bind it to input asp-for="ImageUrl" type="file" name="file" class="form-control" id="ImageUrl".
When I click on create button,my ImageUrl shows up null in controller method even though I selected a file via Uppy. How can I bind ImageUrl to Uppy and add the file to the folder I created (/tree/test file) ?
<head>
<meta charset="utf-8">
<meta name="viewport">
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" />
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no, shrink-to-fit=no" />
<link href="https://releases.transloadit.com/uppy/v3.1.1/uppy.min.css" rel="stylesheet">
<script src="https://releases.transloadit.com/uppy/v2.12.3/uppy.min.js" type="module"></script>
<script src="https://releases.transloadit.com/uppy/v2.12.3/uppy.legacy.min.js" type="nomodule"></script>
<script src="https://releases.transloadit.com/uppy/locales/v2.1.1/ru_RU.min.js"></script>
</head>
<body>
<form method="post" asp-action="create" id="form2" enctype="multipart/form-data">
<div class="form-group">
<label asp-for="ImageUrl">#localizer.GetLocalizedHtmlString("ImageUrl")</label>
<div id="drag-drop-area">
<input asp-for="ImageUrl" type="file" name="file" class="form-control" id="ImageUrl"/>
</div>
</div>
</br>
<button class="btn btn-primary" type="submit" style="visibility:visible">#localizer.GetLocalizedHtmlString("create")</button>
<a asp-controller="Banner" asp-action="index" class="btn btn-danger">#localizer.GetLocalizedHtmlString("cancel")</a>
</form>
<script>
window.addEventListener('DOMContentLoaded', function () {
'use strict';
var uppy = new Uppy.Core({
debug: true,
autoProceed: false,
locale: Uppy.locales.ru_RU
});
uppy.use(Uppy.Dashboard, {
inline: true,
target: '#drag-drop-area',
showProgressDetails: true,
height: 470,
browserBackButtonClose: false,
hideUploadButton: false
}).use(Uppy.XHRUpload, {
endpoint: '/wwwroot/images/tree/test',
formData: true,
fieldName: 'files[]',
});
uppy.use(Uppy.Form, {
target: 'form',
resultName: 'ImageUrl',
getMetaFromForm: true,
addResultToForm: true,
submitOnSuccess: true,
triggerUploadOnSubmit: true,
});
window.uppy = uppy;
});
</script>
</body>
public async Task Create(Command command,IFormFile? file)
{
string wwwRootPath = _hostEnvironment.WebRootPath;
if (file != null)
{
if (IsImage(file) == true)
{
string fileName = Guid.NewGuid().ToString();
var uploads = Path.Combine(wwwRootPath, #"images\banner");
var extension = Path.GetExtension(file.FileName);
if (command.ImageUrl != null)
{
var oldImagePath = Path.Combine(wwwRootPath, command.ImageUrl.TrimStart('\\'));
if (System.IO.File.Exists(oldImagePath))
{
System.IO.File.Delete(oldImagePath);
}
}
using (var fileStreams = new FileStream(Path.Combine(uploads, fileName + extension), FileMode.Create))
{
file.CopyTo(fileStreams);
}
command.ImageUrl = #"\images\banner\" + fileName + extension;
}
return View();
}
var viewModel = await _mediator.Send(command);
}
return View();
}

HttpPostedFileBase could not be found Visual studio 2019

hi,
i'm working on a asp.net core mvc with visual studio 2019,
(see attached for the mvc version (3.1.8).
i want to use HttpPostedFileBase, but getting error could not be found,
i've seen a solution suggesting to add using system.Web, and i did, but still getting this error,
Any ideas?
Edit:
Created the html :
<div class="col-md-6">
<div>
<input id="CSVFile" type="file">
</div>
<button onclick="Submit()">submit</button>
</div>
and javascript:
<script type="text/javascript">
function Submit() {
var pdata = new FormData();
var files = $("#CSVFile").get(0).files;
window.alert(files.Length);
pdata.append('CSVFile', files[0]);
$.ajax({
url: "Index",
type: "POST",
data: pdata,
processData: false,
contentType: false,
success: function (data) {
var input = $("#CSVFile");
input.replaceWith(input.val('').clone(true));
}
});
}
</script>
but the controller is not being called (it is defined HttpPost)
public ActionResult Index(IFormFile CSVFile)
{
return View();
}
.net core 3.1 doesn't contain HttpPostedFileBase.If you want to upload files,you can use IFormFile,here is an official tutorial.
Here is a simple demo to use IFormFile(from view to controller):
view:
<div class="row">
<div class="col-md-6">
<div>
<input id="CertImageFile" type="file">
</div>
<button onclick="Submit()">submit</button>
</div>
</div>
#section scripts{
<script type="text/javascript">
function Submit() {
var pdata = new FormData();
var files = $("#CertImageFile").get(0).files;
pdata.append('CertImageFile', files[0]);
$.ajax({
url: "Submit",
type: "POST",
data: pdata,
processData: false,
contentType: false,
success: function (data) {
var input = $("#CertImageFile");
input.replaceWith(input.val('').clone(true));
}
});
}
</script>
}
Controller:
[HttpGet]
public IActionResult TestIFormFile()
{
return View();
}
[HttpPost]
public IActionResult Submit(IFormFile CertImageFile)
{
return Ok();
}
result:

Jquery Mobile select Options menu[Phonegap Project]

I get informations about the product name , image, price, category etc from server but i put the informations in a select menus and i want when i change the options of the select menu i display an alert success here is my code:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
<script type="text/javascript" charset="utf-8" src="cordova.js"></script>
<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.10.2/jquery.min.js"></script>
<title></title>
</head>
<body onLoad="Extra(); " >
<div id="extra" >
</div>
<script type="text/javascript" >
function Extra()
{
var callData = JSON.stringify({"serviceName":"global_functions", "methodName":"getAcces","parameters":[]});
$.post("http://www.test.com/webservice/?contentType=application/json", callData, function(data)
{
$.each(data, function( index, value)
{
$("#extra").append('<div style="border:2px solid red" id="'+index+'"><h3>'+value["name"]+'</h3><img width="200px" src="http://www.test.com/'+value["image"]+'"><select class="comboextra" selected="selected" id="test'+index+'">');
$.each(value["items"],function(index1,value1)
{
$("#test"+index).append('<option prix="'+value1["prix"]+'"cat="'+value1["cat"]+'" value= "'+value1["id"]+'" >"'+value1["name"]+'"</option>');
});
$("#extra").append('</select><label>Quantity</label><input type="number" name="q_extra1" value="0" id="q_extra1" class="quantiteextra" style="width:80px"></div><div class="alert alert-success icon-money"> valeur <span class="totalprix">0</span> </div>')
//alert("test");
});
});
}
$(document).on("change", ".comboextra", function ()
{
alert($(this).find(".comboextra option:selected").attr("prix"));
id = $(this).val();
prix = $("option:selected", this).attr("prix")
qte = $(".quantiteextra").val();
acccat = $("option:selected", this).attr("cat");
total = prix * qte;
acccat = ($(this).find(".comboextra option:selected").attr("cat"));
if (id != 0){$('#finaldata').find("[acccat="+acccat+"]").remove(); $("#finaldata").append('<input type="tex00t" acccat="'+acccat+'" id="acc'+id+'" name="acc['+id+']" value="'+qte+'">');} else {$('#finaldata').find("[acccat="+acccat+"]").remove();}
$(this).find(".totalprix").html(total);
});
</script>
<body>
</html>
//////////////////////////////////////////////EDITED AGAIN//////////////////////////////////
I can now display the alert and i want to select the product from the select menu and add the quantity and calculate the price here is my code after modification it's displaying the alert and the value =0 , it's not calculating and not displaying any value even when i change the quantity and when i change the product:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.10.2/jquery.min.js"></script>
<title></title>
</head>
<body onLoad="Extra(); " >
<div id="extra" >
</div>
<div id="finaldata"></div>
<script type="text/javascript" >
function Extra()
{
var callData = JSON.stringify({"serviceName":"global_functions", "methodName":"getAcces","parameters":[]});
$.post("http://www.test.com/webservice/?contentType=application/json", callData, function(data)
{
$.each(data, function( index, value)
{
$("#extra").append('<div style="border:2px solid red" id="'+index+'"><h3>'+value["name"]+'</h3><img width="200px" src="http://www.test.com/'+value["image"]+'"><select class="comboextra" selected="selected" id="test'+index+'">');
$.each(value["items"],function(index1,value1)
{
$("#test"+index).append('<option prix="'+value1["prix"]+'"cat="'+value1["cat"]+'" value= "'+value1["id"]+'" >"'+value1["name"]+'"</option>');
});
$("#extra").append('</select><label>Quantity</label><input type="number" name="q_extra1" value="0" id="q_extra1" class="quantiteextra" style="width:80px"></div><div class="alert alert-success icon-money"> valeur <span class="totalprix">0</span> </div>')
//alert("test");
});
});
}
$(document).on("change", ".comboextra", function ()
{
alert($(this).find(".comboextra option:selected").attr("prix"));
id = $(this).val();
prix = $("option:selected", this).attr("prix")
qte = $(".quantiteextra").val();
acccat = $("option:selected", this).attr("cat");
total = prix * qte;
acccat = ($(this).find(".comboextra option:selected").attr("cat"));
if (id != 0){$('#finaldata').find("[acccat="+acccat+"]").remove(); $("#finaldata").append('<input type="tex00t" acccat="'+acccat+'" id="acc'+id+'" name="acc['+id+']" value="'+qte+'">');} else {$('#finaldata').find("[acccat="+acccat+"]").remove();}
$(this).find(".totalprix").html(total);
});
</script>
<body>
</html>
You should bind the change event when you have updated your document. Try adding the binding after you print the selects:
function Extra()
{
var callData = JSON.stringify({"serviceName":"global_functions", "methodName":"getAcces","parameters":[]});
$.post("http://www.test.com/webservice/?contentType=application/json", callData,
function(data)
{
$.each(data, function( index, value)
{
$("#extra").append('<div style="border:2px solid red" id="'+index+'"><h3>'+value["name"]+'</h3><img width="200px" src="http://www.test.com/'+value["image"]+'"><select class="comboextra" selected="selected" id="test'+index+'">');
$.each(value["items"],function(index1,value1)
{
$("#test"+index).append('<option prix="'+value1["prix"]+'"cat="'+value1["cat"]+'" value= "'+value1["id"]+'" >"'+value1["name"]+'"</option>');
});
$("#extra").append('</select><label>Quantity</label><input type="number" name="q_extra1" value="0" id="q_extra1" class="quantiteextra" style="width:80px"></div><div class="alert alert-success icon-money"> valeur <span class="totalprix">0</span> </div>')
});
$(".comboextra").change(function()
{
alert("success");
});
});
}

Jquery sortable index change to ASP.NET MVC controller

I am trying to get the model binder to recognize the change. I am not sure what I am missing here. Basically the initial page population pulls the page number from the database. I then have the sortable working, the raw HTML in Firebug shows the change in order. But when I post back to the model first off it is not figuring out to go the post method and the other issue is Survey. Pages does not seem to have the change in order.
View
#for (var i = 0; i < Model.Pages.Count; i++)
{
var page = Model.Pages.ElementAt(i);
#Html.Hidden("Pages[" + i + "].PageId", page.PageId, new { #class = "page_index" })
#Html.Hidden("Pages[" + i + "].PageNumber", page.PageNumber)
<li id="#page.PageId" class="sortable-item text-center ui-state-default"><span class="ui-icon ui-icon-arrowthick-2-n-s">
</span>#page.PageNumber</li>
}
</ul>
JavaScript
<script type="text/javascript">
$(document).ready(function () {
$('.sortable').sortable({
stop: function (event, ui) {
var formData = $('#editSurveryForm').serialize();
$.ajax({
url: "#Url.Action("Edit")",
data: formData,
type: 'POST',
traditional: true,
success: function () {
alert("success");
},
error: function () {
alert("fail");
}
}
);
}
});
});
</script>
Controller
[HttpPost]
public ActionResult Edit(Survey survey)
{
if (!ModelState.IsValid)
{
return View("EditSurvey", survey);
}
surveyRepository.UpdateSurvey(survey);
return RedirectToAction("Index", "Administration");
}
Ok, I figure this one out. I had the hidden fields outside of the <li></li> tag. Once I moved them inside I did all my logic as I would have.
<div class="span9">
<div class="span4">
<ul class="sortable_page_list">
#for (var i = 0; i < Model.Pages.Count; i++)
{
<li class="sortable-item text-center ui-state-default">
#Html.HiddenFor(model => model.Pages[i].PageId)
#Html.HiddenFor(model => model.Pages[i].PageNumber)
<span class="ui-icon ui-icon-arrowthick-2-n-s"></span>#Model.Pages[i].PageNumber
</li>
}
</ul>
<div class="span1 pull-right internal-wrapper">
#Html.ActionLink("Add", "AddPage", new { id = Model.SurveyId }, new { #class = "add_survey_icon common_icon_settings" })
</div>
</div>
</div>
<script type="text/javascript">
$(document).ready(function () {
$('.sortable_page_list').sortable({
update: function (event, ui) {
var counter = 1;
$("[id*='PageNumber']").each(function() {
$(this).attr("value", counter);
counter++;
});
//var surveyToUpdate = $('#editSurveyForm');
$.ajax({
url: '#Url.Action("Edit","Administration")',
contentType: "application/json; charset=utf-8",
data: $('#editSurveyForm').serialize(),
type: 'POST'
});
}
});
});
Last thing to figure out is why the ajax post is not posting to the Post method with the survey form data

Facing issue while showing the error messages in Partial View using unobstructive JQuery

Following is my Area in MVC3
Model
public class AdminModule
{
[Display(Name = "My Name")]
[Required]
public String MyName { get; set; }
}
Partial View
#model _1.Areas.Admin.Models.AdminModule
#using (Html.BeginForm(null, null, FormMethod.Post, new { id = "myForm" }))
{
#Html.LabelFor(i => i.MyName)
#Html.TextBoxFor(i => i.MyName)
#Html.ValidationMessageFor(i => i.MyName)
<p id="getDateTimeString">
</p>
<input type="submit" value="Click here" id="btn" />
}
<script language="javascript" type="text/javascript">
$('#btn1').click(function () {
debugger;
var $form = $("#myForm");
// Unbind existing validation
$form.unbind();
$form.data("validator", null);
// Check document for changes
$.validator.unobtrusive.parse(document);
// Re add validation with changes
$form.validate($form.data("unobtrusiveValidation").options);
if ($(this).valid()) {
var url = '#Url.Action("Index_partialPost", "Admin",
new { area = "Admin" })';
$.post(url, null, function (data) {
alert(data);
$('#myForm').html(data);
});
}
else
return false;
});
</script>
Controller Action
[HttpPost]
public ActionResult Index_partialPost(AdminModule model)
{
return PartialView("_PartialPage1", model);
}
[HttpGet]
public ActionResult Index_partial()
{
return PartialView("_PartialPage1");
}
Whenever I submit the form and leaves the required field empty. it goes to server i think. I checked here...
My confusion is => How can I modify my below mentioned code to display the same validation messages mentioned in model at client end using $.post ?
You could enable unobtrusive client side validation. Start by adding the following script reference:
<script type="text/javascript" src="#Url.Content("~/scripts/jquery.validate.unobtrusive.js")"></script>
and then:
#model _1.Areas.Admin.Models.AdminModule
#using (Html.BeginForm(null, null, FormMethod.Post, new { id = "myForm" }))
{
#Html.LabelFor(i => i.MyName)
#Html.TextBoxFor(i => i.MyName)
#Html.ValidationMessageFor(i => i.MyName)
<p id="getDateTimeString"></p>
<input type="submit" value="Click here" />
}
<script type="text/javascript">
$('#myForm').submit(function () {
if ($(this).valid()) {
$.post(this.action, $(this).serialize(), function(data) {
$('#myForm').html(data);
$('#myForm').removeData('validator');
$('#myForm').removeData('unobtrusiveValidation');
$.validator.unobtrusive.parse('#myForm');
});
}
return false;
});
</script>
UPDATE:
Now that you sent me your actual code by email I see that there are a hell lot of a problems with it. Instead of going through all of them I prefer to completely rewrite everything from scratch.
So we start by the ~/Areas/Admin/Views/Shared/_LayoutPage1.cshtml:
<!DOCTYPE html>
<html>
<head>
<title>#ViewBag.Title</title>
</head>
<body>
<div>
<ul>
<li>#Html.ActionLink("Home", "Index", "Home", new { area = "" }, null)</li>
</ul>
#RenderBody()
</div>
<script src="/Scripts/jquery-1.4.1.min.js" type="text/javascript"></script>
<script src="/Scripts/jquery.validate.js" type="text/javascript"></script>
<script src="/Scripts/jquery.validate.unobtrusive.js" type="text/javascript"></script>
#RenderSection("Scripts", required: false)
</body>
</html>
Notice how I moved all scripts to the bottom of the file as well as added a specifically dedicated section where custom scripts will be placed.
Next we move to the ~/Areas/Admin/Views/Admin/Index.cshtml:
#model _1.Areas.Admin.Models.AdminModule
#{
ViewBag.Title = "Index";
Layout = "~/Areas/Admin/Views/Shared/_LayoutPage1.cshtml";
}
<div id="formContainer" data-url="#Url.Action("Index_partial", "Admin", new { area = "Admin" })"></div>
<input id="BTN" type="button" value="Button" />
#section Scripts {
<script type="text/javascript" src="#Url.Content("~/areas/admin/scripts/myscript.js")"></script>
}
Here you could notice that I have replaced the type of the button from submit to button because this button is not contained within a form to submit. I have also gotten rid of the <p> element you were having with id="myForm" which was not only useless but you were ending up with duplicate ids in your DOM which is invalid markup. I have also used the data-url HTML5 attribute on the container div to indicate the url of the server side script that will load the form. And the last thing I did in this file was to override the scripts section we defined earlier in the Layout with a custom script.
So the next part is the custom script: ~/areas/admin/scripts/myscript.js:
$('#BTN').click(function () {
var $formContainer = $('#formContainer');
var url = $formContainer.attr('data-url');
$formContainer.load(url, function () {
var $form = $('#myForm');
$.validator.unobtrusive.parse($form);
$form.submit(function () {
var $form = $(this);
if ($form.valid()) {
$.post(this.action, $(this).serialize(), function (data) {
$form.html(data);
$form.removeData('validator');
$form.removeData('unobtrusiveValidation');
$.validator.unobtrusive.parse($form);
});
}
return false;
});
});
return false;
});
Pretty standard code here. We subscribe to the click event of the button and load the partial using an AJAX call. As soon as this is done we instruct the unobtrusive validation framework to parse the newly added contents to our DOM. The next step is to AJAXify the form by subscribing to the .submit event. And because in the success handler we are once again replacing the contents of the container we need to instruct the unobtrusive validation framework to parse the new contents.
and finally the partial:
#model _1.Areas.Admin.Models.AdminModule
#using (Html.BeginForm("Index_partialPost", "Admin", FormMethod.Post, new { id = "myForm" }))
{
#Html.LabelFor(i => i.MyName)
#Html.TextBoxFor(i => i.MyName)
#Html.ValidationMessageFor(i => i.MyName)
<p id="getDateTimeString"></p>
<input type="submit" value="Click here" />
}
Here you could notice that I have gotten rid of absolutely any traces of javascript. javascript belongs to separate files. It has nothing to do in views. You should not mix markup and scripts. When you have separate scripts not only that your dynamic markup will be much smaller but also you could take advantage of things like browser caching for the external scripts, minification, ... Another thing you will notice in this partial is that I remove the <script> nodes in which you were referencing jQuery and the jQuery.validate scripts. You already did that in the Layout, do not repeat it twice.

Resources