首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> Java 程式設計 >> Java 相關知識

Spring 2.5 註解開發入門:@Service、@Autowired、@Qualifier 完整範例

     編輯:Java 相關知識

Spring 2.5 引入基於註解的配置方式 (@Service、@Autowired、@Qualifier),大幅簡化 XML 配置。本文透過完整範例示範:元件掃描、Bean 定義、依賴注入、多實現類限定、單元測試驗證。

一、專案配置:beans.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="https://www.springframework.org/schema/beans"
       xmlns:xsi="https://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="https://www.springframework.org/schema/context"
       xsi:schemaLocation="
           https://www.springframework.org/schema/beans
           https://www.springframework.org/schema/beans/spring-beans-2.5.xsd
           https://www.springframework.org/schema/context
           https://www.springframework.org/schema/context/spring-context-2.5.xsd">

  <!-- 1. 啟用註解驅動 -->
  <context:annotation-config/>

  <!-- 2. 元件掃描基礎套件 -->
  <context:component-scan base-package="org.example"/>

</beans>

關鍵配置說明

  • context:annotation-config:啟用 @Autowired、@Resource、@PostConstruct、@PreDestroy 等註解處理器
  • context:component-scan:掃描 org.example 及子套件下的 @Component、@Service、@Repository、@Controller 類別,自動註冊為 Bean

二、程式碼結構

org.example
├── IMan.java                 # 介面
├── ChineseMan.java           # 實作 1 (@Service)
├── EnglishMan.java           # 實作 2 (@Service("usMan"))
├── SimpleMan.java            # 使用者 (@Service + @Autowired)
└── SpringTest.java           # 測試類

三、介面與實作類

IMan.java

package org.example;
public interface IMan {
    String sayHello();
}

ChineseMan.java (預設 Bean ID: chineseMan)

package org.example;
import org.springframework.stereotype.Service;

@Service
public class ChineseMan implements IMan {
    public String sayHello() { return "抽你丫的"; }
}

EnglishMan.java (指定 Bean ID: usMan)

package org.example;
import org.springframework.stereotype.Service;

@Service("usMan")  // 指定 Bean ID 為 "usMan"
public class EnglishMan implements IMan {
    public String sayHello() { return this + " said: Fuck you!"; }
}

四、使用者類:SimpleMan

package org.example;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Service;

@Service
public class SimpleMan {
    // 1. 自動注入名為 "chineseMan" 的 Bean
    @Autowired(required = false)
    @Qualifier("chineseMan")  // 限定具體 Bean
    private IMan man;

    public IMan getMan() { return man; }
    public void setMan(IMan man) { this.man = man; }

    public String hello() {
        System.out.println("man.sayHello()=" + man.sayHello());
        return "SimpleMan said: Hi";
    }
}

關鍵註解解析

五、單元測試驗證

package org.example;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class SpringTest {
    public static void main(String[] args) {
        ApplicationContext ctx = new ClassPathXmlApplicationContext("beans.xml");

        // 1. 取得 SimpleMan (Bean ID: simpleMan)
        SimpleMan dao = (SimpleMan) ctx.getBean("simpleMan");
        System.out.println(dao.hello());

        // 2. 取得 EnglishMan (Bean ID: usMan)
        IMan man = (IMan) ctx.getBean("usMan");
        System.out.println(man.sayHello());
    }
}

六、執行輸出

man.sayHello()=抽你丫的
SimpleMan said: Hi
org.example.EnglishMan@12bcd4b said: Fuck you!

七、@Autowired 注入方式對比

註解作用關鍵屬性
@Service定義 Service 層 Bean,屬 @Component 特化value: Bean ID (預設類名首字母小寫)
@Autowired自動裝配 (byType),可用於建構子、Setter、欄位required=false: 允許找不到 Bean 時不報錯
@Qualifier限定 Bean 名稱 (byName),配合 @Autowired 使用value: Bean ID
方式程式碼優點
欄位注入@Autowired @Qualifier("x") private IMan man;簡潔、不可變 (final 配合建構子)
Setter 注入@Autowired public void setMan(@Qualifier("x") IMan man)可選依賴、易測試 (手動注入 Mock)
建構子注入@Autowired public SimpleMan(@Qualifier("x") IMan man)不可變、強制依賴、循環依賴檢測

推薦:Spring 4.3+ 單一建構子可省略 @Autowired,建構子注入為首選。

八、@Resource vs @Autowired

特性@Autowired (Spring)@Resource (JSR-250)
匹配策略優先 byType,再 byName優先 byName,再 byType
指定名稱@Qualifier("name")@Resource(name="name")
標準化Spring 專有Java EE 標準

九、String 類型 Bean 定義問題 (文中提到的未解決點)

若需定義 java.lang.String 類型的 Bean 並注入:

<bean id="myString" class="java.lang.String">
  <constructor-arg value="hello world"/>
</bean>

@Autowired @Qualifier("myString") private String myStr;  // 注入成功

或使用 @Value("${property.key}") 注入屬性檔值 (需 PropertyPlaceholderConfigurer)。

十、遷移建議

  • 新專案:全註解配置,beans.xml 僅保留 component-scan、資料源、交易管理等基礎設施
  • 舊專案:漸進式遷移,Service/DAO 層優先改註解,Controller/配置類保留 XML
  • 團隊規範:統一 Bean ID 命名 (類名首字母小寫)、統一注入方式 (建構子優先)
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved