構造函數注入在spring boot 中怎么使用詳解

我們來詳細講解一下在 Spring Boot 中如何使用構造函數注入,并通過一個完整的、可運行的例子來演示。

構造函數注入是 Spring 官方最推薦的依賴注入方式,因為它能保證對象的不可變性和依賴的完整性。

核心理念

在 Spring Boot 中使用構造函數注入非常簡單,你只需要做到:

  1. 在你的類中,創建一個需要依賴作為參數的構造函數。
  2. 將依賴字段聲明為 private final
  3. 就這樣,完成了! Spring Boot 會自動檢測到這個構造函數,并為你注入所需的 Bean。

一個關鍵點:自 Spring 4.3 版本以后,如果一個類只有一個構造函數,那么 Spring 會自動用它來進行依賴注入,你不再需要在構造函數上顯式地添加 @Autowired 注解。這讓代碼變得更加干凈。


舉例說明:一個簡單的通知服務

我們來創建一個場景:一個 NotificationController(通知控制器)需要依賴一個 MessageService(消息服務)來發送通知。

項目結構
src/main/java/com/example/demo/
├── controller/
│   └── NotificationController.java
├── service/
│   ├── MessageService.java       (接口)
│   └── EmailService.java         (實現)
└── DemoApplication.java          (主啟動類)
第1步:創建依賴接口和實現

首先,我們定義消息服務的接口和它的一個具體實現(比如郵件服務)。

MessageService.java (接口)

package com.example.demo.service;public interface MessageService {String sendMessage(String message);
}

EmailService.java (實現類)

這個類會被 Spring 作為一個 Bean 來管理。

package com.example.demo.service;import org.springframework.stereotype.Service;@Service // 1. 標記為 @Service,讓 Spring 掃描并創建一個 Bean
public class EmailService implements MessageService {@Overridepublic String sendMessage(String message) {System.out.println("正在通過郵件發送消息: " + message);return "郵件發送成功: " + message;}
}
第2步:在控制器中使用構造函數注入

現在,我們在 NotificationController 中通過構造函數來注入 MessageService

NotificationController.java (消費者)

這是演示構造函數注入的核心代碼。

package com.example.demo.controller;import com.example.demo.service.MessageService;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;@RestController
public class NotificationController {// 2. 將依賴聲明為 private final// final 確保了依賴在對象創建后不會被修改private final MessageService messageService;// 3. 定義一個構造函數,并將依賴作為參數傳入// 因為這是唯一的構造函數,所以 @Autowired 注解可以省略public NotificationController(MessageService messageService) {System.out.println("NotificationController 正在被創建,注入 MessageService...");this.messageService = messageService;}@GetMapping("/notify")public String sendNotification() {// 4. 直接使用被注入的依賴return messageService.sendMessage("你好,世界!");}
}
第3步:運行 Spring Boot 應用

你的主啟動類 DemoApplication.java 不需要任何改動。

package com.example.demo;import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;@SpringBootApplication
public class DemoApplication {public static void main(String[] args) {SpringApplication.run(DemoApplication.class, args);}
}
運行與測試
  1. 啟動 DemoApplication
  2. 在控制臺,你會看到啟動日志,其中應該包含我們打印的信息:
    NotificationController 正在被創建,注入 MessageService...
    
    這證明了 Spring 在創建 NotificationController 時調用了它的構造函數。
  3. 打開瀏覽器或使用 Postman/curl 訪問 http://localhost:8080/notify
  4. 你會看到瀏覽器頁面顯示:
    郵件發送成功: 你好,世界!
    
  5. 同時,你的應用程序控制臺會打印出:
    正在通過郵件發送消息: 你好,世界!
    

這整個過程完美地演示了構造函數注入。Spring 自動發現了 EmailServiceMessageService 的一個實現,并在創建 NotificationController 時,通過其構造函數將 EmailService 的實例注入了進去。


進階:使用 Lombok 進一步簡化

在實際項目中,如果依賴很多,手寫構造函數會變得很繁瑣。這時可以使用 Lombok 庫來自動生成構造函數。

  1. 在你的 pom.xml 中添加 Lombok 依賴。

    <dependency><groupId>org.projectlombok</groupId><artifactId>lombok</artifactId><optional>true</optional>
    </dependency>
    
  2. 修改 NotificationController,使用 @RequiredArgsConstructor 注解。

    @RequiredArgsConstructor 會為所有 final 的字段,或者標記了 @NonNull 的字段,自動生成一個構造函數。

    package com.example.demo.controller;import com.example.demo.service.MessageService;
    import lombok.RequiredArgsConstructor; // 導入 Lombok 注解
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.RestController;@RestController
    @RequiredArgsConstructor // 使用 Lombok 自動生成構造函數
    public class NotificationController {// Lombok 會為這個 final 字段生成構造函數參數private final MessageService messageService;// 你不再需要手寫下面的構造函數了!/*public NotificationController(MessageService messageService) {this.messageService = messageService;}*/@GetMapping("/notify")public String sendNotification() {return messageService.sendMessage("你好,世界!(來自Lombok)");}
    }
    

