MVC form doesn't validate - asp.net-mvc-3

I am very new to MVC 3.
I am using custom helpers for the controls but when i submit the form, the control is not being validated.
Can some one tell me if i am missing something? Following is the code snippet.
public static MvcHtmlString TextBox(string fieldName)
{
TagBuilder tagBuilder = new TagBuilder("Input");
tagBuilder.MergeAttribute("type", "Text");
tagBuilder.AddCssClass("text-box");
tagbuilder.MergeAttribute("data-val","true");
tagbuilder.MergeAttribute("data-val-regex-pattern","true");
tagbuilder.MergeAttribute("data-val","true");
TagBuilder validator = new TagBuilder("span");
validator.MergeAttribute("data-valmsg-for", fieldName);
validator.MergeAttribute("data-valmsg-replace", "true");
validator.MergeAttribute("class", "field-validation-valid");
return new MvcHtmlString(string.Concat(tagBuilder.ToString(), validator.ToString()));
}
The view has the following code
#using (Html.BeginForm())
{
#Html.ValidationSummary(true)
<div class="main-border" style="width: 890px;">
<div style="clear: both;">
</div>
<div style="padding: 0px 20px 0px 20px;">
<table style="width: 100%">
<tr>
<td colspan="2" class="main-subhead2">
<div class="label-text">
</div>
</td>
</tr>
<tr>
<td>Email :</td>
<td>#ControlHelper.TextBox("txtEmailAddress")</td>
</tr>
<tr>
<td></td>
<td><input type="submit" value="submit" onclick="return validate(this.form);" /></td>
</tr>
</table>
</div>
</div>
}
the source code of rendered by the page is :
<form action="/" method="post">
<div class="main-border" style="width: 890px;">
<div style="clear: both;">
</div>
<div style="padding: 0px 20px 0px 20px;">
<table style="width: 100%">
<tr>
<td colspan="2" class="main-subhead2">
<div class="label-text">
</div>
</td>
</tr>
<tr>
<td>Email :</td>
<td><Input class="text-box" data-val="True" data-val-regex-pattern="^([0-9a-zA-Z]([-\.\w]*[0-9a-zA-Z]))*#[A-Za-z0-9_\.-]+[A-Za-z0-9_][A-Za-z0-9_]$" name="txtEmailAddress" type="Text" visible="True"></Input><span class="field-validation-valid" data-valmsg-for="txtEmailAddress" data-valmsg-replace="true"></span></td>
</tr>
<tr>
<td></td>
<td><input type="submit" value="submit" /></td>
</tr>
</table>
</div>
</div>
</form>

Input should be lowercased:
TagBuilder tagBuilder = new TagBuilder("input");
And don't forget to include the unobtrusive client side validation scripts to your page:
<script src="#Url.Content("~/Scripts/jquery.validate.js")" type="text/javascript"></script>
<script src="#Url.Content("~/Scripts/jquery.validate.unobtrusive.js")" type="text/javascript"></script>
and ensure that client side validation is enabled in web.config:
<appSettings>
<add key="ClientValidationEnabled" value="true"/>
<add key="UnobtrusiveJavaScriptEnabled" value="true"/>
</appSettings>

There are a number of reasons your form may not validating. In MVC3, you're most likely going to want to use unobtrusive validation (via jQuery). You can learn how to do this (it's not a big change - just include the correct JavaScript libraries and update web.config) at Microsoft's ASP.NET website.

You may need to add (data-val-regex) attribute:
public static MvcHtmlString TextBox(string fieldName)
{
TagBuilder tagBuilder = new TagBuilder("Input");
tagBuilder.MergeAttribute("type", "Text");
tagBuilder.AddCssClass("text-box");
tagbuilder.MergeAttribute("data-val","true");
tagbuilder.MergeAttribute("data-val-regex-pattern","true");
tagbuilder.MergeAttribute("data-val","true");
tagbuilder.MergeAttribute("data-val-regex","Field must be character (?![ء|ئ|ؤ])[ء-يA-Za-z]");
TagBuilder validator = new TagBuilder("span");
validator.MergeAttribute("data-valmsg-for", fieldName);
validator.MergeAttribute("data-valmsg-replace", "true");
validator.MergeAttribute("class", "This is an invalid Email format!");
return new MvcHtmlString(string.Concat(tagBuilder.ToString(), validator.ToString()));
}

