前幾篇文章皆採用 XML 配置 Bean,應讀者要求,本文將系統講解基於註解的依賴注入方式。內容淺顯易懂,避免複雜程式碼,助您快速掌握核心概念。
以下四個註解用於標記 Spring 應管理的類別,啟用組件掃描後,單例模式下容器啟動時會自動實例化:
非單例模式下,實例創建時機取決於客戶端請求(由 Spring 代理創建),詳見《Spring 進階之路(7)-Bean 生命週期》一文。
兩者皆用於將已實例化的 Bean 注入目標類屬性中。
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="https://www.springframework.org/schema/beans"
xmlns:context="https://www.springframework.org/schema/context"
xmlns:xsi="https://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="
https://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans-4.0.xsd
https://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context-4.0.xsd">
<context:component-scan base-package="com.siti.spring20160316" />
</beans>
@Controller
@Scope("prototype")
public class UserAction {
@Resource private UserService userService;
@Autowired private Utils utils;
public boolean login(String userName, String password) {
System.out.println("UserAction--login");
if (utils.check(userName)) {
return userService.login(userName, password);
}
return false;
}
}
@Service
public class UserService {
@Resource private UserDao userDao;
public boolean login(String userName, String password) {
System.out.println("UserService--login");
return userDao.isExist(userName, password);
}
@PostConstruct public void init() { System.out.println("UserService--init"); }
@PreDestroy public void destroyMethod() { System.out.println("UserService--destroyMethod"); }
}
@Repository
public class UserDao {
public boolean isExist(String userName, String password) {
System.out.println("UserDao--isExist");
return "wy".equals(userName);
}
}
public class MainTest {
public static void main(String[] args) {
AbstractApplicationContext context = new ClassPathXmlApplicationContext("applicationContext20160316.xml");
UserAction action = (UserAction) context.getBean("userAction");
UserAction action2 = (UserAction) context.getBean("userAction");
System.out.println("是否同一實例:" + action.equals(action2)); // 輸出 false,驗證 prototype 生效
boolean success = action.login("wy", "******");
System.out.println(success ? "登入成功!" : "登入失敗!");
context.registerShutdownHook();
}
}
以下示範定義一個簡單的 @MyAutowired 註解(僅為演示,需配合處理器才能生效):
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.FIELD, ElementType.METHOD})
public @interface MyAutowired {
String name() default "";
}
讀者可嘗試自行實現對應的處理器,歡迎交流心得。