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

Spring Boot → Solon 注解迁移实战指南:一张对照表说清楚

一、写在前面

如果你会 Spring Boot,那你已经会了一大半 Solon。

Solon 不是 Spring 的分支或封装,它是独立发展的全栈应用开发框架。但在设计哲学上,Solon 遵循了 Java 主流的 IoC、AOP、MVC 范式——概念相同,注解名不同

这篇文章把 Spring Boot 到 Solon 的注解映射、配置迁移、关键差异整理成对照表,供迁移参考。

二、IoC/DI 容器:注解对照

核心原则:Solon 将 Spring 的多个细分注解合并为少数几个核心注解。

2.1 组件注册

SolonSpring Boot说明
@Component@Component/@Service/@Repository/@DaoSolon 统一用一个注解
@Configuration@Configuration完全一致
@Bean@Bean完全一致

2.2 依赖注入

SolonSpring Boot说明
@Inject@Autowired按类型注入(by type)
@Inject("name")@Qualifier+@Autowired按名称注入(by name)
@Inject("${key}")@Value("${key}")注入配置值
@BindProps(prefix="xxx")@ConfigurationProperties(prefix="xxx")绑定属性集

注意:Solon 的@Inject一个注解兼顾了 Spring 中@Autowired@Qualifier@Value三个注解的功能。

2.3 生命周期与作用域

SolonSpring Boot说明
@Init@PostConstruct组件初始化回调
@Destroy@PreDestroy组件销毁回调
LifecycleBeanInitializingBean+DisposableBean接口方式控制生命周期
AppLoadEndEventApplicationRunner/CommandLineRunner应用启动后执行
@Singleton(默认)@Scope("singleton")单例(Solon 默认)
@Singleton(false)@Scope("prototype")多例
@Condition(...)@ConditionalOnClass/@ConditionalOnPropertySolon 统一为单一注解
@Import@Import+@ComponentScan导入组件/配置类

三、Web 层:Controller 改写

3.1 注解映射

SolonSpring Boot说明
@Controller@Controller/@RestControllerSolon 默认 JSON 输出
@Mapping@RequestMapping路由映射
@Get+@Mapping@GetMappingGET 方法限定
@Post+@Mapping@PostMappingPOST 方法限定
@Put+@Mapping@PutMappingPUT 方法限定
@Delete+@Mapping@DeleteMappingDELETE 方法限定
@Param@RequestParam请求参数
@Path@PathVariable路径变量
@Body@RequestBody请求体
@Header@RequestHeader请求头
@Cookie@CookieValueCookie
@Produces—(Spring 无直接等价)声明输出类型
@Consumes—(Spring 无直接等价)声明输入类型

3.2 Before / After 示例

Spring Boot 写法:

@RestController @RequestMapping("/users") public class UserController { @Autowired private UserService userService; @GetMapping("/{id}") public User getUser(@PathVariable Long id) { return userService.findById(id); } @PostMapping public User create(@RequestBody User user) { return userService.save(user); } }

Solon 写法:

@Controller @Mapping("/users") public class UserController { @Inject private UserService userService; @Get @Mapping("/{id}") public User getUser(@Path Long id) { return userService.findById(id); } @Post @Mapping public User create(@Body User user) { return userService.save(user); } }

3.3 关键差异:Context 替代 Servlet API

Solon不依赖 Servlet 容器,因此HttpServletRequest/HttpServletResponse需替换为Context

// Spring 写法 public User get(HttpServletRequest request) { String token = request.getHeader("Token"); String id = request.getParameter("id"); } // Solon 写法 public User get(Context ctx) { String token = ctx.header("Token"); String id = ctx.param("id"); // ctx.redirect(url) 重定向 // ctx.render(obj) 渲染 // ctx.remoteIp() 客户端 IP }

⚠️Context只能在方法参数中注入,不能作为字段注入。

四、配置文件迁移

4.1 文件命名

项目Spring BootSolon
主配置文件application.ymlapp.yml
环境配置文件application-dev.ymlapp-dev.yml
激活方式spring.profiles.active=devsolon.env=dev

4.2 常用配置键名对照

含义Spring BootSolon
应用名spring.application.namesolon.app.name
端口server.portserver.port(不变)
上下文路径server.servlet.context-pathserver.contextPath
数据源spring.datasource.urlsolon.dataSources.db1.url
日志级别logging.level.com.xxsolon.logging.level.com.xx
环境切换spring.profiles.activesolon.env

⚠️ Solon 配置键名统一使用驼峰命名contextPath),不是短横线(context-path)。

五、数据访问:@Db 一站式注入

5.1 多数据源配置(YAML)

solon.dataSources: db1: class: com.zaxxer.hikari.HikariDataSource url: jdbc:mysql://localhost/test driverClassName: com.mysql.cj.jdbc.Driver username: root password: 123456 db2: url: jdbc:mysql://localhost/order driverClassName: com.mysql.cj.jdbc.Driver username: root password: 123456

5.2 @Db 注入

// Solon 一行搞定多数据源 @Db("db1") UserMapper userMapper; @Db("db2") OrderMapper orderMapper;

对比 Spring Boot 多数据源需要配置:多个DataSource+ 多个SqlSessionFactory+ 多个TransactionManager+@MapperScan...Solon 使用@Db

5.3 ORM 集成

