一、开篇:Server 插件化设计哲学
Java Web 开发中,应用框架与底层服务器通常是强绑定的。你选了一个框架,就绑定了它支持的服务器实现。切换?往往意味着大量适配工作。

Solon 的设计哲学不同:业务代码与底层容器完全解耦。

在 Solon 中,你的 Controller、Service、Repository 等业务代码是"不变的",而底层服务器是"可插拔的"。只需要换一个 Maven 依赖,就能从 JDK 内置 HTTP 服务器(0.3MB)切换到 Jetty(2.7MB)、Undertow(4.6MB)或 Vert.x(6.3MB)——业务代码零修改。

这就是 Solon Server 插件化设计的核心价值:

维度 传统方式 Solon 方式
框架与服务器关系 强绑定 可插拔
切换服务器 改代码/改配置 换一个 Maven 依赖
包大小 通常较大 按需选择,最小 0.3MB
协议支持 通常只有 HTTP HTTP + WebSocket + Socket.D
本文将带你深入解析 Solon 的 Server 启动模式体系。

二、应用启动入口与生命周期
2.1 标准启动方式
所有 Solon 应用的入口都是 Solon.start():

@SolonMain
public class App {
public static void main(String[] args) {
Solon.start(App.class, args);
}
}
2.2 带初始化函数的启动
第三个参数是初始化函数,在应用初始化时机点执行:

@SolonMain
public class App {
public static void main(String[] args) {
Solon.start(App.class, args, app -> {
// 控制信号启停、订阅早期事件等
app.enableHttp(true);
app.enableWebSocket(true);
});
}
}
2.3 应用生命周期全景
Solon 应用的生命周期包含四个层次的时机点:

① 一个初始化函数时机点

Solon.start() 的第三个参数回调
② 六个应用事件时机点

事件 说明 订阅方式
AppInitEndEvent 应用初始化完成 只支持手动订阅
AppPluginLoadEndEvent 插件加载完成 只支持手动订阅
AppBeanLoadEndEvent Bean 扫描完成 自动/手动
AppLoadEndEvent 应用启动完成 自动/手动
AppPrestopEndEvent 应用预停止 自动/手动
AppStopEndEvent 应用停止 自动/手动
③ 三个插件生命时机点

public interface Plugin {
void start(AppContext context) throws Throwable;
default void prestop() throws Throwable {}
default void stop() throws Throwable {}
}
④ 两个容器生命时机点

AppContext::start() — 扫描完成后执行
AppContext::stop() — 插件 stop 后执行
AppBeanLoadEndEvent 之前的事件需要在启动前完成订阅,否则会错过时机。

三、启动参数体系
3.1 完整参数表
启动参数在应用启动后会被静态化(启动后不可修改)。

启动参数 对应配置 描述
–env solon.env 环境变量(配置切换)
–scanning — 是否扫描(默认 1)
–debug solon.debug 调试模式(0 或 1)
–setup solon.setup 安装模式(0 或 1)
–white solon.white 白名单模式(0 或 1)
–drift solon.drift 漂移模式(k8s 部署设为 1)
–alone solon.alone 单体模式(0 或 1)
–extend solon.extend 扩展目录
–locale solon.locale 默认地区
–config.add solon.config.add 增加外部配置
–app.name solon.app.name 应用名
–app.group solon.app.group 应用分组
–app.title solon.app.title 应用标题
–stop.safe solon.stop.safe 安全停止(0 或 1)
–stop.delay solon.stop.delay 安全停止延时秒数(默认 10)
3.2 三种等价写法
所有带 . 的启动参数同时会成为应用配置,以下三种写法完全等价:

方式一:JVM 系统属性

java -Dsolon.env=dev -jar demo.jar

方式二:完整的命令行参数

java -jar demo.jar --solon.env=dev

方式三:简写命令行参数

java -jar demo.jar --env=dev
同理,server.port 也支持三种写法:

java -Dserver.port=8081 -jar demo.jar
java -jar demo.jar --server.port=8081
四、Server 插件全景矩阵
Solon Server 系列包含所有通讯"服务启动器"插件。切换 Boot 插件只需更换 Maven/Gradle 依赖。

