2011年11月20日星期日

JavaEE_019:JavaEE6 新特性之八:CDI 1.0

CDI(Context and Dependency Injection)指的是把一个Java类通过依赖注入的方式“注入”到另一个类供其使用。
虽然JavaEE5支持资源注入,但只能支持有限的资源,比如EJB。
在CDI 1.0出现以前,如果你想把一个POJO类“注入”到另一个POJO类中,你只能用Spring之类的框架来完成“注入”。
现在好了,因为CDI 1.0增加以下元注释帮助我们实现了这个功能。

1. @Inject
原来使用@EJB和@Resource的地方都可以使用@Inject替换。
当然,@Inject主要用途还是“依赖注入”POJO类。

2. @Qualifier
用于区别实现同一接口的不同类,比如DefaultCustomer和SpecialCustomer都实现了接口Customer。
为了区分普通用户和白金用户,先创建一个接口Premium,加上元注释@Qualifier。
@Qualifier
@Target({ElementType.FIELD,ElementType.TYPE,ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
public @interface Premium {}

然后在SpecialCustomer类上加上元注释@Premium,表明该用户属于白金用户。
@Premium
public class SpecialCustomer implements Customer {
......

最后在使用时,使用CDI注入:
加上@Premium元注释表明注入SpecialCustomer类,不加则注入DefaultCustomer类。
@Inject // injection point
@Premium // qualifier to obtain an instance of SpecialCustomer
Customer cust;

3. @Named
如果一个类加上了@Named元注释,表明该类可以在JSF中使用EL访问。
比如类LanguageSingleton定义如下:
@Startup
@Singleton
@Named("languages")
public class LanguageSingleton {

// ======================================
// = Attributes =
// ======================================

private Logger logger = Logger.getLogger("org.beginningee6.tutorial");

private Map languages;

// ======================================
// = Lifecycle methods =
// ======================================

@PostConstruct
private void initLanguages() {
languages = new HashMap();
languages.put("EN", "English");
languages.put("FR", "French");
languages.put("DE", "German");
languages.put("ES", "Spanish");
languages.put("FI", "Finnish");
languages.put("IT", "Italian");
languages.put("RU", "Russian");
logger.info("Loaded " + languages.size() + " languages !!!");
}

// ======================================
// = Business methods =
// ======================================

public String getLanguageValue(String code) {
return languages.containsKey(code.toUpperCase()) ? languages.get(code.toUpperCase()) : "UNKNOWN";
}

public String getListOfValues() {
return languages.keySet().toString();
}
}
在JSF中可以这样使用:
<h:outputLabel value="#{languages.listOfValues}"/>


参考文献:
1. http://developer.51cto.com/art/200912/173801.htm
2. http://download.oracle.com/javaee/5/tutorial/doc/bncjk.html
3. http://www.theserverside.com/news/1373391/Dependency-Injection-in-Java-EE-6-Part-1

没有评论: