You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Java8/Spring5项目:服务定位器模式下可配置Validator子集实现方案

我来分享一个适配Java 8/Spring 5环境、严格遵循SOLID原则且完全配置化的最优实现方案,完美匹配你的需求:

核心思路概述

通过Spring原生特性+配置映射+抽象封装的组合,实现IBase实现类与Validator子集的动态绑定,全程无需硬编码逻辑,同时满足开闭、单一职责等SOLID要求。


1. 配置层:定义IBase与Validator的映射规则

在application.properties中添加配置,直接指定每个IBase实现类(全限定名)对应的Validator Bean名称列表:

# 格式:base.validators.[IBase实现类全限定名]=[逗号分隔的Validator Bean名称]
base.validators.com.example.service.IBaseImplA=validatorA
base.validators.com.example.service.IBaseImplB=validatorB,validatorC
base.validators.com.example.service.IBaseImplC=validatorA,validatorB,validatorC,validatorN

# 单独控制每个Validator是否启用(对应原需求的enabled属性)
validators.validatorA.enabled=true
validators.validatorB.enabled=true
validators.validatorC.enabled=true
validators.validatorN.enabled=true

2. Validator层:基于Spring条件注解动态加载

用Spring的@ConditionalOnProperty替代手动init方法判断,让Spring自动管理Validator Bean的创建与否,完全符合Spring生态:

@Component("validatorA")
@ConditionalOnProperty(prefix = "validators", name = "validatorA.enabled", havingValue = "true", matchIfMissing = true)
public class ValidatorA implements Validator {
    @Override
    public void validate(Request req) {
        // 具体验证逻辑
    }
}
  • 当enabled为true时,该Validator会被注册为Spring Bean;反之则不会被加载
  • matchIfMissing = true配置可以让Validator默认启用,无需额外配置

3. 映射器层:实现IBase与Validator的动态绑定

创建一个单一职责的ValidatorMapper组件,负责读取配置、建立映射关系,同时提供根据IBase实例获取对应Validator列表的方法:

@Component
public class ValidatorMapper {

    private final Map<String, List<Validator>> validatorMap = new ConcurrentHashMap<>();
    private final ApplicationContext applicationContext;

    // 构造注入Spring上下文与配置映射
    public ValidatorMapper(ApplicationContext applicationContext,
                           @Value("#{${base.validators}}") Map<String, String> baseValidatorConfig) {
        this.applicationContext = applicationContext;
        initValidatorMapping(baseValidatorConfig);
    }

    // 初始化映射关系
    private void initValidatorMapping(Map<String, String> config) {
        config.forEach((baseClassFullName, validatorNames) -> {
            List<Validator> validators = Arrays.stream(validatorNames.split(","))
                    .map(String::trim)
                    .map(applicationContext::getBean)
                    .map(Validator.class::cast)
                    .collect(Collectors.toList());
            validatorMap.put(baseClassFullName, validators);
        });
    }

    // 根据IBase实例获取对应的Validator子集
    public List<Validator> getValidatorsForBase(IBase baseInstance) {
        String className = baseInstance.getClass().getName();
        return validatorMap.getOrDefault(className, Collections.emptyList());
    }
}
  • 完全配置化:新增IBase实现或Validator,仅需修改配置文件,无需修改代码
  • 容错处理:可以在initValidatorMapping中添加日志或异常捕获,处理配置的Validator Bean不存在的情况

4. IBase层:抽象封装验证逻辑,避免重复代码

创建抽象基类AbstractBase,封装验证逻辑,让所有IBase实现类专注于业务逻辑,符合单一职责原则:

public abstract class AbstractBase implements IBase {

    @Autowired
    private ValidatorMapper validatorMapper;

    // 统一验证入口
    protected void validateRequest(Request req) {
        List<Validator> validators = validatorMapper.getValidatorsForBase(this);
        validators.forEach(validator -> validator.validate(req));
    }

    // 模板方法:先验证再执行业务
    @Override
    public void handleRequest(Request req) {
        validateRequest(req);
        executeBusinessLogic(req);
    }

    // 子类实现具体业务逻辑
    protected abstract void executeBusinessLogic(Request req);
}

然后让所有IBase实现类继承该抽象类:

@Component("baseA")
public class IBaseImplA extends AbstractBase {
    @Override
    protected void executeBusinessLogic(Request req) {
        // IBaseImplA的具体业务逻辑
    }
}

5. 适配Service Locator Pattern

由于你的IBase实现基于Service Locator运行,只需用Spring的ServiceLocatorFactoryBean实现Locator接口,确保获取到的IBase实例已自动注入ValidatorMapper:

@Configuration
public class ServiceLocatorConfig {

    @Bean
    public ServiceLocatorFactoryBean baseServiceLocator() {
        ServiceLocatorFactoryBean factoryBean = new ServiceLocatorFactoryBean();
        factoryBean.setServiceLocatorInterface(IBaseLocator.class);
        return factoryBean;
    }

    // 定义Service Locator接口
    public interface IBaseLocator {
        IBase getBase(String baseBeanName); // 根据Bean名称获取IBase实例
    }
}

为什么符合SOLID原则?

  • 单一职责:Validator只做验证、ValidatorMapper只做映射、IBase实现只做业务逻辑
  • 开闭原则:新增IBase实现或Validator,仅需添加配置和对应类,无需修改现有代码
  • 里氏替换:所有IBase子类可无缝替换抽象基类,不影响功能
  • 接口隔离:Validator接口仅包含validate方法,IBase接口专注于业务方法,无冗余依赖
  • 依赖倒置:IBase实现依赖抽象的Validator接口和ValidatorMapper服务,而非具体实现类

内容的提问来源于stack exchange,提问作者Valamorde

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.09 20:23:16