4.1 HTTP 类 Server 插件
插件 框架版本 包大小 信号协议 JDK要求 开源协议
solon-server-jdkhttp JDK 0.3MB http 8+ Apache 2.0
solon-server-smarthttp [国产] — 0.8MB http, ws 8+ Apache 2.0
solon-server-grizzly — 1.8MB http, ws, http2 8+ EPL-2.0
solon-server-vertx — 6.3MB http, ws, http2 8+ EPL-2.0
solon-server-jetty v9 2.7MB http, ws 8+ EPL-2.0
solon-server-jetty-jakarta v12 3.9MB http, ws, http2 17+ EPL-2.0
solon-server-undertow v2.2 4.6MB http, ws, http2 8+ Apache 2.0
solon-server-undertow-jakarta v2.3 — http, ws, http2 17+ Apache 2.0
solon-server-tomcat v9 — http, ws, http2 8+ Apache 2.0
solon-server-tomcat-jakarta v11 — http, ws, http2 17+ Apache 2.0
4.2 WebSocket 类 Server 插件
插件 包大小 信号协议 JDK要求 开源协议
solon-server-websocket 0.4MB ws 8+ MIT
solon-server-websocket-netty 3.6MB ws 8+ Apache 2.0
4.3 Socket.D 类 Server 插件
插件 包大小 信号协议 JDK要求 开源协议
solon-server-socketd 0.4MB tcp, udp, ws 8+ Apache 2.0
4.4 插件切换方法
切换 Boot 插件只需更换依赖,业务代码无需任何修改:

org.noear solon-server-jdkhttp org.noear solon-server-jetty 4.5 二级扩展插件 部分 Boot 插件有配套的二级插件,按需添加:

Boot 插件 二级插件 说明
solon-server-jetty solon-server-jetty-add-jsp 增加 JSP 视图
solon-server-jetty solon-server-jetty-add-websocket 增加 WebSocket
solon-server-tomcat solon-server-tomcat-add-jsp 增加 JSP 视图
solon-server-tomcat solon-server-tomcat-add-websocket 增加 WebSocket
solon-server-undertow solon-server-undertow-add-jsp 增加 JSP 视图
五、HTTP 模式详解
5.1 基础 Web 应用
以最轻量的 solon-server-jdkhttp(0.3MB)为例:

org.noear solon-server-jdkhttp @SolonMain public class DemoApp { public static void main(String[] args) { Solon.start(DemoApp.class, args); } }

@Controller
public class DemoController {
@Mapping(“/hello”)
public String hello(@Param(defaultValue = “world”) String name) {
return "Hello " + name + “!”;
}
}
5.2 SSL/HTTPS 配置
方式一:配置文件

server:
ssl:
keyStore: “/data/_ca/demo.jks” # 或 “demo.pfx”
keyPassword: “demo”
方式二:自定义 SSLContext(v2.5.9+)

不走配置文件,完全代码控制:

@SolonMain
public class AppDemo {
public static void main(String[] args) {
Solon.start(AppDemo.class, args, app -> {
SSLContext sslContext = buildSSLContext(); // 自行构建
app.onEvent(HttpServerConfigure.class, e -> {
e.enableSsl(true, sslContext);
});
});
}
}
5.3 额外 HTTP 端口
启用 HTTPS 后仍需保留 HTTP 端口的场景(v2.2.18+):

@SolonMain
public class SeverDemo {
public static void main(String[] args) {
Solon.start(SeverDemo.class, args, app -> {
app.onEvent(HttpServerConfigure.class, e -> {
e.addHttpPort(8082);
});
});
}
}
5.4 控制端口启停
// 关闭 HTTP 自动启动
@SolonMain
public class SeverDemo {
public static void main(String[] args) {
Solon.start(SeverDemo.class, args, app -> {
app.enableHttp(false);
});
}
}
六、WebSocket 模式
6.1 启用 WebSocket
使用 Jetty 为例(需添加二级插件):

