javax.validation.ValidationException: HV000183: Não é possível carregar 'javax.el.ExpressionFactory'

103

Tento escrever um aplicativo muito simples com o validador de hibernação:

meus passos:

adicione a seguinte dependência em pom.xml:

<dependency>
    <groupId>org.hibernate</groupId>
    <artifactId>hibernate-validator</artifactId>
    <version>5.1.1.Final</version>
</dependency>

escrever código:

class Configuration {
    Range(min=1,max=100)
    int threadNumber;
    //...

    public static void main(String[] args) {
        ValidatorFactory factory = Validation.buildDefaultValidatorFactory();

        Validator validator = factory.getValidator();

        Configuration configuration = new Configuration();
        configuration.threadNumber = 12;
            //...

        Set<ConstraintViolation<Configuration>> constraintViolations = validator.validate(configuration);
        System.out.println(constraintViolations);

    }
}

E recebo o seguinte rastreamento de pilha:

Exception in thread "main" javax.validation.ValidationException: Unable to instantiate Configuration.
    at javax.validation.Validation$GenericBootstrapImpl.configure(Validation.java:279)
    at javax.validation.Validation.buildDefaultValidatorFactory(Validation.java:110)
    ...
    at org.hibernate.validator.internal.engine.ConfigurationImpl.<init>(ConfigurationImpl.java:110)
    at org.hibernate.validator.internal.engine.ConfigurationImpl.<init>(ConfigurationImpl.java:86)
    at org.hibernate.validator.HibernateValidator.createGenericConfiguration(HibernateValidator.java:41)
    at javax.validation.Validation$GenericBootstrapImpl.configure(Validation.java:276)
    ... 2 more

O que eu errado?

gstackoverflow
fonte
1
Atualizando o Hibernate-validator para 5.2.4.Finalresolver o problema para mim.
fracz
1
@fracz Eu tenho o hibernate-validator = 5.2.4.Finale a exceção ainda está lá.
Alfonso Nishikawa

Respostas:

154

Ele está funcionando após adicionar as pom.xmlseguintes dependências:

<dependency>
   <groupId>javax.el</groupId>
   <artifactId>javax.el-api</artifactId>
   <version>2.2.4</version>
</dependency>
<dependency>
   <groupId>org.glassfish.web</groupId>
   <artifactId>javax.el</artifactId>
   <version>2.2.4</version>
</dependency>

Primeiros passos com o Hibernate Validator :

O Hibernate Validator também requer uma implementação da Unified Expression Language ( JSR 341 ) para avaliar expressões dinâmicas em mensagens de violação de restrição. Quando seu aplicativo é executado em um contêiner Java EE, como WildFly , uma implementação EL já é fornecida pelo contêiner. Em um ambiente Java SE, no entanto, você deve adicionar uma implementação como dependência ao seu arquivo POM. Por exemplo, você pode adicionar as duas dependências a seguir para usar a implementação de referência JSR 341 :

<dependency>
   <groupId>javax.el</groupId>
   <artifactId>javax.el-api</artifactId>
   <version>2.2.4</version>
</dependency>
<dependency>
   <groupId>org.glassfish.web</groupId>
   <artifactId>javax.el</artifactId>
   <version>2.2.4</version>
</dependency>
gstackoverflow
fonte
5
O Bean Validation 1.1 requer as dependências do Expression Language no classpath. Veja também hibernate.org/validator/documentation/getting-started
Hardy
1
<dependency> <groupId> org.glassfish.web </groupId> <artifactId> javax.el </artifactId> <version> 2.2.4 </version> <scope> runtime </scope> </dependency> é suficiente como o validador do hibernate já depende de javax.el-api
mvera
8
<dependency><groupId>javax.el</groupId><artifactId>javax.el-api</artifactId><version>2.3.1</version></dependency>foi suficiente para mim
trenó de
1
<dependency> <groupId> javax.el </groupId> <artifactId> el-api </artifactId> <version> 2.2 </version> </dependency> resolveu meu problema.
zhy2002,
3
Parece que eles recomendam ambos na página do github para ambientes SE: github.com/hibernate/hibernate-validator . O de cima foi suficiente para mim.
vphilipnyc
56

faça apenas

<dependency>
   <groupId>javax.el</groupId>
   <artifactId>javax.el-api</artifactId>
   <version>2.2.4</version>
</dependency>
Bruno Lee
fonte
8
Por que não hibernate-validatorconfia nessa dependência?
thomas.mc.work
Não sei por que, mas seria melhor
Bruno Lee
@ thomas.mc.work eu acho que para evitar problemas de dependência transitiva
gstackoverflow
1
Na verdade, está marcado como dependência no arquivo pom, mas com o escopo maven fornecido. Isso significa que você é responsável por adicioná-lo se o seu servidor JavaEE não fornecer um para você.
real_paul
Esta solução não funcionou para mim, estou usando o validador de hibernate 6.0.4 e java.el da versão 3.0.0 e estou usando o WebLogic. Qualquer um pode me ajudar .. apreciado ajudando mãos com antecedência.
Kushwaha
18

