2016-12-20 9 views
0

저는 MapStruct를 사용하여 엔티티를 DTO로 변환하거나 그 반대로 변환하는 작업을 돕는 mappers를 생성하는 maven 프로젝트를 보유하고 있습니다. 이 mappers는 maven의 generate-sources 단계에서 생성되고 target/generated-sources 및 target/AppName/WEB-INF/classes 폴더에 저장됩니다.생성 된 소스에서 용접 검색 클래스를 만드는 방법

제이보스 서버에서 실행 때이 perfectely 작동
@Generated(
value = "org.mapstruct.ap.MappingProcessor", 
date = "2016-12-19T23:19:36-0200", 
comments = "version: 1.1.0.CR1, compiler: javac, environment: Java 1.8.0_112" 
) 
@Singleton 
@Named 
public class RuleMapperImpl implements RuleMapper { 

    @Override 
    public RuleDto ruletoDto(Rule rule) { 

     ruleDto ruleDto = new ruleDto(); 

     if (rule != null) { 
      ruleDto.setIdRule(rule.getIdRule()); 
     } 

     return ruleDto; 
    } 
} 

문제 :

예를 들어,이 매퍼

@Mapper 
public interface RuleMapper { 

    RuleDto ruletoDto(Rule rule); 

    //other cool stuf 
} 

내가 다음을 생성 할 수 있도록 MapStruct는 CDI를 사용하는 컨피그에게 있습니다 저는이 클래스를 테스트하기 위해 노력하고 있습니다.이를 위해 다음과 같이 사용자 정의 러너를 구현했습니다.

import org.junit.runners.BlockJUnit4ClassRunner; 
import org.junit.runners.model.InitializationError; 

public class WeldJUnit4Runner extends BlockJUnit4ClassRunner { 

    public WeldJUnit4Runner(Class<Object> clazz) throws InitializationError { 
     super(clazz); 
    } 

    @Override 
    protected Object createTest() throws Exception { 
     final Class<?> test = getTestClass().getJavaClass(); 
     return WeldContext.INSTANCE.getBean(test); 
    } 

} 
,451,515,

그리고는 :

import org.jboss.weld.environment.se.Weld; 
import org.jboss.weld.environment.se.WeldContainer; 

public class WeldContext { 

    public static final WeldContext INSTANCE = new WeldContext(); 

    private final Weld weld; 
    private final WeldContainer container; 

    private WeldContext() { 
     this.weld = new Weld(); 
     this.container = weld.initialize(); 
     Runtime.getRuntime().addShutdownHook(new Thread() { 
      @Override 
      public void run() { 
       weld.shutdown(); 
      } 
     }); 
    } 

    public <T> T getBean(Class<T> type) { 
     return container.instance().select(type).get(); 
    } 

} 

이러한 구현은 here에서 촬영되었다.

마지막 시험 :

@RunWith(WeldJUnit4Runner.class) 
public class RuleMapperTest { 

    @Inject 
    private RuleMapper ruleMapper; 

    @Test 
    public void coolTestName() { 
     Assert.assertTrue(Boolean.TRUE); 
    } 
} 

내가 실행하려고,이 콘솔 출력은 다음과 같습니다

의 log4j : 없음 펜더가 로거 (org.jboss.logging)를 찾을 수 없습니다 WARN . log4j : WARN log4j 시스템을 올바르게 초기화하십시오. log4j : WARN 자세한 내용은 http://logging.apache.org/log4j/1.2/faq.html#noconfig을 참조하십시오.

로그에 대한 경고, 다음과 같은 예외 :

br.com.treinoos.common.cdi.WeldJUnit4Runner.createTest (WeldJUnit4Runner.java:15) 에서

