Skip to content

Commit

Permalink
FORGE-885: Implemented bean-validation addon
Browse files Browse the repository at this point in the history
javaee addon now depends on bean-validation

Created javaee-spi
  • Loading branch information
gastaldi committed Jun 6, 2014
1 parent 69e2b1b commit 1886b2e
Show file tree
Hide file tree
Showing 25 changed files with 927 additions and 156 deletions.
81 changes: 81 additions & 0 deletions bean-validation/README.asciidoc
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
== bean-validation
:idprefix: id_

This addon provides support of link:http://beanvalidation.org/1.1/(Bean Validation 1.1) features for dependent addons.

=== Depends on

[options="header"]
|===
|Addon |Exported |Optional


|javaee-spi
|no
|no

|ui
|no
|no

|org.jboss.forge.furnace.container:cdi
|yes
|no

|===

== Setup

This Addon requires the following installation steps.

=== Add configuration to pom.xml

To use this addon, you must add it as a dependency in the *pom.xml* of your `forge-addon` classified artifact:

[source,xml]
----
<dependency>
<groupId>org.jboss.forge.addon</groupId>
<artifactId>bean-validation</artifactId>
<classifier>forge-addon</classifier>
<version>${version}</version>
</dependency>
----
+
[WARNING]
====
This addon will only work with addons that use the CDI container
====

== Features

Method validation::
link::http://beanvalidation.org/1.1/spec/#d0e267(Method validation) is provided out-of-box for usage in addon methods.
+
[source,java]
----
public class MyService {
public void sayHello(@NotNull String name) {...}
}
@Inject private MyService service;
service.sayHello(null); // will throw ValidationException
----

UI input validation::
you can add validators to an InputComponent by declaring the Bean Validation annotations and using the @UnwrapValidatedValue annotation
+
[source,java]
----
public class MyCommand {
@Inject
@Size(min=2, max=10)
@UnwrapValidatedValue
UIInput<String> name;
...
}
----
85 changes: 85 additions & 0 deletions bean-validation/addon/pom.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.jboss.forge.addon</groupId>
<artifactId>bean-validation-parent</artifactId>
<version>2.6.1-SNAPSHOT</version>
<relativePath>../pom.xml</relativePath>
</parent>

<artifactId>bean-validation</artifactId>
<name>Forge - Bean Validation Addon</name>

<dependencies>
<dependency>
<groupId>org.jboss.forge.addon</groupId>
<artifactId>bean-validation-api</artifactId>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.jboss.forge.addon</groupId>
<artifactId>bean-validation-impl</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.jboss.forge.addon</groupId>
<artifactId>ui</artifactId>
<classifier>forge-addon</classifier>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.jboss.forge.addon</groupId>
<artifactId>javaee-spi</artifactId>
<classifier>forge-addon</classifier>
<scope>provided</scope>
</dependency>

<!-- Furnace Container -->
<dependency>
<groupId>org.jboss.forge.furnace.container</groupId>
<artifactId>cdi</artifactId>
<classifier>forge-addon</classifier>
<scope>provided</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.jboss.forge.furnace</groupId>
<artifactId>furnace-maven-plugin</artifactId>
<executions>
<execution>
<id>generate-dot</id>
<phase>prepare-package</phase>
<goals>
<goal>generate-dot</goal>
</goals>
<configuration>
<attach>true</attach>
</configuration>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-jar-plugin</artifactId>
<executions>
<execution>
<id>create-forge-addon</id>
<phase>package</phase>
<goals>
<goal>jar</goal>
</goals>
<inherited>false</inherited>
<configuration>
<classifier>forge-addon</classifier>
</configuration>
</execution>
</executions>
</plugin>

</plugins>
</build>
</project>
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
/*
* Copyright 2013 Red Hat, Inc. and/or its affiliates.
*
* Licensed under the Eclipse Public License version 1.0, available at
* http://www.eclipse.org/legal/epl-v10.html
*/
package org.jboss.forge.addon.validation;

31 changes: 31 additions & 0 deletions bean-validation/api/pom.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.jboss.forge.addon</groupId>
<artifactId>bean-validation-parent</artifactId>
<version>2.6.1-SNAPSHOT</version>
</parent>
<artifactId>bean-validation-api</artifactId>
<name>Forge - Bean Validation API</name>

<dependencies>
<!-- Bean Validation 1.1 API -->
<dependency>
<groupId>org.jboss.forge.addon</groupId>
<artifactId>javaee-spi</artifactId>
<classifier>forge-addon</classifier>
</dependency>
<!-- Needed for @org.hibernate.validator.valuehandling.UnwrapValidatedValue -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-validator</artifactId>
</dependency>

