君子终日乾乾,夕惕若厉,无咎。|

唐钰逍遥

园龄:9年9个月粉丝:0关注:0

springboot策略设计模式最佳实践

假设我们希望实现以下需求:

  1. 支付方式(如支付宝、微信支付)可以动态切换。
  2. 支付方式配置从配置文件中加载,或者支持在数据库中动态更新。
  3. 配置文件或数据库中指定当前生效的支付方式。

步骤 1: 配置文件定义支付方式

我们可以在 application.ymlapplication.properties 中定义支付方式配置项,指定默认的支付方式。

# application.yml
payment:
defaultMethod: alipay

这里我们定义了一个 payment.defaultMethod 配置项,它用于指定当前选择的支付方式。假设我们有多个支付方式,默认支付方式是 alipay

步骤 2: 在 PaymentContext 中加载动态配置

为了根据配置动态选择支付方式,我们需要将配置文件中的 defaultMethod 读入,并根据它来确定使用哪个支付策略。可以通过 Spring 的 @Value 注解来注入配置项。

import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import java.util.Map;
@Service
public class PaymentContext {
private final Map<String, PaymentStrategy> paymentStrategies;
@Value("${payment.defaultMethod}")
private String defaultPaymentMethod;
public PaymentContext(Map<String, PaymentStrategy> paymentStrategies) {
this.paymentStrategies = paymentStrategies;
}
public void executePayment(double amount) {
// 根据配置的支付方式动态选择策略
PaymentStrategy strategy = paymentStrategies.get(defaultPaymentMethod);
if (strategy != null) {
strategy.pay(amount);
} else {
throw new IllegalArgumentException("Invalid payment method: " + defaultPaymentMethod);
}
}
}

在这个 PaymentContext 中,我们通过 @Value 注解将 application.yml 中的 payment.defaultMethod 配置项注入到 defaultPaymentMethod 变量中。然后在 executePayment 方法中,根据配置项选择对应的支付策略执行支付。

步骤 3: 动态更新支付方式(可选)

如果您希望在运行时动态切换支付方式,可以考虑将支付方式配置存储在数据库中。通过查询数据库中的配置项,可以灵活地更新支付方式。

假设我们有一个 PaymentConfig 表,包含 method_codeenabled 等字段来表示当前生效的支付方式。

@Entity
public class PaymentConfig {
@Id
private Long id;
private String methodCode;
private Boolean enabled;
// getters and setters
}

接着,可以通过 Spring Data JPA 访问数据库中的配置:

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.List;
@Service
public class DynamicPaymentConfigService {
private final PaymentConfigRepository paymentConfigRepository;
@Autowired
public DynamicPaymentConfigService(PaymentConfigRepository paymentConfigRepository) {
this.paymentConfigRepository = paymentConfigRepository;
}
public String getActivePaymentMethod() {
List<PaymentConfig> activeConfigs = paymentConfigRepository.findByEnabled(true);
// 假设返回第一个启用的支付方式
if (!activeConfigs.isEmpty()) {
return activeConfigs.get(0).getMethodCode();
}
return null; // 如果没有配置,返回空
}
}

然后在 PaymentContext 中使用这个动态配置服务来更新支付方式:

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.Map;
@Service
public class PaymentContext {
private final Map<String, PaymentStrategy> paymentStrategies;
private final DynamicPaymentConfigService dynamicPaymentConfigService;
@Autowired
public PaymentContext(Map<String, PaymentStrategy> paymentStrategies, DynamicPaymentConfigService dynamicPaymentConfigService) {
this.paymentStrategies = paymentStrategies;
this.dynamicPaymentConfigService = dynamicPaymentConfigService;
}
public void executePayment(double amount) {
// 从数据库或配置中获取当前启用的支付方式
String activePaymentMethod = dynamicPaymentConfigService.getActivePaymentMethod();
if (activePaymentMethod != null) {
PaymentStrategy strategy = paymentStrategies.get(activePaymentMethod);
if (strategy != null) {
strategy.pay(amount);
} else {
throw new IllegalArgumentException("Invalid payment method: " + activePaymentMethod);
}
} else {
throw new IllegalStateException("No active payment method configured.");
}
}
}

通过上述方式,我们可以从数据库动态获取当前启用的支付方式,并在执行支付时应用它。

步骤 4: 控制器调用(不暴露支付方式)

在控制器层面,我们依然只关心执行支付,而不会暴露具体的支付方式。支付方式的选择完全依赖于配置文件或数据库中的设置。

import org.springframework.web.bind.annotation.*;
@RestController
@RequestMapping("/payment")
public class PaymentController {
private final PaymentContext paymentContext;
@Autowired
public PaymentController(PaymentContext paymentContext) {
this.paymentContext = paymentContext;
}
@PostMapping("/pay")
public String pay(@RequestParam double amount) {
try {
paymentContext.executePayment(amount);
return "支付成功!";
} catch (IllegalArgumentException | IllegalStateException e) {
return e.getMessage();
}
}
}

总结

  • 动态配置:通过 application.yml 或数据库存储支付方式配置,能够动态切换支付方式而不暴露给前端请求 URL。
  • 灵活扩展:新增支付方式时,只需要实现一个新的支付策略类,并在配置文件或数据库中添加相应的配置,无需修改控制器或核心业务逻辑。
  • 安全性:通过不暴露支付方式具体实现,只提供支付功能接口,增加了安全性和封装性。

这种设计不仅能够支持多种支付方式,还能够根据配置灵活切换支付策略,适应不同的支付场景。

本文作者:唐钰逍遥

本文链接:https://www.cnblogs.com/tyxy/p/18534129

版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。

posted @   唐钰逍遥  阅读(53)  评论(0编辑  收藏  举报
点击右上角即可分享
微信分享提示
评论
收藏
关注
推荐
深色
回顶
收起