This content has been marked as final.
Show 4 replies
-
1. Re: Example of using Weld and TestNG?
nickarls Mar 21, 2010 9:42 PM (in response to andersaa)Have a look at the core tests (under tests in the distro), they are not Arquillianized yet.
-
2. Re: Example of using Weld and TestNG?
wujek Mar 22, 2010 11:01 AM (in response to andersaa)Hi. What I do is:
1. bootstrap Weld in @BeforeTest (you can choose @BeforeSuite) - note that TestNG @BeforeTest means all test classes within <test> - and store it in the TestNG injected ITestContext:
@BeforeTest
public void beforeTest(ITestContext ctx) {
WeldContainer wc = Weld.initialize();
BeanManager bm = wc.getBeanManager();
ctx.setAttribute("beanManager", bm);
}
2. in the test class's @BeforeClass I retrieve the BeanManager and perform injection (you can have it in a common superclass):
@BeforeClass
public void beforeClass(ITestContext ctx) {
BeanManager bm = (BeanManager) ctx.getAttribute("beanManager");
CDIInjector.inject(bm, this); // this is the test class instance
}
where CDIInjector is:
public class CDIInjector {
@SuppressWarnings({ "rawtypes", "unchecked" })
public static void inject(BeanManager beanManager, Object instance) {
Class<?> clazz = instance.getClass();
checkTestMethods(clazz);
Annotation[] qualifiers = getQualifiers(beanManager, clazz.getAnnotations());
AnnotatedType<?> annotatedType = beanManager.createAnnotatedType(clazz);
InjectionTarget<?> injectionTarget = beanManager.createInjectionTarget(annotatedType);
Set<Bean<?>> beans = beanManager.getBeans(clazz, qualifiers);
if (beans.size() == 0) {
throw new IllegalStateException("class '" + clazz.getName()
+ "' seems not to be a CDI managed bean; make sure it complies with "
+ "the CDI specification requirements and the class is in a bean "
+ "archive - there must be a 'beans.xml' file in appropriate location");
}
Bean<?> bean = beans.iterator().next();
CreationalContext<?> creationalContext = beanManager.createCreationalContext(bean);
InjectionTarget rawInjectionTarget = injectionTarget;
rawInjectionTarget.inject(instance, creationalContext);
}
private static void checkTestMethods(Class<?> clazz) {
for (Method m : clazz.getMethods()) {
if (m.isAnnotationPresent(Inject.class) && (m.isAnnotationPresent(Test.class) || clazz.isAnnotationPresent(Test.class))) {
throw new IllegalTestClassException("test method '" + m
+ "' is also annotated @Inject - it doesn't make any sense! "
+ "it would be invoked by your CDI provider, it would not be "
+ "treated as a test at this time and the environment might "
+ "not be fully initialized - consider methods it depends on, "
+ "any @BeforeMethod callbacks, etc.; it would be executed again "
+ "by TestNG; it is very likely to fail and not hence supported");
}
}
}
private static Annotation[] getQualifiers(BeanManager beanManager, Annotation[] annotations) {
List<Annotation> qualifiers = new ArrayList<Annotation>(annotations.length);
for (Annotation annotation : annotations) {
if (beanManager.isQualifier(annotation.getClass())) {
qualifiers.add(annotation);
}
}
return qualifiers.toArray(new Annotation[qualifiers.size()]);
}
}
This way you can have your test classes look like:
public class SomeTest {
@Inject
private SomeInjected si;
@Test
public void test() {
Assert.assertNotNull(si);
}
}
3. shut down Weld in @AfterTest:
@AfterTest
public void afterTest(ITestContext ctx) {
BeanManager bm = (BeanManager) ctx.getAttribute("beanManager");
if (bm != null) {
Weld.shutdown(bm);
}
}
This is a simplified version of what I use and it might have some errors as I didn't check it in the IDE. It should get you started, though. The downside is that this works easiest when you have a base class for test that performs the injection, and you cannot then extends from something else. Arquillian had (has?) the same limitation last time I checked.
I am not using Arquillian as what I show here was written before we found out about it, a fairly long time ago.
Hope you find it helpful. -
3. Re: Example of using Weld and TestNG?
dan.j.allen Mar 27, 2010 7:55 PM (in response to andersaa)I beg of you to check out Arquillian. It will simplify your life dramatically. Join us on #jbosstesting in IRC too.
-
4. Re: Example of using Weld and TestNG?
swd847 Mar 28, 2010 11:25 AM (in response to andersaa)If you really can't use Arquillian for whatever reason you could look at seam-xml tests, they currently use weld-se. These will be changed to Arquillian in the near future though.