<dependency>
<groupId>org.jboss.forge.furnace</groupId>
<artifactId>furnace-api</artifactId>
<scope>provided</scope>
</dependency>
</dependencies>
</project>
36 changes: 36 additions & 0 deletions bean-validation/impl/pom.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.jboss.forge.addon</groupId>
<artifactId>bean-validation-parent</artifactId>
<version>2.6.1-SNAPSHOT</version>
</parent>
<artifactId>bean-validation-impl</artifactId>
<name>Forge - Bean Validation Impl</name>
<dependencies>
<dependency>
<groupId>org.jboss.forge.furnace.container</groupId>
<artifactId>cdi-api</artifactId>
<scope>provided</scope>
</dependency>

<dependency>
<groupId>org.jboss.forge.addon</groupId>
<artifactId>bean-validation-api</artifactId>
</dependency>

<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-validator-cdi</artifactId>
</dependency>

<dependency>
<groupId>org.jboss.forge.addon</groupId>
<artifactId>ui</artifactId>
<classifier>forge-addon</classifier>
<scope>provided</scope>
<optional>true</optional>
</dependency>
</dependencies>
</project>
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
/**
* Copyright 2014 Red Hat, Inc. and/or its affiliates.
*
* Licensed under the Eclipse Public License version 1.0, available at
* http://www.eclipse.org/legal/epl-v10.html
*/

package org.jboss.addon.validation;

import java.lang.reflect.Type;

import org.hibernate.validator.spi.valuehandling.ValidatedValueUnwrapper;
import org.jboss.forge.addon.ui.input.InputComponent;

import com.fasterxml.classmate.ResolvedType;
import com.fasterxml.classmate.TypeResolver;

/**
* Unwraps the value of a {@link InputComponent}
*
* @author <a href="ggastald@redhat.com">George Gastaldi</a>
*/
class InputComponentValueUnwrapper extends ValidatedValueUnwrapper<InputComponent<?, ?>>
{
private final TypeResolver typeResolver = new TypeResolver();

@Override
public Object handleValidatedValue(InputComponent<?, ?> value)
{
return value.getValue();
}

@Override
public Type getValidatedValueType(Type valueType)
{
ResolvedType resolvedType = typeResolver.resolve(valueType);
return resolvedType.typeParametersFor(InputComponent.class).get(1).getErasedType();
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
/**
* Copyright 2014 Red Hat, Inc. and/or its affiliates.
*
* Licensed under the Eclipse Public License version 1.0, available at
* http://www.eclipse.org/legal/epl-v10.html
*/

package org.jboss.addon.validation;

import javax.enterprise.inject.Produces;
import javax.inject.Singleton;
import javax.validation.Validation;
import javax.validation.Validator;

import org.hibernate.validator.HibernateValidator;
import org.hibernate.validator.valuehandling.UnwrapValidatedValue;

/**
* Produces a {@link Validator} object with support for {@link UnwrapValidatedValue}
*
* @author <a href="ggastald@redhat.com">George Gastaldi</a>
*/
public class ValidatorProducer
{
@Produces
@Singleton
public Validator createValidator()
{
Validator validator = Validation.byProvider(HibernateValidator.class)
.configure()
.addValidatedValueHandler(new InputComponentValueUnwrapper())
.buildValidatorFactory()
.getValidator();
return validator;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
/**
* Copyright 2013 Red Hat, Inc. and/or its affiliates.
*
* Licensed under the Eclipse Public License version 1.0, available at
* http://www.eclipse.org/legal/epl-v10.html
*/

package org.jboss.addon.validation.ui;

import java.util.concurrent.Callable;
import java.util.logging.Level;
import java.util.logging.Logger;

import javax.validation.ConstraintViolation;
import javax.validation.Validator;

import org.jboss.forge.addon.ui.context.UIValidationContext;
import org.jboss.forge.addon.ui.input.InputComponent;
import org.jboss.forge.addon.ui.util.InputComponents;
import org.jboss.forge.addon.ui.validate.UIValidator;
import org.jboss.forge.furnace.util.ClassLoaders;

/**
* A {@link UIValidator} adapter that validates using Bean Validation 1.1
*
* @author <a href="ggastald@redhat.com">George Gastaldi</a>
*/
class UIValidationAdapter implements UIValidator
{
private final Validator validator;
private final InputComponent<?, ?> input;
private final Class<?> commandClass;
private Logger log = Logger.getLogger(UIValidationAdapter.class.getName());

public UIValidationAdapter(Validator validator, InputComponent<?, ?> input, Class<?> commandClass)
{
super();
this.validator = validator;
this.input = input;
this.commandClass = commandClass;
}

@Override
public void validate(final UIValidationContext context)
{
try
{
// Needed to avoid the javax.el.ExpressionFactory instance not found error
ClassLoaders.executeIn(getClass().getClassLoader(), new Callable<Void>()
{
@Override
public Void call()
{
String inputLabel = InputComponents.getLabelFor(input, true);
for (ConstraintViolation<?> violation : validator.validateValue(commandClass, input.getName(), input))
{
context.addValidationError(input, inputLabel + " " + violation.getMessage());
}
return null;
}
});
}
catch (Exception e)
{
log.log(Level.SEVERE, "Error while validating using BV", e);
}
}
}

0 comments on commit 1886b2e

Please sign in to comment.