java.lang.ExceptionInInitializerError 에서 조직 org.junit.runners.BlockJUnit4ClassRunner.methodBlock에서 org.junit.internal.runners.model.ReflectiveCallable.run (ReflectiveCallable.java:12) 에서 .junit.runners.BlockJUnit4ClassRunner $ 1.runReflectiveCall (BlockJUnit4ClassRunner.java:266) (BlockJUnit4ClassRunner.java:263) at org.junit.runners.BlockJUnit4ClassRunner.runChild (BlockJUnit org.junit.runners에서 org.junit.runners.ParentRunner $ 3.run (ParentRunner.java:290) 에서 org.junit.runners.BlockJUnit4ClassRunner.runChild (BlockJUnit4ClassRunner.java:57) 에서 4ClassRunner.java:78) .ParentRunner $의 1.schedule org.junit.runners.ParentRunner.runChildren에서 (ParentRunner.java:71) (ParentRunner.java:288) org.junit.runners.ParentRunner.access $ 000 (ParentRunner.java:58)에서 org.junit.runners.ParentRunner $ 2.evaluate (ParentRunner.java:268) at org.junit.runners.ParentRunner.run (ParentRunner.java:363) at org.eclipse.jdt.internal.junit4.runner. (JUnit4TestReference.java:86) at org.eclipse.jdt.internal.junit.runner.TestExecution.run (TestExecution.java:38) (org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests (RemoteTestRunner.java:459) RemoteTestRunner.java:382) at org.org.jboss.weld.exceptions.DeploymentException : WELD-001,408 : 주입에 @Default 한정자 형 RuleMapper 대한 의존성으로 인한 불만족 eclipse.jdt.internal.junit.runner.RemoteTestRunner.main (RemoteTestRunner.java:192) point [BackedAnnotatedField] @Inject private br.com.treinoos.model.core.business.treinoos.mappers.RuleMapperTest.ruleMapper br.com.treinoos.model.core.business.treinoos.mappers.RuleMapperTest.ruleMapper (RuleMapperTest. java : 0) at org.jboss.weld.bootstrap.Validator.validateInjectionPointForDeploymentProblems (Validator.java:359) at org.jboss.weld.bootstrap.Validator.validateInjectionPoint (Validator.java:281) at org.jboss. weld.bootstrap.Validator.validateGeneralBean (Validator.java:134) at org.jboss.weld.bootstrap.Validator.valid ateRIBean (Validator.java:155) at org.jboss.weld.bootstrap.Validator.validateBean (Validator.java:518) at org.jboss.weld.bootstrap.ConcurrentValidator $ 1.doWork (ConcurrentValidator.java:68) org.jboss.weld.bootstrap.ConcurrentValidator $ 1.doWork (ConcurrentValidator.java:66) at org.jboss.weld.executor.IterativeWorkerTaskFactory $ 1.call (IterativeWorkerTaskFactory.java:63) at org.jboss.weld.executor .IterativeWorkerTaskFactory $ 1.call java.util.concurrent.FutureTask.run에서 (IterativeWorkerTaskFactory.java:56) java.util.concurrent.ThreadPoolExecutor.runWorker (ThreadPoolExecutor.java:1142)에서 (FutureTask.java:266) 에서 java.util.concurrent.ThreadPoolExecutor $ Worker.run (ThreadPoolExecutor.java:617) at java.la ng.Thread.run (Thread.java:745)

마찬가지로 Weld는 생성 된 클래스를 조회하기가 쉽지 않았습니다. beans.xml 이미 src/test/resources/META-INF/beans.xml에서 생성됩니다

<?xml version="1.0" encoding="UTF-8"?> 
<beans xmlns="http://xmlns.jcp.org/xml/ns/javaee" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee 
        http://xmlns.jcp.org/xml/ns/javaee/beans_1_1.xsd" 
    version="1.1" bean-discovery-mode="all"> 
</beans> 

는 아무도 나에게이 문제에 대한 해결책을 포인트? 나는 이미 similar를 검색했지만 성공하지는 못했다.

+0

'beans.xml'도'src/main/resources/META-INF'에 추가 했습니까? –

+0

@Joh 그래, 그랬어. –

+0

정확히 같은 내용입니까? 당신은이 파일이 명시 적으로'src/test/resources'라고 언급하고 또한 내 경로를 적어주세요 - src/main/webapp가 아닌 것 –

답변

0

여기에 귀하의 문제에 대한 전체 설명과 내가 작성한 이유가 수정되었습니다.

Maven에는 최소한 2 개의 클래스 로더가 있습니다. 테스트 클래스 경로와 기본 클래스 경로에는 각각 고유 한 클래스 로더가 있습니다. 의존성 구조에 따라 다른 것을 가질 수 있습니다. CDI는 이러한 방식으로 실행될 때 각 클래스 로더를 별도의 bean 아카이브로 식별합니다. src/main/webapp은 명시 적으로 WAR 파일입니다. beans.xml 거기에 bean 보관소가 없습니다. src/main/resources에 하나를 추가합니다. 이 문제는 용접을 인스턴스화하는 방법에 따라 다릅니다.

이 작업을 올바르게 수행하는 다른 프로젝트 - CDI-unitArquillian, 특히 Weld Embedded 컨테이너. 이 중 하나를 사용한다면 이것은 문제가되지 않습니다.

+0

CDIUnit을 사용했는데 문제가 lib인지 알아보기 위해 변경되었습니다. 어쨌든, 고마워, 그건 나를 도왔다. –