org.noear solon-server-jetty org.noear solon-server-jetty-add-websocket @SolonMain public class DemoApp { public static void main(String[] args) { Solon.start(DemoApp.class, args, app -> { app.enableWebSocket(true); // 启用 WebSocket }); } } 6.2 WebSocket 端点 @ServerEndpoint("/ws/demo/{id}") public class WebSocketDemo extends SimpleWebSocketListener { @Override public void onMessage(WebSocket socket, String text) throws IOException { socket.send("我收到了:" + text); }
@Override
public void onOpen(WebSocket socket) {
    System.out.println("连接建立:" + socket.param("id"));
}

}
七、Socket.D 模式
7.1 依赖配置

org.noear
solon-server-socketd

org.noear socketd-transport-netty 7.2 启用 Socket.D 服务 @SolonMain public class DemoApp { public static void main(String[] args) { Solon.start(DemoApp.class, args, app -> { app.enableSocketD(true); }); } } 7.3 Socket.D 端点 @ServerEndpoint("/demo/{id}") public class SocketDDemo extends SimpleListener { @Override public void onMessage(Session session, Message message) throws IOException { session.send("test", new StringEntity("我收到了:" + message)); // session.param("id"); // 获取路径变量 } } 7.4 三种协议架构的端口分配 协议 端口计算 示例(server.socket.port=28080) sd:tcp ${server.socket.port} 28080 sd:udp ${server.socket.port} + 1 28081 sd:ws ${server.socket.port} + 2 28082 7.5 Socket.D 配置项全表 server: socket: name: "waterapi.tcp" # 信号名称 port: 28080 # 信号端口 host: "0.0.0.0" # 绑定主机 wrapPort: 28080 # 包装端口(Docker + 注册时用) wrapHost: "0.0.0.0" # 包装主机 coreThreads: 0 # 最小线程(0=自动) maxThreads: 0 # 最大线程(0=自动) idleTimeout: 0 # 闲置超时(0=自动,ms) ioBound: true # IO密集型 八、Server 配置体系 8.1 四大配置系列 系列 说明 备注 server.? 主配置 供信号配置继承 server.http.? HTTP 信号配置 — server.socket.? Socket 信号配置 — server.websocket.? WebSocket 信号配置 — 8.2 配置继承关系 当没有"信号配置"时,使用"主配置" 例如:没有 server.http.ssl 时,使用 server.ssl 端口默认值:

信号 默认端口 说明
http server.port(默认 8080) 主端口
websocket 主端口 + 15000 23080
socket 主端口 + 20000 28080
8.3 完整配置模板
solon:
app:
name: “demo”
group: “demo”
env: “dev”
stop:
safe: 1
delay: 10
threads:
virtual:
enabled: false

server:
port: 8080
host: “0.0.0.0”

SSL 主配置(所有信号共享)

ssl:
keyStore: “/data/_ca/demo.jks”
keyPassword: “demo”

HTTP 信号配置

http:
port: 8080
coreThreads: 0
maxThreads: 0
idleTimeout: 0
ioBound: true

WebSocket 信号配置

websocket:
port: 23080

Socket 信号配置

socket:
name: “demo.tcp”
port: 28080
host: “0.0.0.0”
coreThreads: 0
maxThreads: 0
idleTimeout: 0
ioBound: true
九、线程数配置
9.1 配置项
server:
http:
coreThreads: 0 # 最小线程(0=自动)
maxThreads: 0 # 最大线程(0=自动)
idleTimeout: 0 # 闲置超时(ms)
ioBound: true # IO密集型

虚拟线程池(v2.7.3+)

solon:
threads:
virtual:
enabled: false
9.2 自动计算规则
IO 密集型(ioBound: true,默认)

配置项 计算公式 2c4g 实例
coreThreads CPU 内核数 × 2 4
maxThreads coreThreads × 32 128
CPU 密集型(ioBound: false)

配置项 计算公式 2c4g 实例
coreThreads CPU 内核数 × 2 4
maxThreads coreThreads × 8 32
9.3 调优建议
coreThreads 一般不需要配置(BIO 太大不收缩,NIO 不能太大)
maxThreads 一般默认即可;单实例且流量大或请求慢时适当调大
线程数不是越多越好(切换需要时间),也不是越少越好(会不够用)
Java 21+ 可考虑开启虚拟线程:solon.threads.virtual.enabled: true
十、嵌入式启动
Solon 的所有 Server 插件均支持嵌入式启动,可直接通过 Server 实现类手动控制生命周期:

// JDK HTTP Server
JdkHttpServer server = new JdkHttpServer();
server.start(null, 8080);
// … 使用中
server.stop();

// Jetty Server
JettyServer server = new JettyServer();
server.start(null, 8080);

// Undertow Server
UndertowServer server = new UndertowServer();
server.start(null, 8080);

// Vert.x Server
VertxServer server = new VertxServer();
server.start(null, 8080);
这种模式适合:

将 Solon 嵌入到已有 Java 应用中
在单元测试中启动轻量级服务器
构建自定义的启动流程
十一、实战案例:三种服务同时运行
一个应用同时提供 HTTP API + WebSocket + Socket.D 三种服务:

11.1 Maven 依赖

org.noear solon-server-jetty org.noear solon-server-jetty-add-websocket org.noear solon-server-socketd org.noear socketd-transport-netty org.noear solon-web 11.2 配置文件 server: port: 8080

http:
port: 8080
coreThreads: 4
maxThreads: 128

websocket:
port: 8080 # 与 http 共用端口

socket:
name: “demo.tcp”
port: 28080
coreThreads: 2
maxThreads: 64
11.3 启动类
@SolonMain
public class App {
public static void main(String[] args) {
Solon.start(App.class, args, app -> {
app.enableHttp(true);
app.enableWebSocket(true);
app.enableSocketD(true);
});
}
}
11.4 HTTP 控制器
@Controller
public class ApiGateway {
@Inject
OrderService orderService;

@Mapping("/api/order/create")
public OrderDTO createOrder(@Body OrderRequest req) {
    return orderService.create(req);
}

@Mapping("/api/order/{id}")
public OrderDTO getOrder(int id) {
    return orderService.getById(id);
}

}
11.5 WebSocket 端点
@ServerEndpoint(“/ws/notify/{userId}”)
public class NotifyWebSocket extends SimpleWebSocketListener {
@Override
public void onOpen(WebSocket socket) {
String userId = socket.param(“userId”);
SessionManager.register(userId, socket);
}

@Override
public void onClose(WebSocket socket) {
    String userId = socket.param("userId");
    SessionManager.unregister(userId);
}

@Override
public void onMessage(WebSocket socket, String text) {
    // 处理客户端推送的消息
}

}
11.6 Socket.D 端点
@ServerEndpoint(“/sd/rpc”)
public class RpcSocketD extends SimpleListener {
@Override
public void onMessage(Session session, Message message) throws IOException {
if (“order.query”.equals(message.topic())) {
String orderId = message.bodyAsString();
// 处理 RPC 请求
session.reply(message, new StringEntity(“{“status”:“ok”}”));
}
}
}
十二、总结与选型建议
选型决策表
场景 推荐 Server 插件 理由
微服务 API、RESTful solon-server-jdkhttp 0.3MB 极简,够用
需要 WebSocket solon-server-jetty 或 solon-server-smarthttp 原生 WS 支持
高性能 HTTP/2 solon-server-undertow 或 solon-server-vertx HTTP/2 支持
传统 JSP 项目 solon-server-tomcat + JSP 二级插件 JSP 兼容
RPC 长连接 solon-server-socketd Socket.D 协议
最小化部署 solon-server-jdkhttp 0.3MB 包大小
国产化/信创 solon-server-smarthttp 国产 HTTP 服务器
核心要点
业务代码与 Server 完全解耦 — 只需换依赖,代码零修改
最小 0.3MB — jdkhttp 适合微服务和 Serverless
三种信号并存 — HTTP + WebSocket + Socket.D 可以同一应用运行

Logo

汇聚全球AI编程工具,助力开发者即刻编程。

更多推荐