Quel est le meilleur moyen d'effectuer une validation de formulaire côté client à l'aide de Javascript (avec une duplication minimale du code) lors de l'utilisation de la validation de bean JSR 303 côté serveur? J'utilise actuellement Spring 3 et le validateur Hibernate .
Réponses
Trop de publicités?Je suggère que vous regardez Printemps JS, qui s'appuie fortement sur le Dojo. Un tutoriel peut être trouvé ici.
Manière la plus facile pour vous de commencer à jouer avec elle, c'est de télécharger Spring Roo, créer la petclinic exemple d'application avec un des exemples de scripts (ce qui vous prend 5 minutes), puis de jouer avec la façon dont le javascript est intégré. Spring Roo crée une application avec la même technologie de la pile que vous utilisez (Spring+hibernate+mise en œuvre de la jsr 303)
J'ai trouvé ce projet open source, mais il semble morte, peut-être il vaut la peine de ressusciter.
http://kenai.com/projects/jsr303js/pages/Home
Cette bibliothèque fournit la validation côté client d'un formulaire HTML basé sur la norme JSR-303 et Hibernate Validator annotations, intégré avec Spring MVC. La bibliothèque fournit une validation JavaScript base de code qui gère la base de l'interaction avec les formulaires HTML, ainsi que des fonctions JavaScript à la mise en œuvre de la validation des annotations pris en charge par Hibernate Validator (y compris ceux qui ne sont pas de la JSR-303 spec). Ce code JavaScript de base peuvent être inclus dans une page en utilisant une bibliothèque de tags ou par l'extraction du fichier JavaScript à partir du bocal et y compris à l'aide d'une balise. Une fois cette base de code a été inclus dans une page, une deuxième taglib est utilisé pour générer le code JavaScript pour la validation d'un formulaire HTML. Vous pouvez également fournir un objet JSON dans le corps de la balise pour spécifier des informations de configuration supplémentaires.
Voici comment je le fais à l'aide de Spring MVC + JQuery + Bootstrap, fondées en partie sur un récent billet de blog à SpringSource:
AddressController.java
@RequestMapping(value="/validate")
public @ResponseBody ValidationResponse processForm(Model model, @Valid AddressForm addressForm, BindingResult result) {
ValidationResponse res = new ValidationResponse();
if (result.hasErrors()) {
res.setStatus("FAIL");
for (ObjectError error : result.getAllErrors()) {
if (error instanceof FieldError) {
FieldError fieldError = (FieldError) error;
res.addError(fieldError.getField(), fieldError.getDefaultMessage());
}
}
}
else {
res.setStatus("SUCCESS");
}
return res;
}
AddressForm.java
public class AddressForm {
@NotNull
@Size(min=1, max=50, message="Address 1 is required and cannot be longer than {max} characters")
private String address1;
@Size(max=50, message="Address 2 cannot be longer than {max} characters")
private String address2;
// etc
}
ValidationResponse.java:
public class ValidationResponse {
private String status;
private Map<String,String> errors;
// getters, setters
}
adresse.jsp:
<f:form commandName="addressForm">
<div class="control-group">
<label for="address1">Address 1</label>
<div class="controls">
<f:input path="address1" type="text" placeholder="Placeholder Address 1" class="wpa-valid" />
<span class="help-inline"></span>
</div>
</div>
<!-- etc -->
<div class="form-actions">
<button type="submit" class="btn btn-primary">Save</button>
<button type="button" class="btn">Cancel</button>
</div>
</f:form>
<script type="text/javascript">
function collectFormData($fields) {
var data = {};
for (var i = 0; i < $fields.length; i++) {
var item = $($fields[i]);
data[item.attr("id")] = item.val();
}
return data;
}
function clearErrors($fields) {
for (var i = 0; i < $fields.length; i++) {
var item = $($fields[i]);
$("#"+item.attr("id")).parents(".control-group").removeClass("error");
$("#"+item.attr("id")).siblings(".help-inline").html("");
}
}
function markErrors(errors) {
$.each(errors, function(key, val) {
$("#"+key).parents(".control-group").addClass("error");
$("#"+key).siblings(".help-inline").html(val);
});
}
$(document).ready(function() {
var $form = $("form.validate");
$form.bind("submit", function(e) {
var $fields = $form.find(".validate");
clearErrors($fields);
var data = collectFormData($fields);
var validationUrl = "validate";
$.get(validationUrl, data, function(response) {
$("#alert").removeClass();
if (response.status == "FAIL") {
markErrors(response.errors);
$("#alert").addClass("alert alert-error");
$("#alert").html("Correct the errors below and resubmit.");
} else {
$("#alert").addClass("alert alert-success");
$("#alert").html("Success!");
$form.unbind("submit");
$form.submit();
}
}, "json");
e.preventDefault();
return false;
});
});
</script>
Il pourrait utiliser un peu de refactoring, mais cela va faire une requête ajax avec la forme de données et de mise à jour de la page basée sur le résultat.
Richfaces le supporte. Ils ont une petite démo sur leur site .