Se você estiver usando o tomcat como o tempo de execução do servidor e obtiver esse erro nos testes (porque o tempo de execução do tomcat não está disponível durante os testes), faz sentido incluir o tempo de execução do tomcat el em vez do do glassfish). Este seria:

    <dependency>
        <groupId>org.apache.tomcat</groupId>
        <artifactId>tomcat-el-api</artifactId>
        <version>8.5.14</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.apache.tomcat</groupId>
        <artifactId>tomcat-jasper-el</artifactId>
        <version>8.5.14</version>
        <scope>test</scope>
    </dependency>
walkeros
fonte
Eu te amo. Sim.
xdhmoore
Ainda amo você. Parece que você pode incluir apenas a tomcat-jasper-eldependência, já que parece incluir transitivamente a tomcat-el-apidependência.
xdhmoore
13

Se você estiver usando o Spring Boot com starters - esta dependência adiciona ambos tomcat-embed-ele hibernate-validatordependências:

<dependency>
   <groupId>org.springframework.boot</groupId>
   <artifactId>spring-boot-starter-validation</artifactId>
</dependency>
Michał Stochmal
fonte
13

Caso você não precise de javax.el (por exemplo, em um aplicativo JavaSE), use ParameterMessageInterpolator do validador Hibernate . O validador do Hibernate é um componente independente, que pode ser usado sem o próprio Hibernate .

Depende do validador de hibernação

<dependency>
   <groupId>org.hibernate</groupId>
   <artifactId>hibernate-validator</artifactId>
   <version>6.0.16.Final</version>
</dependency>

Use ParameterMessageInterpolator

import javax.validation.Validation;
import javax.validation.Validator;
import org.hibernate.validator.messageinterpolation.ParameterMessageInterpolator;

private static final Validator VALIDATOR =
  Validation.byDefaultProvider()
    .configure()
    .messageInterpolator(new ParameterMessageInterpolator())
    .buildValidatorFactory()
    .getValidator();
Markus Schulte
fonte
Sim, não quero adicionar mais dependência. Bom trabalho
nokieng
Oh, esta é realmente uma boa resposta para mim em relação aos projetos de biblioteca.
Jin Kwon
Esta deve ser a resposta escolhida.
anataliocs
12

Em relação à página de documentação do validador do Hibernate , você deve definir uma dependência para uma JSR-341implementação:

<dependency>
   <groupId>org.glassfish</groupId>
   <artifactId>javax.el</artifactId>
   <version>3.0.1-b11</version>
</dependency>
herau
fonte
4

Se estiver usando Spring Boot, isso funcionará bem. Mesmo com Spring Reactive Mongo.

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-validation</artifactId>
</dependency>

e configuração de validação:

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.mongodb.core.mapping.event.ValidatingMongoEventListener;
import org.springframework.validation.beanvalidation.LocalValidatorFactoryBean;

@Configuration
public class MongoValidationConfig {

    @Bean
    public ValidatingMongoEventListener validatingMongoEventListener() {
        return new ValidatingMongoEventListener(validator());
    }

    @Bean
    public LocalValidatorFactoryBean validator() {
        return new LocalValidatorFactoryBean();
    }
}
Navalha
fonte
2

para sbt, use as versões abaixo

val glassfishEl = "org.glassfish" % "javax.el" % "3.0.1-b09"

val hibernateValidator = "org.hibernate.validator" % "hibernate-validator" % "6.0.17.Final"

val hibernateValidatorCdi = "org.hibernate.validator" % "hibernate-validator-cdi" % "6.0.17.Final"
prathameshr
fonte
1

De acordo com a documentação Getting started with Hibernate Validator , uma implementação Expression Language (EL) deve ser fornecida. Em um ambiente Java EE, ele seria fornecido pelo contêiner. No entanto, em um aplicativo autônomo como o seu, ele precisa ser fornecido.

O Hibernate Validator também requer uma implementação da Unified Expression Language (JSR 341) para avaliar expressões dinâmicas em mensagens de violação de restrição.

Quando seu aplicativo é executado em um contêiner Java EE, como WildFly, uma implementação EL já é fornecida pelo contêiner.

Em um ambiente Java SE, no entanto, você deve adicionar uma implementação como dependência ao seu arquivo POM. Por exemplo, você pode adicionar a seguinte dependência para usar a implementação de referência JSR 341:

<dependency>
  <groupId>org.glassfish</groupId>
  <artifactId>javax.el</artifactId>
  <version></version>
</dependency>

O exemplo de dependência da documentação é um pouco desatualizado, pois a linguagem de expressão fez a transição para o projeto Jakarta EE em 2018. Para usar a versão Jakarta EE da linguagem de expressão, adicione a seguinte dependência Eclipse Glassfish EL:

<dependency>
   <groupId>org.glassfish</groupId>
   <artifactId>jakarta.el</artifactId>
   <version>3.0.3</version>
</dependency>

Existem outras implementações de EL que podem ser usadas além do Glassfish. Por exemplo, Spring Boot por padrão usa Tomcat integrado . Esta versão do EL pode ser usada da seguinte forma:

<dependency>
   <groupId>org.apache.tomcat.embed</groupId>
   <artifactId>tomcat-embed-el</artifactId>
   <version>9.0.30</version>
</dependency>
M. Justin
fonte
0

para gradle:

compile 'javax.el:javax.el-api:2.2.4'
Borino
fonte