当前位置: 首页 > article >正文

springboot 四层架构之间的关系整理笔记五

问题:service 和 多个serviceimpl 分层之间的逻辑关系?

好的!用班级活动的例子继续讲,假设班长(Service接口)要管理多种任务,而不同的班委(ServiceImpl实现类)负责不同场景的实现。这样分层后,代码会更灵活、易扩展!👇


场景设定

班级要组织一次 ‌「秋游活动」‌,班长(Service接口)定规则:

  • 必须有一个方法 planTrip() 用来规划路线
  • 必须有一个方法 calculateCost() 用来计算费用

但根据 ‌不同出行方式‌(比如步行、坐大巴),劳动委员和文艺委员分别写了两种实现!


1. Service接口(班长定的规则)

 

javaCopy Code

public interface TripService { String planTrip(); // 规划路线 double calculateCost(); // 计算费用 }


2. ServiceImpl实现类1:步行方案(劳动委员写的)

 

javaCopy Code

@Service("walkingTripService") // 给实现类起个名字,方便区分 public class WalkingTripServiceImpl implements TripService { @Override public String planTrip() { return "路线:学校 -> 公园(步行30分钟)"; } @Override public double calculateCost() { return 0; // 步行不需要费用 } }


3. ServiceImpl实现类2:大巴方案(文艺委员写的)

@Service("busTripService") public class BusTripServiceImpl implements TripService { @Override public String planTrip() { return "路线:学校 -> 山区(大巴1小时)"; } @Override public double calculateCost() { return 500; // 大巴租车费用 } }


关键问题:Controller 如何选择不同的实现?

就像班级要决定最终用哪种方案,可以通过两种方式:


方式1:用 @Qualifier 指定具体实现

在 Controller 中明确告诉 Spring 要注入哪个实现类:

@RestController

public class TripController {

@Autowired

@Qualifier("busTripService") // 指定用大巴方案

private TripService tripService;

@GetMapping("/plan") public String getPlan() { return tripService.planTrip(); } }


方式2:用 @Primary 标记默认实现

如果大部分情况用步行,可以设一个默认实现:

@Service("walkingTripService")

@Primary // 默认选这个 public class WalkingTripServiceImpl implements TripService { // ... 同上 }

Controller 中不指定时,自动用 @Primary 的实现:

@Autowired private TripService tripService; // 默认注入 WalkingTripServiceImpl


多个 ServiceImpl 的优势

就像班级可以灵活切换方案,代码也能动态调整!

  1. 按需切换‌:

    • 根据配置选择实现(比如测试环境用步行,生产环境用大巴)

    # application.yml school: trip-type: bus

  2. 扩展方便‌:

    • 如果新增「骑自行车」方案,只需写 BikeTripServiceImpl,其他代码不用改!
  3. 逻辑隔离‌:

    • 大巴的费用计算和步行完全不同,分开实现更清晰

实际应用场景

场景1:支付方式多样化
  • 接口:PaymentService
  • 实现类:
    • AliPayServiceImpl(支付宝)
    • WeChatPayServiceImpl(微信支付)
    • BankCardServiceImpl(银行卡)

Controller 根据用户选择调用不同实现:

// 根据用户选择的支付方式,动态注入对应的

ServiceImpl String paymentType = "wechat";

PaymentService paymentService = getPaymentService(paymentType); paymentService.pay(100);


场景2:数据库多版本支持
  • 接口:UserRepository
  • 实现类:
    • MySQLUserServiceImpl(连接 MySQL)
    • MongoDBUserServiceImpl(连接 MongoDB)

通过配置文件切换数据库:

yamlCopy Code

# application.yml database: type: mongodb


总结:Service 和多个 ServiceImpl 的关系就像「总规则和具体方案」

  • 📜 ‌Service接口‌:定义「必须做什么」(What)
  • 🛠 ‌ServiceImpl实现类‌:定义「具体怎么做」(How)
  • 🎛 ‌Controller‌:根据需求选择「用哪种实现」

这样设计后,班级活动(项目)既能保证统一规则,又能灵活适应各种变化! 🌟


http://www.kler.cn/a/612912.html

相关文章:

  • 怎样进行服务器的日常安全监控和审计?
  • uniapp用户登录及获取用户信息(头像昵称)
  • 全国职业技能大赛_网络安全_中职A模块解析
  • spring security的过滤器链
  • MySQL-事务与锁
  • skynet.crypt 使用详解
  • vllm+openwebui,玩转私有化AI
  • 蓝桥与力扣刷题(蓝桥 最少刷题数)
  • python力扣73.矩阵置零
  • 卷积神经网络输入通道和输出通道的确定
  • JVM 面经
  • 【vLLM 学习】快速入门
  • Windows .gitignore文件不生效的情况排查
  • 板端ros2 VM ubuntu 虚拟机之间通信
  • Java 基本数据类型 vs 包装类(引用数据类型)
  • flink 分组窗口聚合 与 窗口表值函数聚合 的区别
  • 基于飞腾FT2000+服务器主板与DeepSeek大模型的国产化AI算力探索
  • 典范硬币系统(Canonical Coin System)→ 贪心算法
  • React19源码系列之Hooks(useRef)
  • 基于DrissionPage的TB商品信息采集与可视化分析