Related

Spring Boot doesnt return template in Post Mapping

I hope some of you have an idea about this. I'm still new to Spring but till this point I could figured out every problem myself. I'm using also Thymeleaf for the templates.
In the Controller the function for #GetMapping works as intended, but the #PostMapping function doesnt return the template which I specified in the return parameter and so the browser shows the wrong page.
The #PostMapping function gets triggered by the ajax statement in the html script.
I get no errors or warnings on server side as well as on client side. So I have no idea were the spot the mistake.
Hope some of you can spot the mistake. Thanks in advance anyway.
Controller:
#Controller
public class SpringController {
#RequestMapping(value="/tank", method = RequestMethod.GET)
public String loadData(Model model){
Tankstelle[] data = TankerAPI.getTankData(lat, lng, 5, sort, type);
model.addAllAttributes(convertdata("name", data));
model.addAllAttributes(convertdata("dist", data));
model.addAllAttributes(convertdata("price", data));
return "home";
}
#RequestMapping(value = "/tank", method = RequestMethod.POST)
public String getChangedData(#RequestBody JSONObject incomingjson) {
lat = Float.parseFloat(incomingjson.get("lat").toString());
lng = Float.parseFloat(incomingjson.get("lng").toString());
BigDecimal biglat = new BigDecimal(lat).setScale(3, RoundingMode.HALF_UP);
BigDecimal biglng = new BigDecimal(lng).setScale(3, RoundingMode.HALF_UP);
lat = biglat.floatValue();
lng = biglng.floatValue();
sort = "price"; //for seeing a difference
System.out.println(incomingjson.get("lat")+" "+incomingjson.get("lng"));
return "test"; //here it should return the template "test" but it return "home"
}
home.html:
<!DOCTYPE html>
<html lang="en" xmlns:th="http://www.thymeleaf.org/">
<head>
<meta charset="UTF-8"/>
<title>guenstigertanken.de</title>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>
<style>...
</style>
</head>
<body onload="getLocation()">
<div class="ueberschriftbox"></div>
<h2 class="header">guenstigertanken.de</h2>
<h2 class="subheader">Wir finden die günstigsten Spritpreise für Sie</h2>
<div class="backrounding">
<div class="steuerelementebox"></div>
<div class="steuerelementespritsorteueberschrift">
<h2>Spritsorte</h2>
<label class="container1">Super E5
<input type="radio" id="E5" name="radio1" onclick="autoSubmit()">
<span class="checkmark1"></span>
</label>
<label class="container1">Super E10
<input type="radio" id="E10" name="radio1" onclick="autoSubmit()">
<span class="checkmark1"></span>
</label>
<label class="container1">Diesel
<input type="radio" id="Diesel" name="radio1" onclick="autoSubmit()">
<span class="checkmark1"></span>
</label>
</div>
<div class="steuerelementesortierennachueberschrift">
<h2>Sortieren nach</h2>
<label class="container2">Preis aufsteigend
<input type="radio" checked="checked" name="radio2" onclick="autoSubmit()">
<span class="checkmark2"></span>
</label>
<label class="container2">Preis absteigend
<input type="radio" name="radio2" onclick="autoSubmit()">
<span class="checkmark2"></span>
</label>
<label class="container2">Distanz aufsteigend
<input type="radio" name="radio2" onclick="autoSubmit()">
<span class="checkmark2"></span>
</label> <label class="container2">Distanz absteigend
<input type="radio" name="radio2" onclick="autoSubmit()">
<span class="checkmark2"></span>
</label>
<label class="container2" id="alph">Name alphabetisch
<input type="radio" name="radio2" onclick="autoSubmit()">
<span class="checkmark2"></span>
</label>
</div>
<div class="buttonsbox"></div>
<div class="tabellenbox"></div>
<div class="ueberuns">
<p>Über uns</p>
</div>
<div class="agb">
<p>AGB</p>
</div>
<div class="datenschutz">
<p>Datenschutz</p>
</div>
<div class="impressum">
<p>Impressum</p>
</div>
<div class="left show">
<table id="datatable">
<thead>
<tr> <th>Name</th> <th>Entfernung</th> <th>Preis</th> <th>Favorit</th> </tr>
</thead>
<tbody>
<tr> <td th:text="${name1}">AGIP</td> <td th:text="${dist1}">7km</td> <td th:text="${price1}">1,20€</td> <td><input type="checkbox"></td> </tr>
<tr> <td th:text="${name2}">Aral</td> <td th:text="${dist2}">12km</td> <td th:text="${price2}">1,23€</td> <td><input type="checkbox"></td> </tr>
<tr> <td th:text="${name3}">Esso</td> <td th:text="${dist3}">2km</td> <td th:text="${price3}">1,25€</td> <td><input type="checkbox"></td> </tr>
<tr> <td th:text="${name4}">Esso</td> <td th:text="${dist4}">10km</td> <td th:text="${price4}">1,25€</td> <td><input type="checkbox"></td> </tr>
<tr> <td th:text="${name5}">Esso</td> <td th:text="${dist5}">5km</td> <td th:text="${price5}">1,25€</td> <td><input type="checkbox"></td> </tr>
<tr> <td th:text="${name6}">BP</td> <td th:text="${dist6}">13km</td> <td th:text="${price6}">1,35€</td> <td><input type="checkbox"></td> </tr>
<tr> <td th:text="${name7}">BP</td> <td th:text="${dist7}">13km</td> <td th:text="${price7}">1,35€</td> <td><input type="checkbox"></td> </tr>
<tr> <td th:text="${name8}">BP</td> <td th:text="${dist8}">13km</td> <td th:text="${price8}">1,35€</td> <td><input type="checkbox"></td> </tr>
</tbody>
</table>
</div>
</div>
<a class="cssbuttonfavoriten" href="test.html">Favoriten></a>
<a class="cssbuttonleaderboard" href="test.html">Leaderboard></a>
<a class="cssbuttonstatistiken" href="test.html">Statistiken></a>
<script>
function getLocation() {
if (navigator.geolocation) {
navigator.geolocation.getCurrentPosition(showPosition);
} else {
}
}
function showPosition(position) {
var posdata = '{"lat":"'+position.coords.latitude+'","lng":"'+position.coords.longitude+'","typeselect":"'+type+'"}';
$.ajax({
type: 'post',
url: '/tank',
data: JSON.stringify(posdata),
contentType: "application/json; charset=utf-8",
traditional: true,
success: function(posdata) {
//alert("ajax success: refresh page to sort after price[prob current setting]")
},
error: function(){
alert("ajax error")
}
});
}
</script>
</body>
</html>
When you make any request through ajax you just receive corresponding response in your callback function:
success: function(posdata) {
//alert("ajax success: refresh page to sort after price[prob current setting]")
},
So browser will not show you a new template page. Your page is in "postdata" response

Dynamic row thymeleaf

I want to create dynamic adding and removing list rows in Thymeleaf and Spring Boot.
I don't know how to use thymeleaf in dynamic rows, but i am trying to do it
So this is my code:
public class Form{
private List<Obj> list = new ArrayList<>();
//...
}
public class Obj{
private String a;
}
Controller:
#GetMapping("/form")
public String form(Model model) {
model.addAttribute("form", new Form());
return "/form";
}
HTML:
[...]
<form class="form-horizontal row-border" action="#" th:action="#{/form}" th:object="${form}" method="post">
<div class="form-group">
<div class="col-md-12">
<div class="row">
<label class="col-md-2 control-label">...</label>
<div class="col-md-10">
<table id="myTable" class=" table order-list">
<thead>
<tr>
<td>String</td>
</tr>
</thead>
<tbody>
<tr th:each="row:${list}">
<td class="col-sm-1">
1
</td>
<td class="col-sm-3">
<input th:field="*{list[__${row.index}__].a}" type="text" name="xyz" class="form-control"/>
</td>
</tr>
</tbody>
<tfoot>
<tr>
<td colspan="5" style="text-align: left;">
<input type="button" class="btn btn-lg btn-block " id="addrow" value="Add row" />
</td>
</tr>
<tr>
</tr>
</tfoot>
</table>
</div>
</div>
</div>
</div>
</form>
[...]
but i don't know how to get send data from form to controller
The controller recieves your data based on the input names. th:field sets your input name in the proper way so the controller will recieve it.
Sadly, if you add a new row in the client, where thymeleaf doesn't exist anymore, you have to set the proper name manually. You can look up for which name to set in your new row inputs with a js function like this (or any other way):
var nextRow = 0;
while($("input[name='list[" + nextRow + "].a']").length){
nextRow ++;
}
nextRow will have the next free row, just use it to build a name in the fashion of the ones thymeleaf generates and set it as your new input's name.

Dynamically inserted textbox values to be stored in a variable

<tr style="background: #D0CDCD;">
<td colspan='2'>
<input type="text" name="mytext1[]">
</td>
<td></td>
<td colspan='2' style="text-align:right;">
<input type="text" name="mytext2[]" id="txt1" onkeyup="sum();">
</td>
</tr>
This is my html code to add dynamic textboxes.
JS Script is follows
<script type="text/javascript">
$(document).ready(function() {
var max_fields= 3;
var x = 1;
$('a').click(function() {
if(x < max_fields){
x++;
$('#myTable #row').append('<tr class="child"><td class="child" colspan="2"><input type="text" name="mytext1[]"></td><td></td><td colspan="2" style="text-align:right;"><input type="text" name="mytext2[]"></td></tr>');
}
});
});
</script>
My problem is that I need to store the dynamically added textbox values to a variable so that I can perform some mathematical operations in that. I don't know how to achieve this. Please help me.
I got the result. I make use of javascript and jQuery
<tr style="background: #D0CDCD;">
<td colspan='2'><input type="text" name="mytext1[]"></td>
<td></td>
<td colspan='2' style="text-align:right;">
<input type="text" class="value_field" name="mytext2[]" >
</td>
</tr>
Function to append
<script type="text/javascript">
$(document).ready(function() {
$('a').click(function() {
$('#myTable #row').append('<tr class="child"><td class="child" colspan="2"><input type="text" name="mytext1[]"></td><td></td><td colspan="2" style="text-align:right;"><input type="text" name="mytext2[]" class="value_field"></td></tr>');
$("input.value_field").blur(function(){
check_value();
});
});
});
$("input.value_field").blur(function(){
check_value();
});

How to know from which jsp page the request has come to the controller in Spring MVC

I am developing an app where LoginForm.jsp and UserRegistration.jsp will lead to UserAccount jsp page on specific action.In LoginForm when a user presses a 'Login' button ->UserAccount form is displayed.In UserRegistration Form when details are entered and submitted ->UserAccount form is displayed.
Below is the controller code when a request comes as UserAccount.html
#RequestMapping(value="/UserAccount.html", method = RequestMethod.POST)
public ModelAndView userAccountForm(#Valid #ModelAttribute("user") UserDetails user,BindingResult result) {
if(result.hasErrors())
{ System.out.println(result.getAllErrors());
ModelAndView model1=new ModelAndView("UserRegistration");
return model1;
}
// User validation
System.out.println(user.getAccountType());
userDAO.create(user);
ModelAndView model1 = new ModelAndView("UserAccount");
return model1;
}
LoginForm.jsp
<%# taglib prefix="form" uri="http://www.springframework.org/tags/form"%>
<html>
<body>
<h1
style="background-color: green; color: Yellow; padding: 10px; text-align: center;">Mybank
Online Login</h1>
<form:errors path="user.*" />
<form action="/MyBankProject/UserAccount.html" method="post">
<div
style="background-color: yellow; color: black; padding: 10px; text-align: center;"
align="center">
<p>
User ID <input type="text" name="userName" />
</p>
<p>
Password <input type="password" name="password" />
</p>
<input type="submit" value="Login" /> New User?
</div>
<input type="hidden" name="page" value="LoginForm"/>
</form>
</body>
</html>
UserRegistration.jsp
<%# taglib prefix="form" uri="http://www.springframework.org/tags/form"%>
<html>
<body>
<h1>${headerMessage}</h1>
<h3>USER REGISTRATION</h3>
<form:errors path="user.*" />
<form action="/MyBankProject/UserAccount.html" method="post">
<table border="1" style="width:100%" >
<tr>
<td>FirstName :</td>
<td><input type="text" name="firstName" /></td>
</tr>
<tr>
<td>LastName :</td>
<td><input type="text" name="lastName" /></td>
</tr>
<tr>
<td>User's EmailId :</td>
<td><input type="text" name="emailId" /></td>
</tr>
<tr>
<td>user's gender :</td>
<td><select name="gender" multiple>
<option value="M">Male</option>
<option value="F">Female</option>
</select></td>
</tr>
<tr>
<td>user's age :</td>
<td><input type="text" name="age" /></td>
</tr>
<tr>
<td>user's DOB :</td>
<td><input type="text" name="dOB" /></td>
</tr>
<tr>
<td>Account Type :</td>
<td><select name="accountType" multiple>
<option value="Savings">Savings</option>
<option value="Current">Current</option>
<option value="FixedDeposit">Fixed Deposit</option>
</select>
<td>
</tr>
<tr>
<td>Amount :</td>
<td><input type="text" name="amount" /></td>
</tr>
</table>
<table>
<tr>
<td>UserName</td>
<td><input type="text" name="userName" /></td>
</tr>
<tr>
<td>Password</td>
<td><input type="password" name="password" /></td>
</tr>
</table>
<table>
<tr>
<td>User's Address :</td>
</tr>
<tr>
<td>country: <input type="text" name="address.country" /></td>
<td>city: <input type="text" name="address.city" /></td>
<td>street: <input type="text" name="address.street" /></td>
<td>pincode:<input type="text" name="address.pincode" /></td>
</tr>
<tr>
<td><button type="submit">Submit</button></td>
<td><input type="button" onclick="history.back();"
value="Cancel"></td>
</tr>
</table>
<input type="hidden" name="page" value="UserRegistration"/>
</form>
</body>
</html>
Now for me I need to know the jsp page from which the UserAccount invoked ,to perform different actions based on that.
I am new to Spring MVC and searched all over the internet for the solution.
HTTP is a stateless protocol. This means that you can not make assumptions about previous states.
I think you have two options to get information about the previous page anyways.
Add a hidden field to your form and send the name of the page with the request.
HTML:
<form>
<input type="hidden" name="page" value="[the name of the current page]"/>
</form>
Controller:
#RequestMapping(value="/UserAccount.html", method = RequestMethod.POST)
public ModelAndView userAccountForm(#RequestParam(value="page", required=false) String page) {
[...]
}
Now you can check the page value.
Use the session. Store the current page in the controller methods that render the form:
#RequestMapping("/login")
public String login(HttpServletRequest request) {
request.getSession().setAttribute("lastPage", "login");
return "redirect:/UserAccount.html";
}
#RequestMapping("/register")
public String register(HttpServletRequest request) {
request.getSession().setAttribute("lastPage", "register");
return "redirect:/UserAccount.html";
}
Check the lastPage value in userAccountForm():
#RequestMapping(value="/UserAccount.html", method = RequestMethod.POST)
public ModelAndView userAccountForm(HttpServletRequest request) {
HttpSession session = request.getSession();
String lastPage = (String) session.getAttribute("lastPage");
session.removeAttribute("lastPage");
[...]
}
Check the referer field of the request header.
#RequestMapping(value="/UserAccount.html", method = RequestMethod.POST)
public ModelAndView userAccountForm(#RequestHeader(value = "referer", required = false) String referer) {
[...]
}
This gives you the referer as a method argument if there is one. Be careful. It is possible that there was no referer or that the field was manipulated by the client.
Hope this will solve your need.
URL url = new URL(request.getHeader("referer"));
System.out.println("last page url"+ url.getPath());
if(url.getPath().equals("your last url"){
//code
}

issue with validation in asp.net mvc3

i am system.datamodel.dataannotation for validating my views.
below is my Model for the view.
using System.ComponentModel.DataAnnotations;
public class LoginVM
{
[Required(ErrorMessage="Please provide UserName")]
public string UserName { get; set; }
public string Password { get; set; }
}
below is my view for Login
<% using (Html.BeginForm())
{ %>
<% Html.ValidationSummary(true); %>
<div style="width: 100%; height: 100%; border-style: none;">
<fieldset style="border-style: none;">
<table style="width: 100%; height: 100%; border-style: none;" border="0">
<tr>
<td style="height: 100px;" colspan="4">
</td>
<td class="editor-label" style="width: 35%; font-size: medium; vertical-align: top;
text-align: justify;">
<%: Html.Label("Sign in with your Account Credentials")%><br />
<br />
Support / Contact Us
</td>
<td style="width: 5%;">
</td>
<td style="width: 60%; border-left-width: 2px; border-left-color: #E3E3E3; border-left-style: solid;">
<table style="border-style: none;" border="0">
<tr>
<td colspan="3">
</td>
</tr>
<tr style="height: 30px;">
<td style="width: 20%;" class="login-display-label">
<%: Html.LabelFor(m=>m.UserName,"UserName :") %><br />
<br />
<%: Html.LabelFor(m=>m.Password,"Password :") %><br />
<br />
</td>
<td style="width: 182px;" colspan="2">
<%: Html.TextBoxFor(m=>m.UserName,"UserName :")%><br />
<%: Html.ValidationMessageFor(m=>m.UserName) %><br />
<%: Html.TextBoxFor(m=>m.Password,"Password :")%><br />
<%: Html.ValidationMessageFor(m=>m.Password) %><br />
</td>
</tr>
<tr>
<td>
&nbsp
</td>
<td style="width: 182px;" colspan="3">
<input type="button" id="btnSubmit" value="Submit" />
</td>
</tr>
</table>
</td>
</tr>
</table>
</fieldset>
</div>
below is the scripts i have putted on my view as well as my site.master page
<script src="../../Scripts/jquery-1.5.1.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>
i have also checked my web.config for below markup
<appSettings>
<add key="ClientValidationEnabled" value="true"/>
<add key="UnobtrusiveJavaScriptEnabled" value="true"/>
after lots of effort my validation doesnt occur please help me....
let me known what necessary change i have to make.
thnaks in advance
change javascript Address:
<script src="#Url.Content("~/Scripts/jquery-1.5.1.js")" type="text/javascript"></script>
<script src="#Url.Content("~/Scripts/jquery.validate.js")" type="text/javascript"></script>
<script src="#Url.Content("~/Scripts/jquery.validate.unobtrusive.js")" type="text/javascript"></script>
and Html Helper
Html.TextBoxFor(m=>m.UserName)

Resources