ORMSpring Boot 依赖Solon 依赖
MyBatismybatis-spring-boot-startermybatis-solon-plugin
MyBatis-Plusmybatis-plus-spring-boot-startermybatis-plus-solon-plugin
JPAspring-boot-starter-data-jpasolon-data-jpa
Easy-Queryeasy-query-spring-boot-startereasy-query-solon-plugin

5.4 事务

SolonSpring Boot说明
@Transaction@Transactional声明式事务
@Transaction(policy = TranPolicy.requires_new)@Transactional(propagation = Propagation.REQUIRES_NEW)事务传播策略

Solon 的@Transaction默认遇到任何异常都回滚,无需指定异常类型。

六、测试迁移

SolonSpring Boot说明
@SolonTest(App.class)@SpringBootTest测试启动
@SolonTest(env="test")@ActiveProfiles("test")测试环境
HttpTesterMockMvcHTTP 接口测试
@Rollback@Transactional+@Rollback事务回滚
@Import(profiles=...)@TestPropertySource导入测试属性

HttpTester 用法示例:

@SolonTest(App.class) public class UserControllerTest extends HttpTester { @Test public void testGetUser() { // GET 请求 String resp = path("/users/1").get(); assertEquals(200, resp.code()); // POST 请求 String json = "{\"name\":\"test\"}"; String resp2 = path("/users").body(json).post(); assertContains(resp2, "test"); } }

七、其他常见对照

场景Spring BootSolon
拦截器HandlerInterceptor@Around注解或 Solon Filter
定时任务@Scheduled@Scheduled(同名)+@EnableScheduling
文件上传MultipartFileUploadedFile(用法一致)
RPC 调用@FeignClient@NamiClient
注册发现@EnableDiscoveryClient无需注解,引入插件自动生效
配置刷新@RefreshScope无需注解,配置变更自动感知

八、迁移检查清单

  • POM:spring-boot-starter-parentsolon-parent
  • POM:spring-boot-starter-*solon-*/*-solon-plugin
  • 配置:application.ymlapp.yml(环境文件同理)
  • 启动类:@SpringBootApplication@SolonMain
  • 启动:SpringApplication.run()Solon.start()
  • IoC:@Autowired@Inject
  • IoC:@Service/@Repository@Component
  • Web:@RestController@Controller
  • Web:@RequestMapping@Mapping
  • Web:@PathVariable@Path
  • Web:HttpServletRequestContext
  • 配置:@Value@Inject("${...}")
  • 数据:spring.datasource.*solon.dataSources.*
  • 数据:@Transactional@Transaction
  • 测试:@SpringBootTest@SolonTest
  • 测试:MockMvcHttpTester

九、写在最后

这篇对照表覆盖了日常开发中最常用的 90% 场景。Solon 的注解体系并非简单的"换皮",它在统一性(@Component/@Inject/@Condition)和简便性(@Db/ 无需@RefreshScope)上做了明显的设计取舍。

http://www.gsyq.cn/news/1603969.html

相关文章:

  • Spring Boot Starter 开发规范
  • 基于JPBC库实现国密SM9标识密码算法:Java工程实践指南
  • 如何用MicroPython BLE HID库构建智能无线控制解决方案:从理论到实践
  • LeNet-5 是什么
  • 阿里云灵积SDK深度解析:打造.NET生态的AI开发利器
  • Rust 宏系统编译阶段行为
  • CVE-2025-23419漏洞实战:从应急响应到补丁管理的完整闭环
  • GitOps 工业化的七个核心决策
  • 任务依赖图解析:DAG的声明式编排与自动并行化
  • QModMaster终极指南:如何用免费开源工具轻松调试ModBus设备
  • 深度探索Ryujinx:用C构建的Nintendo Switch模拟器技术奥秘
  • 2026TypeScript前端高频面试题总结大全(最新版)
  • 道歉声明登报怎么办理?办理道歉声明登报需要哪些材料?
  • 终极音乐解锁指南:如何在浏览器中自由转换加密音乐文件
  • 百度文库文档免费获取工具:127行代码实现高效自动化解决方案
  • 深入浅出 Linux 进程间通信:从匿名管道到内核 System V 对象
  • 鸿蒙原生 ArkTS 布局深度解析:RelativeContainer 与宽高比控制实战
  • MSP430X寄存器操作与寻址模式深度解析:嵌入式底层开发核心机制
  • CDS API终极指南:3步解锁全球气象数据的Python实战教程
  • [智能体-586]:OpenClaw(小龙虾) Hermes Agent 全量注意事项与潜在坑
  • ChatGPT Plus / Pro 使用心得整理:真正拉开差距的,不是版本,而是用法
  • Java毕设选题推荐:基于 JavaWeb 的油田耗材物资台账管理系统 油田生产物资库存统计与调度管理系统【附源码、mysql、文档、调试+代码讲解+全bao等】
  • 数据库工程:生产环境索引策略落地全示例‌
  • 从 0 开始学习 AI 测试 - 从接口测试来教你如何用 AI 来生成自动化测试代码
  • Mac Mouse Fix终极指南:让你的普通鼠标在macOS上实现专业级体验
  • MSPM0 LFSS低功耗子系统:RTC、看门狗与篡改检测的实战配置
  • 暗黑破坏神2存档编辑器:5分钟掌握免费D2/D2R游戏存档修改
  • 文科背景想懂技术商业管理-国内硕士转型路径与交大MTT五力培养
  • 接口测试全流程实战:从设计到自动化,构建高效质量保障体系
  • C# 内存安全性的重大演进:重新定义 unsafe 关键字