I have a asp.net MVC website where the user enters a social security number (SSN). The client wants to display a warning message if the SSN is already used, but doesn't want to force them to change the SSN (there are conditions under which multiple records can have the same SSN).
The MVC code I inherited has a validation to check if the SSN has already been used. The code works great. If the user enters a SSN that is already used, a message appears saying "SSN already exists" and prevents the form from being submitted. How can I change this so that the message is displayed, but so it doesn't prevent the form from being submitted?
ModelApplication.cs
[StringLength(9, MinimumLength = 9, ErrorMessage = "Please Enter 9 Digit SSN No")]
[Remote("IsSSNExist", "Admin", HttpMethod = "GET")]
public string ApplicantSSN { get; set; }
AdminController.cs
[HttpGet]
public JsonResult IsSSNExist(string ApplicantSSN)
{
if (Session["viewapp"] == null)
{
if (obj_BllApp.IsSSNExist(ApplicantSSN))
return Json("SSN already exists.", JsonRequestBehavior.AllowGet);
else
return Json(true, JsonRequestBehavior.AllowGet);
}
else
{
return Json(true, JsonRequestBehavior.AllowGet);
}
}
Application.cshtml
<label>
SSN
</label>
@Html.TextBoxFor(m => m.ApplicantSSN, new { @class = "input-small", @maxlength = "9", @onkeypress = "return ValidateNumberKeyPress(this, event);" })<br />
@Html.HiddenFor(m => m.ApplicantSSNID, new { id = "hdnApplicantSSN" })
span id="spAppSSn" class="SSNmsg">@Html.ValidationMessageFor(m => m.ApplicantSSN)</span>
UPDATE
I also tried using the response header like another poster suggested, but I couldn't get it to work.
This code didn't return anything and broke other javascript I had:
$(function () {
$("#txtApplicantSSN").change(function (xhr) {
alert("Hello");
var req = new XMLHttpRequest();
req.open('GET', document.location, false);
req.send(null);
var headers = req.getResponseHeader("SSN-DUPLICATED").toLowerCase();
alert(headers);
alert("Goodbye");
});
});
Using the same concept, I tried another way of getting the request header, but I never got a value. It looked like the validation that set the header value was being called after the javascript.
$(function () {
$("#txtApplicantSSN").change(function () {
var req = new XMLHttpRequest();
req.open('GET', document.location, false);
req.send(null);
var headers = req.getResponseHeader('SSN-DUPLICATED');
$("#remoteMessage").text(headers);
});
});
I tried something similar using session variables, but again the session variable seem to be getting set after the javascript code.
$(function () {
$("#txtApplicantSSN").change(function () {
var someSessionVariable = '@Request.RequestContext.HttpContext.Session["SSNExists"]';
alert(someSessionVariable);
$("#remoteMessage").text(someSessionVariable);
});
});
My current thought is to try to disable the validation when the submit button is clicked, but I haven't found a way to do it. I tried this
HtmlHelper.ClientValidationEnabled = false;
in the controller but it never hits the server side code. I get the validation error before it hits the controller.
Update #2
I disabled the validation when the submit button is clicked using the cancel class:
<input id="Submit1" type="submit" class="btn btn-primary cancel" value="Save" onclick="javascript: return ValidatonCoApplication();" />
This fixes the problem for this field, but disables validation for all other fields. Can someone suggest another way to do what I want without turning off validation?
In summary, this is asp.net MVC with Razor. After the user enters a SSN in a text box, I need a message to appear on the screen saying whether or not the SSN is valid. Currently I have a validation attribute in the model, but this is not only showing the message, it is declaring the model invalid and therefore not letting the user proceed to the next page. I want the validation message to appear, but do not want the model invalid. I'd appreciate any help you could give me. Thank you.
Since you only want to display a message based on the value of ApplicantSSN
(not invalidate the model), remove the [Remote]
attribute, and instead handle the .change()
event of the textbox to call a conroller method and return an appropriate message.
Controller
public JsonResult IsSSNExist(string ApplicantSSN)
{
bool isValid = // your logic
if (isValid)
{
return Json(null, JsonRequestBehavior.AllowGet);
}
else
{
return Json(true, JsonRequestBehavior.AllowGet);
}
}
View
@Html.TextBoxFor(m => m.ApplicantSSN) // remove the onkeypress attribute
// add a placeholder for the message
<span class="field-validation-error"><span id="ssn-message">The SSN already exists.</span></span>
css
#ssn-message {
display: none;
}
Script
var url = '@Url.Action("IsSSNExist")';
var ssnMessage = $('#ssn-message');
$('#ApplicantSSN').change(function() {
$.getJSON(url, { ApplicantSSN: $(this).val() }, function(response) {
if(response) {
ssnMessage.show();
} else {
ssnMessage.hide();
}
});
});
Note: If the user enters an invalid value and tabs out of the control, the message will be displayed. You may want additional logic to hide the message if the user then starts typing in the textbox again in whichcase you would alo need to handle the keyup event