🎯 学习目标
通过本篇教程,你将学会:
- 理解 Atlas Mapper 的 Spring Boot 自动配置机制
- 掌握 Spring Boot Starter 的使用方法
- 学会自定义配置属性和条件装配
- 理解依赖注入和 Bean 生命周期管理
📋 概念讲解:Spring Boot 集成架构
自动配置架构图
graph TB
subgraph SpringApp["Spring Boot 应用"]
A1[Application.java] --> A2["@SpringBootApplication"]
A2 --> A3[ComponentScan]
A3 --> A4[自动扫描 Mapper]
end
subgraph Starter["Atlas Mapper Starter"]
B1[atlas-mapper-spring-boot-starter] --> B2[spring.factories]
B2 --> B3[AtlasMapperAutoConfiguration]
B3 --> B4[条件装配]
B4 --> B5[Bean 注册]
end
subgraph Config["配置属性"]
C1[application.yml] --> C2["atlas.mapper.*"]
C2 --> C3[AtlasMapperProperties]
C3 --> C4[配置绑定]
end
subgraph MapperBean["Mapper Bean"]
D1["@Mapper"] --> D2["componentModel = \"spring\""]
D2 --> D3[Spring Bean]
D3 --> D4[依赖注入]
end
A3 --> D1
B5 --> D3
C4 --> B3
style A1 fill:#e8f5e8
style B1 fill:#e3f2fd
style C1 fill:#fff3e0
style D1 fill:#ffecb3
Bean 生命周期管理
sequenceDiagram
participant App as Spring Boot App
participant AC as AutoConfiguration
participant BF as BeanFactory
participant Mapper as Mapper Bean
participant Service as Business Service
App->>AC: 启动应用
AC->>AC: 检查条件装配
AC->>BF: 注册 Mapper Bean
BF->>Mapper: 创建 Mapper 实例
Mapper->>BF: 注册到容器
Service->>BF: 请求注入 Mapper
BF->>Service: 注入 Mapper Bean
Service->>Mapper: 调用映射方法
Mapper->>Service: 返回映射结果
🔧 实现步骤:Spring Boot 集成详解
步骤 1:添加 Spring Boot Starter 依赖
在你的 Spring Boot 项目中添加 Atlas Mapper Starter:
xml
<!-- pom.xml -->
<dependencies>
<!-- Spring Boot Starter Web -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!-- Atlas Mapper Spring Boot Starter -->
<dependency>
<groupId>io.github.nemoob</groupId>
<artifactId>atlas-mapper-spring-boot-starter</artifactId>
<version>1.0.0</version>
</dependency>
<!-- 其他依赖... -->
</dependencies>
步骤 2:配置属性详解
在 application.yml
中配置 Atlas Mapper:
yaml
# application.yml
atlas:
mapper:
# 🔥 基础配置
enabled: true # 是否启用 Atlas Mapper
component-model: spring # 组件模型:spring, default, cdi
# 🔥 映射策略配置
unmapped-target-policy: IGNORE # 未映射目标字段策略:IGNORE, WARN, ERROR
unmapped-source-policy: WARN # 未映射源字段策略:IGNORE, WARN, ERROR
null-value-mapping-strategy: RETURN_NULL # 空值映射策略:RETURN_NULL, RETURN_DEFAULT
null-value-check-strategy: ON_IMPLICIT_CONVERSION # 空值检查策略
# 🔥 代码生成配置
suppress-generator-timestamp: true # 是否抑制生成器时间戳
suppress-generator-version-comment: false # 是否抑制版本注释
# 🔥 性能优化配置
collection-mapping-strategy: ACCESSOR_ONLY # 集合映射策略
builder-pattern: true # 是否使用建造者模式
# 🔥 调试配置
verbose: false # 是否启用详细日志
show-generated-code: false # 是否显示生成的代码
# 🔥 自定义配置
default-component-model: spring # 默认组件模型
default-injection-strategy: FIELD # 默认注入策略:FIELD, CONSTRUCTOR
# 🔥 包扫描配置
base-packages: # 基础包扫描路径
- "com.example.mapper"
- "com.example.converter"
# 🔥 类型转换器配置
type-converters:
date-format: "yyyy-MM-dd HH:mm:ss" # 默认日期格式
number-format: "#,##0.00" # 默认数字格式
timezone: "Asia/Shanghai" # 时区设置
# Spring Boot 相关配置
spring:
application:
name: atlas-mapper-demo
# 数据源配置(如果需要)
datasource:
url: jdbc:mysql://localhost:3306/demo
username: root
password: password
driver-class-name: com.mysql.cj.jdbc.Driver
# JPA 配置(如果使用)
jpa:
hibernate:
ddl-auto: update
show-sql: true
properties:
hibernate:
format_sql: true
# 日志配置
logging:
level:
io.github.nemoob.atlas.mapper: DEBUG # Atlas Mapper 日志级别
org.springframework: INFO
com.example: DEBUG
pattern:
console: "%d{yyyy-MM-dd HH:mm:ss} [%thread] %-5level %logger{36} - %msg%n"
步骤 3:自动配置类详解
查看 Atlas Mapper 的自动配置实现:
java
/**
* Atlas Mapper 自动配置类
*/
@Configuration
@ConditionalOnClass({Mapper.class, AtlasMapperProcessor.class}) // 🔥 条件装配:类存在
@ConditionalOnProperty( // 🔥 条件装配:属性配置
prefix = "atlas.mapper",
name = "enabled",
havingValue = "true",
matchIfMissing = true
)
@EnableConfigurationProperties(AtlasMapperProperties.class) // 🔥 启用配置属性
@AutoConfigureAfter({DataSourceAutoConfiguration.class}) // 🔥 配置顺序
public class AtlasMapperAutoConfiguration {
private final AtlasMapperProperties properties;
public AtlasMapperAutoConfiguration(AtlasMapperProperties properties) {
this.properties = properties;
}
/**
* 🔥 配置 Atlas Mapper 处理器
*/
@Bean
@ConditionalOnMissingBean(AtlasMapperProcessor.class)
public AtlasMapperProcessor atlasMapperProcessor() {
AtlasMapperProcessor processor = new AtlasMapperProcessor();
// 应用配置属性
processor.setUnmappedTargetPolicy(properties.getUnmappedTargetPolicy());
processor.setNullValueMappingStrategy(properties.getNullValueMappingStrategy());
processor.setVerbose(properties.isVerbose());
processor.setSuppressGeneratorTimestamp(properties.isSuppressGeneratorTimestamp());
return processor;
}
/**
* 🔥 配置类型转换器注册表
*/
@Bean
@ConditionalOnMissingBean(TypeConverterRegistry.class)
public TypeConverterRegistry typeConverterRegistry() {
TypeConverterRegistry registry = new TypeConverterRegistry();
// 注册默认类型转换器
registry.registerConverter(new StringToDateConverter(properties.getTypeConverters().getDateFormat()));
registry.registerConverter(new NumberToStringConverter(properties.getTypeConverters().getNumberFormat()));
registry.registerConverter(new BooleanToStringConverter());
return registry;
}
/**
* 🔥 配置 Mapper 扫描器
*/
@Bean
@ConditionalOnMissingBean(MapperScanner.class)
public MapperScanner mapperScanner() {
MapperScanner scanner = new MapperScanner();
scanner.setBasePackages(properties.getBasePackages());
scanner.setComponentModel(properties.getComponentModel());
return scanner;
}
/**
* 🔥 配置性能监控(可选)
*/
@Bean
@ConditionalOnProperty(prefix = "atlas.mapper", name = "performance-monitoring", havingValue = "true")
@ConditionalOnMissingBean(MapperPerformanceMonitor.class)
public MapperPerformanceMonitor performanceMonitor() {
return new MapperPerformanceMonitor();
}
/**
* 🔥 配置缓存管理器(可选)
*/
@Bean
@ConditionalOnProperty(prefix = "atlas.mapper", name = "caching.enabled", havingValue = "true")
@ConditionalOnMissingBean(MapperCacheManager.class)
public MapperCacheManager cacheManager() {
MapperCacheManager cacheManager = new MapperCacheManager();
cacheManager.setMaxSize(properties.getCaching().getMaxSize());
cacheManager.setExpireAfterWrite(properties.getCaching().getExpireAfterWrite());
return cacheManager;
}
/**
* 🔥 配置健康检查端点
*/
@Bean
@ConditionalOnClass(HealthIndicator.class)
@ConditionalOnProperty(prefix = "atlas.mapper", name = "health-check", havingValue = "true")
public AtlasMapperHealthIndicator atlasMapperHealthIndicator() {
return new AtlasMapperHealthIndicator();
}
}
步骤 4:配置属性类
java
/**
* Atlas Mapper 配置属性类
*/
@ConfigurationProperties(prefix = "atlas.mapper")
@Data
public class AtlasMapperProperties {
/**
* 是否启用 Atlas Mapper
*/
private boolean enabled = true;
/**
* 组件模型
*/
private String componentModel = "spring";
/**
* 未映射目标字段策略
*/
private ReportingPolicy unmappedTargetPolicy = ReportingPolicy.IGNORE;
/**
* 未映射源字段策略
*/
private ReportingPolicy unmappedSourcePolicy = ReportingPolicy.WARN;
/**
* 空值映射策略
*/
private NullValueMappingStrategy nullValueMappingStrategy = NullValueMappingStrategy.RETURN_NULL;
/**
* 空值检查策略
*/
private NullValueCheckStrategy nullValueCheckStrategy = NullValueCheckStrategy.ON_IMPLICIT_CONVERSION;
/**
* 是否抑制生成器时间戳
*/
private boolean suppressGeneratorTimestamp = true;
/**
* 是否抑制版本注释
*/
private boolean suppressGeneratorVersionComment = false;
/**
* 集合映射策略
*/
private CollectionMappingStrategy collectionMappingStrategy = CollectionMappingStrategy.ACCESSOR_ONLY;
/**
* 是否使用建造者模式
*/
private boolean builderPattern = false;
/**
* 是否启用详细日志
*/
private boolean verbose = false;
/**
* 是否显示生成的代码
*/
private boolean showGeneratedCode = false;
/**
* 默认组件模型
*/
private String defaultComponentModel = "spring";
/**
* 默认注入策略
*/
private InjectionStrategy defaultInjectionStrategy = InjectionStrategy.FIELD;
/**
* 基础包扫描路径
*/
private List<String> basePackages = new ArrayList<>();
/**
* 类型转换器配置
*/
private TypeConverters typeConverters = new TypeConverters();
/**
* 缓存配置
*/
private Caching caching = new Caching();
/**
* 性能监控配置
*/
private boolean performanceMonitoring = false;
/**
* 健康检查配置
*/
private boolean healthCheck = false;
/**
* 类型转换器配置类
*/
@Data
public static class TypeConverters {
private String dateFormat = "yyyy-MM-dd HH:mm:ss";
private String numberFormat = "#,##0.00";
private String timezone = "Asia/Shanghai";
private boolean enableCustomConverters = true;
}
/**
* 缓存配置类
*/
@Data
public static class Caching {
private boolean enabled = false;
private long maxSize = 1000L;
private Duration expireAfterWrite = Duration.ofMinutes(30);
private Duration expireAfterAccess = Duration.ofMinutes(10);
}
}
步骤 5:在 Spring Boot 应用中使用
创建 Spring Boot 主类
java
/**
* Spring Boot 应用主类
*/
@SpringBootApplication
@EnableAtlasMapper // 🔥 启用 Atlas Mapper(可选,自动配置会处理)
public class AtlasMapperDemoApplication {
public static void main(String[] args) {
SpringApplication.run(AtlasMapperDemoApplication.class, args);
}
/**
* 🔥 自定义配置 Bean(可选)
*/
@Bean
public AtlasMapperConfigurer atlasMapperConfigurer() {
return new AtlasMapperConfigurer() {
@Override
public void configure(AtlasMapperConfiguration configuration) {
// 自定义配置
configuration.setDefaultDateFormat("yyyy/MM/dd");
configuration.setDefaultNumberFormat("¥#,##0.00");
}
};
}
}
创建 Mapper 接口
java
/**
* 用户映射器 - 自动注册为 Spring Bean
*/
@Mapper(componentModel = "spring") // 🔥 指定为 Spring 组件
public interface UserMapper {
UserDto toDto(User user);
User toEntity(UserDto dto);
List<UserDto> toDtoList(List<User> users);
/**
* 🔥 使用配置属性中的默认格式
*/
@Mapping(target = "createdTime", source = "createdAt", dateFormat = "${atlas.mapper.type-converters.date-format}")
UserDetailDto toDetailDto(User user);
}
在 Service 中注入使用
java
/**
* 用户服务类 - 注入 Mapper
*/
@Service
@Transactional
public class UserService {
private final UserRepository userRepository;
private final UserMapper userMapper; // 🔥 自动注入 Mapper
// 🔥 构造器注入(推荐)
public UserService(UserRepository userRepository, UserMapper userMapper) {
this.userRepository = userRepository;
this.userMapper = userMapper;
}
/**
* 获取用户列表
*/
public List<UserDto> getAllUsers() {
List<User> users = userRepository.findAll();
return userMapper.toDtoList(users); // 🔥 使用注入的 Mapper
}
/**
* 根据 ID 获取用户
*/
public UserDto getUserById(Long id) {
User user = userRepository.findById(id)
.orElseThrow(() -> new EntityNotFoundException("用户不存在: " + id));
return userMapper.toDto(user);
}
/**
* 创建用户
*/
public UserDto createUser(UserDto userDto) {
User user = userMapper.toEntity(userDto); // 🔥 DTO -> Entity
user.setCreatedAt(LocalDateTime.now());
user.setUpdatedAt(LocalDateTime.now());
User savedUser = userRepository.save(user);
return userMapper.toDto(savedUser); // 🔥 Entity -> DTO
}
/**
* 更新用户
*/
public UserDto updateUser(Long id, UserDto userDto) {
User existingUser = userRepository.findById(id)
.orElseThrow(() -> new EntityNotFoundException("用户不存在: " + id));
// 🔥 部分更新:只更新非空字段
updateUserFields(existingUser, userDto);
existingUser.setUpdatedAt(LocalDateTime.now());
User updatedUser = userRepository.save(existingUser);
return userMapper.toDto(updatedUser);
}
/**
* 批量转换
*/
public List<UserDto> convertUsers(List<User> users) {
return userMapper.toDtoList(users);
}
/**
* 辅助方法:更新用户字段
*/
private void updateUserFields(User target, UserDto source) {
if (source.getName() != null) {
target.setName(source.getName());
}
if (source.getEmail() != null) {
target.setEmail(source.getEmail());
}
// 其他字段更新...
}
}
创建 REST 控制器
java
/**
* 用户控制器
*/
@RestController
@RequestMapping("/api/users")
@Validated
public class UserController {
private final UserService userService;
public UserController(UserService userService) {
this.userService = userService;
}
/**
* 获取所有用户
*/
@GetMapping
public ResponseEntity<List<UserDto>> getAllUsers() {
List<UserDto> users = userService.getAllUsers();
return ResponseEntity.ok(users);
}
/**
* 根据 ID 获取用户
*/
@GetMapping("/{id}")
public ResponseEntity<UserDto> getUserById(@PathVariable Long id) {
UserDto user = userService.getUserById(id);
return ResponseEntity.ok(user);
}
/**
* 创建用户
*/
@PostMapping
public ResponseEntity<UserDto> createUser(@Valid @RequestBody UserDto userDto) {
UserDto createdUser = userService.createUser(userDto);
return ResponseEntity.status(HttpStatus.CREATED).body(createdUser);
}
/**
* 更新用户
*/
@PutMapping("/{id}")
public ResponseEntity<UserDto> updateUser(
@PathVariable Long id,
@Valid @RequestBody UserDto userDto) {
UserDto updatedUser = userService.updateUser(id, userDto);
return ResponseEntity.ok(updatedUser);
}
/**
* 删除用户
*/
@DeleteMapping("/{id}")
public ResponseEntity<Void> deleteUser(@PathVariable Long id) {
userService.deleteUser(id);
return ResponseEntity.noContent().build();
}
}
💻 示例代码:完整的 Spring Boot 集成示例
示例 1:多环境配置
yaml
# application.yml - 基础配置
atlas:
mapper:
enabled: true
component-model: spring
base-packages:
- "com.example.mapper"
---
# application-dev.yml - 开发环境
spring:
config:
activate:
on-profile: dev
atlas:
mapper:
verbose: true # 开发环境启用详细日志
show-generated-code: true # 显示生成的代码
performance-monitoring: true # 启用性能监控
logging:
level:
io.github.nemoob.atlas.mapper: DEBUG
---
# application-prod.yml - 生产环境
spring:
config:
activate:
on-profile: prod
atlas:
mapper:
verbose: false # 生产环境关闭详细日志
show-generated-code: false
performance-monitoring: true # 保持性能监控
caching:
enabled: true # 启用缓存
max-size: 10000
expire-after-write: PT1H # 1小时过期
logging:
level:
io.github.nemoob.atlas.mapper: WARN
示例 2:自定义配置器
java
/**
* 自定义 Atlas Mapper 配置器
*/
@Configuration
public class AtlasMapperCustomConfiguration {
/**
* 🔥 自定义类型转换器
*/
@Bean
public CustomTypeConverter customTypeConverter() {
return new CustomTypeConverter();
}
/**
* 🔥 自定义映射策略
*/
@Bean
public AtlasMapperConfigurer customMapperConfigurer() {
return configuration -> {
// 自定义默认配置
configuration.setDefaultDateFormat("yyyy年MM月dd日");
configuration.setDefaultNumberFormat("¥#,##0.00");
configuration.setDefaultTimeZone(ZoneId.of("Asia/Shanghai"));
// 注册自定义转换器
configuration.addTypeConverter(new MoneyConverter());
configuration.addTypeConverter(new PhoneNumberConverter());
// 设置命名策略
configuration.setFieldNamingStrategy(new CamelCaseNamingStrategy());
};
}
/**
* 🔥 自定义 Mapper 后处理器
*/
@Bean
public MapperPostProcessor mapperPostProcessor() {
return new MapperPostProcessor() {
@Override
public void postProcessMapper(Object mapper, String mapperName) {
log.info("Mapper 创建完成: {}", mapperName);
// 可以在这里添加额外的初始化逻辑
if (mapper instanceof BaseMapper) {
((BaseMapper) mapper).initialize();
}
}
};
}
/**
* 🔥 条件化配置 - 仅在特定条件下生效
*/
@Bean
@ConditionalOnProperty(prefix = "atlas.mapper", name = "advanced-features", havingValue = "true")
public AdvancedMapperFeatures advancedMapperFeatures() {
return new AdvancedMapperFeatures();
}
/**
* 🔥 Profile 特定配置
*/
@Bean
@Profile("development")
public MapperDebugger mapperDebugger() {
return new MapperDebugger();
}
}
示例 3:健康检查和监控
java
/**
* Atlas Mapper 健康检查指示器
*/
@Component
@ConditionalOnProperty(prefix = "atlas.mapper", name = "health-check", havingValue = "true")
public class AtlasMapperHealthIndicator implements HealthIndicator {
private final MapperRegistry mapperRegistry;
private final MapperPerformanceMonitor performanceMonitor;
public AtlasMapperHealthIndicator(MapperRegistry mapperRegistry,
MapperPerformanceMonitor performanceMonitor) {
this.mapperRegistry = mapperRegistry;
this.performanceMonitor = performanceMonitor;
}
@Override
public Health health() {
try {
// 检查 Mapper 注册状态
int registeredMappers = mapperRegistry.getRegisteredMapperCount();
// 检查性能指标
PerformanceMetrics metrics = performanceMonitor.getMetrics();
// 构建健康状态
Health.Builder builder = Health.up()
.withDetail("registeredMappers", registeredMappers)
.withDetail("totalMappings", metrics.getTotalMappings())
.withDetail("averageExecutionTime", metrics.getAverageExecutionTime())
.withDetail("errorRate", metrics.getErrorRate());
// 检查错误率
if (metrics.getErrorRate() > 0.1) { // 错误率超过 10%
builder.down().withDetail("reason", "High error rate: " + metrics.getErrorRate());
}
// 检查平均执行时间
if (metrics.getAverageExecutionTime() > 1000) { // 平均执行时间超过 1 秒
builder.down().withDetail("reason", "High execution time: " + metrics.getAverageExecutionTime() + "ms");
}
return builder.build();
} catch (Exception e) {
return Health.down()
.withDetail("error", e.getMessage())
.build();
}
}
}
示例 4:性能监控和指标
java
/**
* Atlas Mapper 性能监控
*/
@Component
@ConditionalOnProperty(prefix = "atlas.mapper", name = "performance-monitoring", havingValue = "true")
public class AtlasMapperPerformanceMonitor {
private final MeterRegistry meterRegistry;
private final Timer.Sample sample;
public AtlasMapperPerformanceMonitor(MeterRegistry meterRegistry) {
this.meterRegistry = meterRegistry;
this.sample = Timer.start(meterRegistry);
}
/**
* 记录映射执行时间
*/
public void recordMappingTime(String mapperName, String methodName, long executionTime) {
Timer.builder("atlas.mapper.execution.time")
.tag("mapper", mapperName)
.tag("method", methodName)
.register(meterRegistry)
.record(executionTime, TimeUnit.MILLISECONDS);
}
/**
* 记录映射错误
*/
public void recordMappingError(String mapperName, String methodName, Exception error) {
Counter.builder("atlas.mapper.errors")
.tag("mapper", mapperName)
.tag("method", methodName)
.tag("error", error.getClass().getSimpleName())
.register(meterRegistry)
.increment();
}
/**
* 记录映射成功
*/
public void recordMappingSuccess(String mapperName, String methodName) {
Counter.builder("atlas.mapper.success")
.tag("mapper", mapperName)
.tag("method", methodName)
.register(meterRegistry)
.increment();
}
/**
* 获取性能指标
*/
public PerformanceMetrics getMetrics() {
// 实现指标收集逻辑
return new PerformanceMetrics();
}
}
/**
* 性能指标数据类
*/
@Data
public class PerformanceMetrics {
private long totalMappings;
private double averageExecutionTime;
private double errorRate;
private Map<String, Long> mapperUsageCount;
private Map<String, Double> mapperAverageTime;
}
🎬 效果演示:Spring Boot 集成测试
创建集成测试
java
/**
* Spring Boot 集成测试
*/
@SpringBootTest
@TestPropertySource(properties = {
"atlas.mapper.enabled=true",
"atlas.mapper.verbose=true",
"atlas.mapper.performance-monitoring=true"
})
class AtlasMapperIntegrationTest {
@Autowired
private UserService userService;
@Autowired
private UserMapper userMapper;
@Autowired
private AtlasMapperProperties properties;
@Test
void testMapperAutoConfiguration() {
// 验证 Mapper 自动注入
assertThat(userMapper).isNotNull();
assertThat(userService).isNotNull();
}
@Test
void testConfigurationProperties() {
// 验证配置属性
assertThat(properties.isEnabled()).isTrue();
assertThat(properties.isVerbose()).isTrue();
assertThat(properties.getComponentModel()).isEqualTo("spring");
}
@Test
void testMappingFunctionality() {
// 创建测试数据
User user = new User();
user.setId(1L);
user.setName("张三");
user.setEmail("zhangsan@example.com");
user.setCreatedAt(LocalDateTime.now());
// 测试映射功能
UserDto dto = userMapper.toDto(user);
assertThat(dto).isNotNull();
assertThat(dto.getId()).isEqualTo(user.getId());
assertThat(dto.getName()).isEqualTo(user.getName());
assertThat(dto.getEmail()).isEqualTo(user.getEmail());
}
@Test
void testServiceIntegration() {
// 测试服务层集成
UserDto userDto = new UserDto();
userDto.setName("李四");
userDto.setEmail("lisi@example.com");
// 这里需要 Mock Repository 或使用 @DataJpaTest
// UserDto result = userService.createUser(userDto);
// assertThat(result).isNotNull();
}
}
启动应用测试
bash
# 启动应用
mvn spring-boot:run
# 或者使用不同的 Profile
mvn spring-boot:run -Dspring-boot.run.profiles=dev
# 测试 API 端点
curl -X GET http://localhost:8080/api/users
curl -X POST http://localhost:8080/api/users \
-H "Content-Type: application/json" \
-d '{"name":"张三","email":"zhangsan@example.com"}'
# 查看健康检查
curl http://localhost:8080/actuator/health/atlasMapper
# 查看性能指标
curl http://localhost:8080/actuator/metrics/atlas.mapper.execution.time
❓ 常见问题
Q1: Mapper 没有被自动注入怎么办?
A: 检查以下几个方面:
java
// 1. 确保 @Mapper 注解配置正确
@Mapper(componentModel = "spring") // 必须指定 componentModel
public interface UserMapper {
// ...
}
// 2. 确保包扫描路径正确
@SpringBootApplication
@ComponentScan(basePackages = {"com.example"}) // 包含 Mapper 所在包
public class Application {
// ...
}
// 3. 检查配置是否启用
atlas:
mapper:
enabled: true # 确保启用
// 4. 查看生成的实现类
// target/generated-sources/annotations/ 目录下应该有生成的实现类
Q2: 如何自定义 Mapper 的 Bean 名称?
A : 使用 @Component
注解指定名称:
java
@Mapper(componentModel = "spring")
@Component("customUserMapper") // 自定义 Bean 名称
public interface UserMapper {
// ...
}
// 注入时使用自定义名称
@Autowired
@Qualifier("customUserMapper")
private UserMapper userMapper;
Q3: 如何在不同环境使用不同的映射策略?
A: 使用 Profile 特定配置:
yaml
# application-dev.yml
atlas:
mapper:
unmapped-target-policy: WARN # 开发环境警告
verbose: true
# application-prod.yml
atlas:
mapper:
unmapped-target-policy: IGNORE # 生产环境忽略
verbose: false
Q4: 如何监控 Mapper 的性能?
A: 启用性能监控和指标收集:
yaml
# 配置
atlas:
mapper:
performance-monitoring: true
management:
endpoints:
web:
exposure:
include: health,metrics,info
endpoint:
health:
show-details: always
java
// 自定义性能监控
@Component
public class MapperPerformanceAspect {
@Around("@within(io.github.nemoob.atlas.mapper.Mapper)")
public Object monitorPerformance(ProceedingJoinPoint joinPoint) throws Throwable {
long startTime = System.currentTimeMillis();
try {
Object result = joinPoint.proceed();
long executionTime = System.currentTimeMillis() - startTime;
log.info("Mapper method {} executed in {} ms",
joinPoint.getSignature().getName(), executionTime);
return result;
} catch (Exception e) {
log.error("Mapper method {} failed", joinPoint.getSignature().getName(), e);
throw e;
}
}
}
🎯 本章小结
通过本章学习,你应该掌握了:
- 自动配置:理解 Spring Boot 自动配置机制和条件装配
- 配置属性:掌握配置文件的使用和自定义配置
- 依赖注入:学会在 Spring 容器中使用 Mapper
- 监控集成:了解健康检查和性能监控的实现
📖 下一步学习
在下一篇教程中,我们将学习:
- 单元测试和集成测试的编写
- Mock 和测试数据的准备
- 测试覆盖率和质量保证