[Buix-commits] r1177 - in jaxx/trunk/jaxx-runtime-validator/src: main/java/jaxx/runtime/validator/field main/resources test/java/jaxx/runtime/validator/field test/resources test/resources/jaxx/runtime/validator/field
Author: tchemit Date: 2009-01-23 12:12:53 +0000 (Fri, 23 Jan 2009) New Revision: 1177 Added: jaxx/trunk/jaxx-runtime-validator/src/main/java/jaxx/runtime/validator/field/CollectionUniqueKeyValidator.java jaxx/trunk/jaxx-runtime-validator/src/test/java/jaxx/runtime/validator/field/CollectionUniqueKeyValidatorTest.java Modified: jaxx/trunk/jaxx-runtime-validator/src/main/java/jaxx/runtime/validator/field/CollectionFieldExpressionValidator.java jaxx/trunk/jaxx-runtime-validator/src/main/resources/validators.xml jaxx/trunk/jaxx-runtime-validator/src/test/resources/jaxx/runtime/validator/field/ValidatorBean-validation.xml jaxx/trunk/jaxx-runtime-validator/src/test/resources/log4j.properties Log: ajout d'un validateur pour tester l'unicit?\195?\169 d'une clef dans une collection Modified: jaxx/trunk/jaxx-runtime-validator/src/main/java/jaxx/runtime/validator/field/CollectionFieldExpressionValidator.java =================================================================== --- jaxx/trunk/jaxx-runtime-validator/src/main/java/jaxx/runtime/validator/field/CollectionFieldExpressionValidator.java 2009-01-22 15:28:17 UTC (rev 1176) +++ jaxx/trunk/jaxx-runtime-validator/src/main/java/jaxx/runtime/validator/field/CollectionFieldExpressionValidator.java 2009-01-23 12:12:53 UTC (rev 1177) @@ -42,7 +42,7 @@ @Override public void validate(Object object) throws ValidationException { if (mode == null) { - throw new ValidationException("no mode was setted"); + throw new ValidationException("no mode defined"); } String fieldName = getFieldName(); Copied: jaxx/trunk/jaxx-runtime-validator/src/main/java/jaxx/runtime/validator/field/CollectionUniqueKeyValidator.java (from rev 1173, jaxx/trunk/jaxx-runtime-validator/src/main/java/jaxx/runtime/validator/field/CollectionFieldExpressionValidator.java) =================================================================== --- jaxx/trunk/jaxx-runtime-validator/src/main/java/jaxx/runtime/validator/field/CollectionUniqueKeyValidator.java (rev 0) +++ jaxx/trunk/jaxx-runtime-validator/src/main/java/jaxx/runtime/validator/field/CollectionUniqueKeyValidator.java 2009-01-23 12:12:53 UTC (rev 1177) @@ -0,0 +1,137 @@ +package jaxx.runtime.validator.field; + +import com.opensymphony.xwork2.validator.ValidationException; +import com.opensymphony.xwork2.validator.validators.FieldExpressionValidator; +import org.apache.commons.lang.builder.HashCodeBuilder; + +import java.util.ArrayList; +import java.util.Collection; +import java.util.List; + +/** + * Un validateur basé sur {@link FieldExpressionValidator} qui valide une clef + * unique sur une collection. + * <p/> + * Le {@link #fieldName} sert à récupérer la propriété de type de collection du bean. + * + * @author chemit + */ +public class CollectionUniqueKeyValidator extends FieldExpressionValidator { + + + public enum Mode { + /** au moins une entrée de la collection doit etre valide */ + AT_LEAST_ONE, + /** exactement une entrée dela collection doit être valide */ + EXACTLY_ONE, + /** toutes les valeurs de la collection doivent etre valides */ + ALL, + /** aucune valeur de la collection doivent etre valides */ + NONE + } + + /** + * la liste des propriétés d'une entrée de la collection qui définit la + * clef unique. + */ + protected String[] keys; + + public String[] getKeys() { + return keys; + } + + public void setKeys(String[] keys) { + this.keys = keys; + } + + @Override + public void validate(Object object) throws ValidationException { + + if (keys == null || keys.length == 0) { + throw new ValidationException("no unique keys defined"); + } + + String fieldName = getFieldName(); + + Collection<?> col = getCollection(object); + + if (col.size() < 2) { + // la liste ne contient pas deux entrées donc c'est valide + return; + } + + boolean answer = true; + + List<Integer> hashCodes = new ArrayList<Integer>(); + + for (Object o : col) { + Integer hash = getUniqueKeyHashCode(o); + if (hashCodes.contains(hash)) { + // on a deja rencontre cette clef unique, + // donc la validation a echouee + answer = false; + break; + } + + // nouveau hashcode enregistre + hashCodes.add(hash); + } + + if (!answer) { + addFieldError(fieldName, object); + } + } + + /** + * Calcule pour une entrée donné, le hash de la clef unique + * + * @param o l'entree de la collection dont on va calculer le hash de la clef unique + * @return le hashCode calclé de la clef unique sur l'entrée donné + * @throws ValidationException if any pb to retreave properties values + */ + protected Integer getUniqueKeyHashCode(Object o) throws ValidationException { + // calcul du hash à la volée + HashCodeBuilder builder = new HashCodeBuilder(); + for (String key : this.keys) { + Object property = getFieldValue(key, o); + builder.append(property); + } + return builder.toHashCode(); + } + + /** + * @param object the incoming object containing the collection to test + * @return the collection of the incoming object given by the fieldName property + * @throws ValidationException if any pb to retreave the collection + */ + protected Collection<?> getCollection(Object object) throws ValidationException { + String fieldName = getFieldName(); + + Object obj = null; + + // obtain the collection to test + try { + obj = getFieldValue(fieldName, object); + } catch (ValidationException e) { + throw e; + } catch (Exception e) { + // let this pass, but it will be logged right below + } + + if (obj == null) { + // la collection est nulle, donc on renvoie une collection vide + return java.util.Collections.EMPTY_LIST; + } + + if (!Collection.class.isInstance(obj)) { + throw new ValidationException("field " + fieldName + " is not a collection type! (" + obj.getClass() + ")"); + } + return (Collection<?>) obj; + } + + @Override + public String getValidatorType() { + return "collectionUniqueKey"; + } + +} \ No newline at end of file Property changes on: jaxx/trunk/jaxx-runtime-validator/src/main/java/jaxx/runtime/validator/field/CollectionUniqueKeyValidator.java ___________________________________________________________________ Name: svn:mergeinfo + Modified: jaxx/trunk/jaxx-runtime-validator/src/main/resources/validators.xml =================================================================== --- jaxx/trunk/jaxx-runtime-validator/src/main/resources/validators.xml 2009-01-22 15:28:17 UTC (rev 1176) +++ jaxx/trunk/jaxx-runtime-validator/src/main/resources/validators.xml 2009-01-23 12:12:53 UTC (rev 1177) @@ -12,5 +12,7 @@ <validator name="notExistingDirectory" class="jaxx.runtime.validator.field.NotExistingDirectoryFieldValidator"/> <validator name="collectionFieldExpression" class="jaxx.runtime.validator.field.CollectionFieldExpressionValidator"/> + <validator name="collectionUniqueKey" + class="jaxx.runtime.validator.field.CollectionUniqueKeyValidator"/> </validators> <!-- END SNIPPET: validators --> Added: jaxx/trunk/jaxx-runtime-validator/src/test/java/jaxx/runtime/validator/field/CollectionUniqueKeyValidatorTest.java =================================================================== --- jaxx/trunk/jaxx-runtime-validator/src/test/java/jaxx/runtime/validator/field/CollectionUniqueKeyValidatorTest.java (rev 0) +++ jaxx/trunk/jaxx-runtime-validator/src/test/java/jaxx/runtime/validator/field/CollectionUniqueKeyValidatorTest.java 2009-01-23 12:12:53 UTC (rev 1177) @@ -0,0 +1,52 @@ +package jaxx.runtime.validator.field; + +import jaxx.runtime.validator.field.ValidatorBean.ValidatorBeanEntry; + +import java.util.Arrays; + +/** @author chemit */ +public class CollectionUniqueKeyValidatorTest extends AbstractValidatorTest { + + static protected ValidatorBeanEntry beanEntry = new ValidatorBeanEntry(0, "stringValue"); + static protected ValidatorBeanEntry beanEntry2 = new ValidatorBeanEntry(0, "fake"); + + @org.junit.Test + @Override + public void testValidator() throws Exception { + assertNull(bean.getEntries()); + + // no entry + assertFieldInError("entries", "collectionUniqueKey.one.failed", false); + assertFieldInError("entries", "collectionUniqueKey.two.failed", false); + assertFieldInError("entries", "collectionUniqueKey.three.failed", false); + + // add a entry + bean.setEntries(Arrays.asList(beanEntry)); + + assertFieldInError("entries", "collectionUniqueKey.one.failed", false); + assertFieldInError("entries", "collectionUniqueKey.two.failed", false); + assertFieldInError("entries", "collectionUniqueKey.three.failed", false); + + // two entries with same key + bean.setEntries(Arrays.asList(beanEntry, beanEntry)); + + assertFieldInError("entries", "collectionUniqueKey.one.failed", true); + assertFieldInError("entries", "collectionUniqueKey.two.failed", true); + assertFieldInError("entries", "collectionUniqueKey.three.failed", true); + + // add a entry + bean.setEntries(Arrays.asList(beanEntry2)); + + assertFieldInError("entries", "collectionUniqueKey.one.failed", false); + assertFieldInError("entries", "collectionUniqueKey.two.failed", false); + assertFieldInError("entries", "collectionUniqueKey.three.failed", false); + + // add two entries (will violated unique key on intValue) + bean.setEntries(Arrays.asList(beanEntry2, beanEntry)); + + assertFieldInError("entries", "collectionUniqueKey.one.failed", true); + assertFieldInError("entries", "collectionUniqueKey.two.failed", false); + assertFieldInError("entries", "collectionUniqueKey.three.failed", false); + + } +} \ No newline at end of file Modified: jaxx/trunk/jaxx-runtime-validator/src/test/resources/jaxx/runtime/validator/field/ValidatorBean-validation.xml =================================================================== --- jaxx/trunk/jaxx-runtime-validator/src/test/resources/jaxx/runtime/validator/field/ValidatorBean-validation.xml 2009-01-22 15:28:17 UTC (rev 1176) +++ jaxx/trunk/jaxx-runtime-validator/src/test/resources/jaxx/runtime/validator/field/ValidatorBean-validation.xml 2009-01-23 12:12:53 UTC (rev 1177) @@ -62,6 +62,19 @@ <param name="expression"><![CDATA[ intValue == 0 && stringValue == "stringValue" ]]></param> <message>collectionFieldExpression.none</message> </field-validator> + + <field-validator type="collectionUniqueKey"> + <param name="keys">intValue</param> + <message>collectionUniqueKey.one.failed</message> + </field-validator> + <field-validator type="collectionUniqueKey"> + <param name="keys">stringValue</param> + <message>collectionUniqueKey.two.failed</message> + </field-validator> + <field-validator type="collectionUniqueKey"> + <param name="keys">intValue,stringValue</param> + <message>collectionUniqueKey.three.failed</message> + </field-validator> </field> </validators> \ No newline at end of file Modified: jaxx/trunk/jaxx-runtime-validator/src/test/resources/log4j.properties =================================================================== --- jaxx/trunk/jaxx-runtime-validator/src/test/resources/log4j.properties 2009-01-22 15:28:17 UTC (rev 1176) +++ jaxx/trunk/jaxx-runtime-validator/src/test/resources/log4j.properties 2009-01-23 12:12:53 UTC (rev 1177) @@ -1,5 +1,5 @@ # Global logging configuration -log4j.rootLogger=ERROR, stdout +log4j.rootLogger=INFO, stdout # Console output... log4j.appender.stdout=org.apache.log4j.ConsoleAppender log4j.appender.stdout.layout=org.apache.log4j.PatternLayout
participants (1)
-
tchemit@users.labs.libre-entreprise.org