使用 Lombok 后,代碼變得更加簡潔,同時保留了構造函數注入的所有優點。這是目前 Spring Boot 項目中最流行和推薦的實踐。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/bicheng/87989.shtml
繁體地址,請注明出處:http://hk.pswp.cn/bicheng/87989.shtml
英文地址,請注明出處:http://en.pswp.cn/bicheng/87989.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

2025.6.30-2025.7.06第26周:第一次參加頭馬演講俱樂部

現在是周一早上6:23&#xff0c;我開始寫上周的周總結。 3件超出預期的事 參加頭馬俱樂部絕對是最超出預期的&#xff0c;使得這個周末格外的快樂簡歷的第一版終于改完了&#xff0c;花了好長的時間&#xff0c;其中有一天心情還很蕩&#xff0c;因為&#xff0c;我想&#x…

2025使用VM虛擬機安裝配置Macos蘋果系統下Flutter開發環境保姆級教程--下篇

其實如何安裝VM,如何安裝MACOS網上的教程很多,我只是結合我的體驗重新整理了一次,接下來才進入本教程最核心的部分,Flutter開發環境的配置部分。、一.配置前準備 主要是準備相應的工具包,以及其他虛擬機設置1.工具包 工具包的版本也可以自行配置,我這主要是我使用的是F…

QSPI、OSPI與FSMC的區別與內存映射分析

QSPI、OSPI與FSMC的區別與內存映射分析 基本概念與區別 1. FSMC (靈活靜態存儲控制器) 接口類型&#xff1a;并行接口&#xff0c;通常8/16位數據總線總線標準&#xff1a;傳統并行總線協議速度&#xff1a;相對較低&#xff0c;通常最高約100MHz應用場景&#xff1a;SRAM、NOR…

系統思考與心智模式探索

成長的真正障礙&#xff0c;不是能力的不足&#xff0c;而是看待問題的局限。 在復雜多變的商業環境中&#xff0c;我們往往習慣于解決“眼前”的問題&#xff0c;卻忽視了深藏背后的系統性障礙。我們看到的只是表面的“癥狀”&#xff0c;而真正的根源&#xff0c;卻往往隱藏…

物聯網技術的關鍵技術與區塊鏈發展趨勢的深度融合分析

一、物聯網技術的核心架構與關鍵技術 物聯網技術體系由感知層、網絡層、平臺層、應用層和安全層構成&#xff0c;各層技術協同工作&#xff0c;實現物理世界與數字世界的深度融合。 感知層&#xff1a;物聯網的“感官” 傳感器技術&#xff1a;包括環境傳感器&#xff08;溫度…

針對Exhcnage Server的攻擊防范措施

一、背景介紹最近&#xff0c;安全研究人員揭露了一個名為 NightEagle&#xff08;又名 APT-Q-95&#xff09; 的高級持續性威脅&#xff08;APT&#xff09;組織。這個組織被觀察到利用 Microsoft Exchange 服務器中的零日漏洞鏈 進行攻擊&#xff0c;其主要目標是中國政府、國…

編程基礎:繼承

能幫到你的話&#xff0c;就給個贊吧 &#x1f618; 文章目錄繼承&#xff1a;使用基類成員&#xff1a;前提——派生類必須同樣支持基類成員(組件和功能)示例&#xff1a;動物Animal 有 鰓 和 會飛。則 鳥Bird 不是 Animal&#xff0c;因為Bird雖會飛&#xff0c;卻沒有鰓。魚…

TMC4361A 使用(未驗證)

prompt 我用STM32F103C8T6 來控制 TMC4361A 運動控制芯片 &#xff0c;我配置 STM32F103C8T6 的 SPI1 與 TMC4361A 進行通信&#xff0c;配置 PA4 作為片選線&#xff0c;配置 PA8 作為 RCC_MCO 輸入時鐘輸入到 TMC4361A, 并將其連接到TMC4361A的CLK_EXT引腳。我想控制 TMC4361…

深度剖析:如何解決Node.js中mysqld_stmt_execute參數錯誤

在Node.js后端開發中&#xff0c;使用mysql2等數據庫驅動與MySQL/MariaDB交互時&#xff0c;Incorrect arguments to mysqld_stmt_execute 是一個令人頭疼的錯誤。它通常意味著你傳遞給SQL預處理語句的參數數量與SQL字符串中問號&#xff08;?&#xff09;占位符的數量不匹配。…

