koupleless 合并多个微服务应用到一个应用实例(包含springcloud gateway)
koupleless
Koupleless 是一种模块化的 Serverless 技术解决方案。基础原理是拆分成了基座+模块的概念。支持模块化开发。 适用的场景:
- 应用合并部署
- 模块化开发
- 模块隔离
- 插件化
- 优化启动速度等
- 热启动部署
拆分原则
- 基座加载所需的所有基础依赖
- 模块只需要将依赖改成provider
- 如果模块依赖基座的bean例如数据源可以使用
SpringBeanFinder.getBaseBean(DataSource.class)
maven 依赖
- 基座
<dependency>
<groupId>com.alipay.sofa.koupleless</groupId>
<artifactId>koupleless-base-starter</artifactId>
<version>${koupleless.runtime.version}</version>
</dependency>
-- 插件
<build>
<finalName>${project.artifactId}</finalName>
<plugins>
<plugin>
<groupId>com.alipay.sofa.koupleless</groupId>
<artifactId>koupleless-base-build-plugin</artifactId>
<version>${koupleless.runtime.version}</version>
<executions>
<execution>
<goals>
<goal>add-patch</goal>
</goals>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<executions>
<execution>
<goals>
<goal>repackage</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
- 模块
<dependency>
<groupId>com.alipay.sofa.koupleless</groupId>
<artifactId>koupleless-app-starter</artifactId>
<version>${koupleless.runtime.version}</version>
<scope>provided</scope>
</dependency>
<build>
<finalName>${project.artifactId}</finalName>
<plugins>
<!--这里添加ark 打包插件-->
<plugin>
<groupId>com.alipay.sofa</groupId>
<artifactId>sofa-ark-maven-plugin</artifactId>
<version>${sofa.ark.version}</version>
<executions>
<execution>
<id>default-cli</id>
<goals>
<goal>repackage</goal>
</goals>
</execution>
</executions>
<configuration>
<skipArkExecutable>true</skipArkExecutable>
<outputDirectory>./target</outputDirectory>
<bizName>hh-bidding</bizName>
<webContextPath>bidding</webContextPath>
<declaredMode>true</declaredMode>
<packExcludesConfig>rules.txt</packExcludesConfig>
</configuration>
</plugin>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<executions>
<execution>
<goals>
<goal>repackage</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
注意事项
- 模块的生命周期
模块销毁会销毁到模块的所有bean,这个时候需要注意如果引用的基座bean的话如 Datasource,可能会被销毁。所有可以,解决方法
package com.ruoyi.common.core.xss;
import javax.sql.DataSource;
import java.io.PrintWriter;
import java.sql.Connection;
import java.sql.SQLException;
import java.sql.SQLFeatureNotSupportedException;
import java.util.logging.Logger;
/**
* @author wxl
*/public class MyDataSource implements DataSource {
public DataSource dataSource;
public MyDataSource(DataSource dataSource) {
this.dataSource = dataSource;
}
@Override
public Connection getConnection() throws SQLException {
return dataSource.getConnection();
}
@Override
public Connection getConnection(String username, String password) throws SQLException {
return dataSource.getConnection(username, password);
}
@Override
public <T> T unwrap(Class<T> iface) throws SQLException {
return dataSource.unwrap(iface);
}
@Override
public boolean isWrapperFor(Class<?> iface) throws SQLException {
return dataSource.isWrapperFor(iface);
}
@Override
public PrintWriter getLogWriter() throws SQLException {
return dataSource.getLogWriter();
}
@Override
public void setLogWriter(PrintWriter out) throws SQLException {
}
@Override
public void setLoginTimeout(int seconds) throws SQLException {
dataSource.setLoginTimeout(seconds);
}
@Override
public int getLoginTimeout() throws SQLException {
return dataSource.getLoginTimeout();
}
@Override
public Logger getParentLogger() throws SQLFeatureNotSupportedException {
return dataSource.getParentLogger();
}
}
- 声明新的ds
@Bean(name = "dataSource")
@ConditionalOnMissingBean
public DataSource dataSource() {
return new MyDataSource(SpringBeanFinder.getBaseBean(DataSource.class));
}
spring cloud gateway 和web 应用合并问题
spring cloud gateway是webflux 和tomcat 部署到一起需要修改一些东西,基座需要引入
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-webflux</artifactId>
</dependency>
并配置
spring.main.web-application-type=servlet
- spring cloud gateway 应用
@SpringBootApplication(exclude = {DataSourceAutoConfiguration.class})
@EnableWebFlux
@Import({GatewayAutoConfiguration.class})
public class RuoYiGatewayApplication {
public static void main(String[] args) {
SpringApplication.run(RuoYiGatewayApplication.class, args);
}
}
- EnableWebFlux 启用webflux
- @Import({GatewayAutoConfiguration.class}) 引入spring cloud gateway 配置