Vue3 學習教程,從入門到精通,Vue 3 安裝指南及語法知識點詳解(2)

Vue 3 安裝指南及語法知識點詳解 本文將詳細介紹 Vue 3 的所有安裝方式&#xff0c;并深入講解 Vue 3 的語法知識點。此外&#xff0c;還將提供一些綜合性案例&#xff0c;展示如何綜合運用 Vue 3 的各項功能。一、安裝 Vue 3 的所有方式 Vue 3 提供了多種安裝方式&#xff0c;…

C++基礎復習筆記

一、數組定義 在C中&#xff0c;數組初始化有多種方式&#xff0c;以下是常見的幾種方法&#xff1a; 默認初始化 數組元素未顯式初始化時&#xff0c;內置類型&#xff08;如int、float&#xff09;的元素值未定義&#xff08;垃圾值&#xff09;&#xff0c;類類型調用默認構…

手機和PC遠控安全深度測評:TeamViewer/ToDesk/向日葵安全防線對比

聲明&#xff1a;本測試報告系作者基于個人興趣及使用場景開展的非專業測評&#xff0c;測試過程中所涉及的方法、數據及結論均為個人觀點&#xff0c;不代表任何官方立場或行業標準。 一、引言 當下遠程控制技術已深度融入大眾的工作與生活&#xff0c;無論是上班族在家操…

Windows 11的開始菜單調整為左下角布局

1.桌面右鍵個性化 2.個性化中任務欄 3.任務欄選擇任務欄行為 4.任務欄行為中 任務欄對齊方式選擇靠左即可

Go語言項目工程化 — 常見開發工具與 CI/CD 支持

在Go語言的項目工程化實踐中&#xff0c;常見開發工具與 CI/CD 支持是保障團隊協作、高效交付與項目質量的關鍵。以下是第 68 章的詳細內容。一、開發輔助工具Go語言生態為開發者提供了豐富的工具&#xff0c;以提高代碼質量與開發效率。1. 格式化與靜態檢查工具說明gofmt標準格…

OpenCV人臉分析------繪制面部關鍵點函數drawFacemarks()

操作系統&#xff1a;ubuntu22.04 OpenCV版本&#xff1a;OpenCV4.9 IDE:Visual Studio Code 編程語言&#xff1a;C11 算法描述 該函數用于在圖像上繪制面部關鍵點&#xff08;facial landmarks&#xff09;&#xff0c;例如使用 FacemarkLBF, FacemarkKazemi 等算法檢測到的…

Linux內核ext4 extent:解決大文件存儲難題的關鍵

在Linux 操作系統的龐大生態中&#xff0c;文件系統猶如一座城市的基礎設施&#xff0c;支撐著數據的有序存儲與高效訪問。而 ext4 文件系統&#xff0c;作為 Linux 文件系統家族中的重要一員&#xff0c;自誕生起便憑借諸多先進特性備受矚目。其中&#xff0c;extent 機制堪稱…

reactnative頁面適配UI設計尺寸px轉dp的完美解決方案px2dp精要篇

你的 px2dp 函數基本思路是正確的&#xff0c;但可以進一步優化以確保更精確的適配。以下是改進后的完美精確方案&#xff1a; 完美精確的適配方案 import { Dimensions, PixelRatio, Platform, ScaledSize } from react-native;// 獲取屏幕尺寸&#xff08;考慮橫豎屏&#…

【世紀龍科技】汽車鈑金虛擬仿真教學實訓軟件

在汽車后市場人才緊缺的當下&#xff0c;職業院校汽車鈑金教學卻長期面臨“三難困境”&#xff1a;實訓設備昂貴且損耗快、學生實操機會稀缺、教學評價依賴主觀經驗。江蘇世紀龍科技公司以十余年汽車教育數字化積淀為基石&#xff0c;推出《汽車鈑金教學軟件》&#xff0c;通過…

Fiddler中文版抓包工具在后端API調試與Mock中的巧用

在現代開發中&#xff0c;前后端往往分屬不同小組甚至不同公司&#xff0c;接口聯調變得至關重要。尤其是在多團隊合作、后端接口尚未完成或頻繁變動的項目中&#xff0c;前端開發進度容易被阻礙。此時&#xff0c;通過靈活運用 Fiddler抓包工具&#xff0c;前端可以在后端接口…

基于 Flask框架開發的輕量級招聘網站

簡單的招聘網站示例 這是一個基于 Flask 框架開發的輕量級招聘網站示例&#xff0c;采用 Jinja2 模板引擎和 Bootstrap 前端框架&#xff0c;模仿 拉勾網 風格&#xff0c;實現了招聘平臺的核心功能。系統支持 個人用戶 和 企業用戶 兩種角色&#xff0c;個人用戶可以瀏覽職位、…