ARTICLE DETAIL

资讯详情

深耕郑州网站建设与运营推广的一线实战洞察。

Flowable多数据源整合PostgreSQL指定Schema实战与避坑总结

Flowable多数据源整合PostgreSQL指定Schema实战与避坑总结 前阵子帮一个老项目接 Flowable需求听起来很简单业务表继续留在主库里流程引擎那几十张 ACT_ 开头的表放到独立数据源并且 PostgreSQL 环境下还得落到指定 schema 里。结果从配置到跑通整整折腾了两个下午期间踩过的坑包括但不限于引擎把表建到了 public schema、多数据源事务互相串、以及被一个看起来像 Flowable 报错、实际是 API 校验的 invalid schema 错误误导了半天。这篇就把这段实战经验完整复盘一遍从多数据源装配、指定 Schema 的原理到常见的翻车现场和排查思路一次性讲透适合正在做 Flowable 集成、或者准备把工作流引擎从业务库中隔离出来的同学参考。1. 场景设定与整体设计思路1.1 为什么业务库和数据源必须分离Flowable 作为 Java 生态里最主流的 BPMN 工作流引擎之一开箱即用确实方便但它默认行为很“霸道”一旦你把flowable-spring-boot-starter-process引入工程它就会自动寻找容器里的主数据源把 ACT_GE_、ACT_RU_、ACT_HI_、ACT_ID_ 这几大类几十张表全部建进去。如果你在项目初期就把流程表和业务表混在同一个库前期开发没感觉到了后面会非常难受备份恢复很被动。业务数据天天在变流程历史数据也在暴涨混在一起备份要么备份文件巨大要么想单独恢复某张业务表时被 ACT_HI_ACTINST 这种大表拖累。权限粒度没法控制。DBA 希望应用账号只能读写业务表流程引擎的账号单独管理混库以后很难实现。迁移和发布有风险。业务库做结构变更、分库分表的时候引擎表会跟着受影响一旦误操作整个流程引擎直接瘫掉。性能互相干扰。流程引擎大量写入 ACT_HI_ 历史表业务报表查询也在跑同一个数据库实例和连接池里互相争抢资源。所以把 Flowable 独立出来不只是“多配一个数据源”这么简单本质上是把工作流引擎当成一个独立的基础设施来对待和业务系统之间只通过 API 交互底层数据完全隔离。1.2 三种多数据源方案怎么选我整理了一下常见的方案其实有三种各有适用场景方案隔离程度配置复杂度适用场景独立数据库实例最高物理隔离高需单独维护实例大型系统、强隔离要求、跨团队运维同实例独立库/独立 Schema中高逻辑隔离中配置相对简单大多数中大型单体/微服务项目同库表前缀隔离低仅表名区分低小项目、快速原型、实在没有数据库权限方案三用的是spring.flowable.table-prefix这个配置让引擎表带上前缀比如FLW_ACT_GE_PROPERTY。它虽然省事但业务库里的表还是混在一起前面说的备份、权限、性能问题一个都没解决。方案一物理隔离最干净但一般公司没那么多数据库实例资源。折中下来绝大多数项目最合理的方案就是方案二同一个 MySQL 实例里建一个独立 database或者同一个 PostgreSQL 实例里建一个独立 schema然后给 Flowable 单独配一个数据源账号。这也正是我这次实战采用的方案。1.3 指定 Schema 到底在解决什么问题很多人第一次看到databaseSchema这个配置会懵其实“Schema”这个概念在不同的数据库里含义不太一样MySQLSchema 基本等同于 Database。你执行CREATE DATABASE flowable_db等于创建了一个 schema表名完整写法就是flowable_db.act_ge_property。PostgreSQLSchema 是数据库内部的一层命名空间一个数据库可以有好几个 schema默认情况下表会建到public这个 schema 里完整写法是flowable.act_ge_property。Oracle一个用户对应一个 Schema权限天然隔离这个其实是 Oracle 的设计好处。SQL ServerSchema 是数据库内的命名空间默认dbo。Flowable 里的databaseSchema配置就是告诉引擎“你建表和读写表的时候给我的表名加上哪个前缀”。比如设置成flowable生成的 SQL 就会变成select * from flowable.act_ru_execution。对于 MySQL由于 schema 就是数据库名直接在 JDBC URL 里带上库名就行databaseSchema填不填影响不大但对于 PostgreSQL如果不指定当前 schema 或者不设置databaseSchema引擎就会老老实实找默认的public然后你会在public里看到一堆 ACT_ 表这就是很多人踩的第一个坑。2. 前置准备与关键配置项2.1 版本搭配参考Flowable 的版本和 Spring Boot 的版本强相关配错版本很容易出现莫名其妙的兼容性问题。我这次用的是 Spring Boot 2.7 搭配 Flowable 6.7.2这是目前比较稳的组合Spring Boot 版本Flowable 版本JDK说明2.7.x6.7.2 或 6.8.x8/11/17经典组合资料最多最稳妥2.7.x6.6.08/11老项目常见升级需注意3.x7.0.017新版引擎包结构和配置有调整3.2.x7.1.017/21新特性多但踩坑资料相对少有个点必须注意Flowable 6 和 7 的某些 API 有变化而且数据库表结构也不同。如果你从 5.x 直接升 6.x不能指望database-schema-update: true帮你自动完成版本跨度太大时就得跑官方迁移脚本。所以生产环境里Flowable 引擎 JAR 版本和数据表里ACT_GE_PROPERTY记录的 schema.version 要保持一致这个后面避坑章节会展开讲。2.2 数据库实例与账号权限准备我这次是 PostgreSQL 环境需要单独建一个 schema 和一个专用账号-- 进入 flowable_db 数据库后执行 CREATE SCHEMA IF NOT EXISTS flowable AUTHORIZATION flow_user; -- 创建专用账号只管理 flowable 相关对象 CREATE USER flow_user WITH PASSWORD flow_pass; GRANT USAGE, CREATE ON SCHEMA flowable TO flow_user; GRANT ALL PRIVILEGES ON ALL TABLES IN SCHEMA flowable TO flow_user; GRANT ALL PRIVILEGES ON ALL SEQUENCES IN SCHEMA flowable TO flow_user; ALTER DEFAULT PRIVILEGES IN SCHEMA flowable GRANT ALL ON TABLES TO flow_user; ALTER DEFAULT PRIVILEGES IN SCHEMA flowable GRANT ALL ON SEQUENCES TO flow_user;如果是 MySQL就简单一些CREATE DATABASE flowable_db DEFAULT CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci; CREATE USER flow_user% IDENTIFIED BY flow_pass; GRANT ALL PRIVILEGES ON flowable_db.* TO flow_user%; FLUSH PRIVILEGES;权限这里有个容易忽略的地方如果你设置了database-schema-update: true引擎启动时会自己去建表、加索引那么数据库账号必须拥有 DDL 权限CREATE、ALTER、INDEX。如果公司安全规范不允许应用账号有 DDL 权限那就得先手动执行 Flowable 提供的建表脚本然后把database-schema-update设为false只保留 DML 权限。2.3 Flowable 核心配置项逐个说清配置 Flowable 时主要围绕这几个参数弄明白参数背后的逻辑比死记配置语句有用得多配置项可选值作用spring.flowable.database-schema-updatetrue/false/create-drop是否自动建表/升级表结构spring.flowable.database-schema字符串指定引擎表所在 SchemaPG 下尤其关键spring.flowable.table-prefix字符串表名前缀比如FLW_用于同库隔离方案spring.flowable.history-levelnone/activity/audit/full历史数据记录粒度直接影响 ACT_HI_ 表数据量spring.flowable.async-executor-activatetrue/false是否启动异步执行器处理定时任务、异步消息关于database-schema-update网上很多人直接写true图省事我建议生产环境谨慎。true的意思是“没有表就建字段缺了就补”听起来很智能但引擎升级时它不会帮你做破坏性变更遇到大版本切换该报错还是报错。而且一旦给了 DDL 权限万一代码里有人手滑把databaseSchemaUpdate改掉生产库结构会被自动改动风险很大。我的习惯是开发环境开true测试和生产环境用官方 SQL 脚本手动建表然后设false。3. 从零到一多数据源与指定 Schema 的完整落地3.1 用 ConfigurationProperties 装配两个 DataSource先看最终的application.yml多数据源的思路是给业务库和 Flowable 库各自定义一组spring.datasource.*配置用自定义前缀区分spring: datasource: business: driver-class-name: org.postgresql.Driver jdbc-url: jdbc:postgresql://192.168.1.10:5432/business_db?currentSchemabusinessstringtypeunspecified username: bus_app password: bus_pass hikari: pool-name: BusinessPool maximum-pool-size: 20 minimum-idle: 5 flowable: driver-class-name: org.postgresql.Driver jdbc-url: jdbc:postgresql://192.168.1.10:5432/business_db?currentSchemaflowablestringtypeunspecified username: flow_user password: flow_pass hikari: pool-name: FlowablePool maximum-pool-size: 10 minimum-idle: 2 flowable: database-schema-update: true database-schema: flowable history-level: audit async-executor-activate: true这里有一个很有迷惑性的细节业务库和 Flowable 库可以不在同一个数据库实例上我这个例子里 Flowable 的 URL 特意写的是business_db?currentSchemaflowable意思是“同一个 PostgreSQL 实例、同一个数据库内使用 flowable 这个 schema”。如果你更希望物理分开那 Flowable 的jdbc-url就指向另一个数据库实例原理完全一样。注意 PG 连接串里的currentSchemaflowable这个参数非常关键。PostgreSQL JDBC 驱动通过它来设置连接默认搜索路径连接建立之后不带 schema 前缀的表名就会先去flowable这个 schema 里找。配合stringtypeunspecified可以避免某些情况下字符串类型被错误推断的问题算是 PG 连接 Flowable 的老经验了。然后定义数据源 Bean两个数据源必须区分清楚谁是主import com.zaxxer.hikari.HikariDataSource; import org.springframework.boot.jdbc.DataSourceBuilder; import org.springframework.boot.context.properties.ConfigurationProperties; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Primary; import javax.sql.DataSource; Configuration public class MultiDataSourceConfig { Bean Primary ConfigurationProperties(prefix spring.datasource.business) public DataSource businessDataSource() { return DataSourceBuilder.create() .type(HikariDataSource.class) .build(); } Bean ConfigurationProperties(prefix spring.datasource.flowable) public DataSource flowableDataSource() { return DataSourceBuilder.create() .type(HikariDataSource.class) .build(); } }关键在于Primary注解必须放在业务数据源上。Spring Boot 里的自动配置、MyBatis、JPA 这些组件默认情况下拿到的是唯一的或带Primary的数据源。我们希望业务框架仍然使用业务库所以主数据源必须是业务库Flowable 这个特殊数据源则由后面专门的配置类去引用。有个小提示使用DataSourceBuilder时配置项要写jdbc-url而不是url因为 HikariCP 内部的真实属性名是jdbcUrlSpring Boot 的宽松绑定会把jdbc-url映射过去。如果写成url启动时大概率会报“DataSource 属性绑定失败”。3.2 通过 ProcessEngineConfigurationConfigurer 接管引擎数据源与事务有了两个数据源 Bean 之后重点来了怎么让 Flowable 引擎不要用主数据源而是用flowableDataSource网上很多教程会让你排除FlowableAutoConfiguration然后手动创建ProcessEngine、各个 Service Bean这个方案能行但代码量很大而且容易漏。其实官方早就提供了更优雅的口子ProcessEngineConfigurationConfigurer。这个接口的作用是在引擎配置对象构建完成、但 ProcessEngine 还没创建之前给你一个修改配置的机会。我们可以在这个回调里把数据源和事务管理器换成 Flowable 专用的import org.flowable.spring.ProcessEngineConfigurationConfigurer; import org.flowable.spring.SpringProcessEngineConfiguration; import org.springframework.beans.factory.annotation.Qualifier; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.transaction.PlatformTransactionManager; import javax.sql.DataSource; Configuration public class FlowableEngineConfig { Bean public ProcessEngineConfigurationConfigurer flowableEngineConfigurer( Qualifier(flowableDataSource) DataSource flowableDataSource, Qualifier(flowableTxManager) PlatformTransactionManager flowableTxManager) { return new ProcessEngineConfigurationConfigurer() { Override public void configure(SpringProcessEngineConfiguration config) { config.setDataSource(flowableDataSource); config.setTransactionManager(flowableTxManager); config.setDatabaseSchema(flowable); config.setDatabaseSchemaUpdate(true); config.setHistoryLevel(HistoryLevel.AUDIT); config.setAsyncExecutorActivate(true); } }; } }setDataSource不用多解释关键是setTransactionManager。Flowable 与 Spring 整合后Service 层操作的事务边界是由PlatformTransactionManager控制的如果你不指定引擎会去 Spring 容器里找但此时容器里有业务库和 Flowable 库两个事务管理器很容易选错。所以必须在配置里明确告诉引擎你的事务管理器是绑定 Flowable 数据源的那个。setDatabaseSchema(flowable)的作用是和currentSchemaflowable双保险。引擎建表和读写 SQL 时会尝试给表名加上 schema 前缀。对于 PostgreSQL 来说如果没有这个配置即使 JDBC URL 里带了currentSchema某些版本的 Flowable 在 DDL 阶段仍可能把表建到public这个后面避坑章节再展开。3.3 指定 Schema 的几种实操姿势与底层原理关于“指定 Schema”我实际用下来有三种姿势分别适用不同场景姿势一JDBC URL 参数指定推荐。PostgreSQL 用currentSchema这个参数由驱动层设置连接默认搜索路径MySQL 则直接把库名写在 URL 里。这种方式在连接层面就锁定了 schema 范围最可靠。比如jdbc:postgresql://host:5432/business_db?currentSchemaflowable连接建立后未加前缀的ACT_RU_EXECUTION会优先在flowableschema 里解析。姿势二Flowable 配置属性指定。spring.flowable.database-schemaflowable或者代码里config.setDatabaseSchema(flowable)。这个属性会被引擎用来在 DML/DDL 语句中拼接 schema 前缀例如生成的 SQL 会变成insert into flowable.act_ru_execution(...)。注意 MySQL 下如果填了 schema 名务必和 URL 里的库名保持一致否则可能出现flowable_db.act_ge_property这种双重前缀的 SQL。姿势三SQL 里显式 set search_path。这个往往被忽略但在排查问题时很好用。数据库侧执行ALTER ROLE flow_user IN DATABASE business_db SET search_path TO flowable, public;这属于数据库层面的默认设置相当于给这个角色在连接时自动执行SET search_path。如果应用配置没法轻易改用这个方式也能解决 PG 下 schema 匹配问题。三种姿势的背后原理是同一个Flowable 在生成 SQL 时表名最终要能在数据库里唯一解析。要么驱动层帮你想好默认 schema要么引擎层主动拼前缀两者至少有一个生效否则必然落到public。3.4 事务边界要分清业务管理器与流程管理器的分工多数据源的难点不只是数据源本身事务管理器是另一个很容易炸的地方。我们最终在容器里要有两个PlatformTransactionManagerBean Primary public PlatformTransactionManager businessTxManager( Qualifier(businessDataSource) DataSource businessDataSource) { return new DataSourceTransactionManager(businessDataSource); } Bean public PlatformTransactionManager flowableTxManager( Qualifier(flowableDataSource) DataSource flowableDataSource) { return new DataSourceTransactionManager(flowableDataSource); }业务代码里凡是用Transactional的地方默认会走businessTxManager因为它有Primary。而引擎内部的 Service 调用走的是flowableTxManager因为我们在ProcessEngineConfigurationConfigurer里显式指定了。实际开发中容易犯的错误是在一个业务事务里同时操作业务表和 Flowable 服务比如Transactional public void createOrderAndStartProcess() { orderMapper.insert(order); runtimeService.startProcessInstanceByKey(orderProcess); }这段代码乍一看没问题但它隐含了一个大坑业务事务和流程引擎事务是两个独立事务orderMapper.insert提交失败时流程实例可能已经启动了反之亦然。多数据源本身不具备分布式事务能力不要把跨库操作硬塞进一个Transactional里。真需要原子性要么引入 Atomikos 这类 XA 事务方案要么用本地消息表加补偿任务从架构层面规避。4. 实战避坑最常见的五个翻车现场4.1 建表失败先分清“数据库 Schema”还是“API Schema”搜索 Flowable schema 相关报错时你可能会搜到形如api error: 400 invalid schema for function artifact: ^(?!.*$)[^\p{cc}\p{cf}\p{zl}\p{zp}\\./[\]]{1,200}$ is not a regex这样的错误。我一开始也以为是 Flowable 的表结构校验报错后来仔细一看完全不是一回事。这种报错的典型特征很明显带api error、400、function并跟着一串正则表达式。它通常来自 API 网关或者 AI 代理工具是“函数参数校验 schema”一般是指 JSON Schema定义不合法和数据库 schema 没有半毛钱关系。Flowable 里的 schema 永远是指数据库里的命名空间报错形式一般是 SQLState、JDBC 异常或者org.flowable.common.engine.api.FlowableException开头的引擎异常。所以排查第一步先看错误类型。数据库 schema 跑偏的报错核心信息里会有表名和 schema 名比如ERROR: schema flowable does not exist或者Unknown database flowable_db这类才是 Flowable 数据源配置的问题。看到一个 400 加一堆正则的报错先去检查你的 HTTP 接口定义和工具参数格式不要在 Flowable 配置里浪费时间。4.2 表建到了默认库/默认 Schema这是多数据源配置里出现频率最高的问题表现是业务系统正常启动ACT_ 表也建出来了但出现在publicPG或者业务库MySQL里而不是预期的 schema。常见原因有三个原因一JDBC URL 没带 schema 参数。PostgreSQL 下如果 URL 没写currentSchema配置里又没设置databaseSchema引擎会用数据库默认的public。解决方式就是前面说的URL 加currentSchema配置里再补setDatabaseSchema。原因二Primary放错了位置。如果flowableDataSource不小心被加了Primary其他框架会优先用它业务 SQL 全部跑到了流程库更隐蔽的是某些自动配置判断主数据源时也会取到 Flowable 数据源导致引擎加载的构造配置混乱。原因三多个ProcessEngineConfigurationConfigurer互相覆盖。如果项目里之前有人写过一个 configurer 把dataSource设成了主数据源而你又新增了一个 configurer 设置流程数据源Bean 的执行顺序不确定后执行的那个会覆盖前一个。这种问题特别隐蔽建议先全局搜一下有没有其他ProcessEngineConfigurationConfigurer实现。排查时用一条 SQL 就能确认表到底建到了哪-- MySQL SELECT table_schema, table_name FROM information_schema.tables WHERE table_name LIKE ACT\_%; -- PostgreSQL SELECT table_schema, table_name FROM information_schema.tables WHERE table_name LIKE ACT\_%;如果结果里 schema 不是预期值先把两处配置URL databaseSchema都改对再删掉建错的表重新启动。4.3 schema.version 不匹配另一个高频报错是启动时抛类似这样的异常org.flowable.common.engine.api.FlowableException: Could not find a valid Flowable database version或者Flowable database schema version mismatch这个错误的根源是ACT_GE_PROPERTY表里记录了schema.version引擎启动时会拿这个值和当前 JAR 包里的版本做比对。常见场景是老项目升级 Flowable JAR 版本但数据库表没有跟着升级或者 pom 里同时引入了多个 Flowable 模块版本号不一致。处理方式很直接先检查 pom 里所有org.flowable相关依赖版本是否一致统一用flowable.version属性管理。小版本升级比如 6.7.1 到 6.7.2设database-schema-update: true让它自动升级。跨大版本6.x 到 7.x不要指望自动升级先用官方升级脚本或者对比ACT_GE_PROPERTY中的 schema.version 与目标版本按官方文档执行迁移。这里还要提醒一句别为了绕过版本检查把ACT_GE_PROPERTY里的版本号手工改掉数据库结构和引擎代码不匹配后面会冒出一堆字段不存在、存储过程调用失败的问题远比版本检查报错难查。4.4 多数据源事务串了导致写错库这类问题表现特别诡异业务代码里用Transactional调用流程引擎服务结果流程数据写到了业务库或者反过来流程执行过程中把业务表数据搞进去了。从原理上讲这通常是事务管理器选错了。DataSourceTransactionManager绑定的是具体哪个DataSource它负责的 Connection 就是从那个数据源拿的。如果引擎的 transactionManager 没显式设置Flowable 的 Spring 整合代码会尝试从容器中找一个事务管理器而容器里有多个时很可能拿到带Primary的业务事务管理器。引擎拿着业务事务管理器事务同步时绑定的资源是业务数据源的但引擎 Service 内部拿连接时又去 flowableDataSource 获取两边对不上写库就乱了。解决办法就是 3.2 节的做法在ProcessEngineConfigurationConfigurer里显式setTransactionManager(flowableTxManager)。配置完之后可以通过一个简单的自检接口确认Autowired Qualifier(flowableTxManager) private PlatformTransactionManager flowableTxManager; Autowired private ProcessEngine processEngine; public void check() { SpringProcessEngineConfiguration config (SpringProcessEngineConfiguration) processEngine.getProcessEngineConfiguration(); System.out.println(Engine DataSource config.getDataSource()); System.out.println(Engine TxManager config.getTransactionManager()); System.out.println(Engine schema config.getDatabaseSchema()); }把这三样打出来数据源和事务管理器是不是 Flowable 专用的一眼就能看出来。4.5 连接池配置不当导致引擎启动假死最后一个坑比较隐蔽表现是应用启动日志停在“Initializing process engine...”很久然后超时失败或者偶尔启动成功但异步任务一多就大量报错。常见原因是 Flowable 数据源的连接池maximum-pool-size设置得太小。Flowable 的异步执行器会在线程池里跑定时任务、消息任务一个事务就要占用一个连接。如果连接池上限是 1引擎初始化时建表事务和异步任务初始化并发抢连接就会出现死等。另外PostgreSQL 下如果 schema 权限不对引擎创建表时可能反复重试也会表现为启动假死。我见过一个案例GRANT USAGE忘了给启动日志只留下一句“Unable to obtain connection from database”排查半天才发现是权限问题。建议 Flowable 独立连接池至少 10 起步异步任务多的项目给到 20 也不过分。同时把 HikariCP 的pool-name分别命名启动时看到BusinessPool和FlowablePool各自 Start completed就能确认两个连接池都起来了。5. 日常维护与性能优化建议5.1 独立连接池参数怎么给多数据源配置完成只是开始连接池参数直接影响引擎稳定性。我的经验是 Flowable 连接池不能照抄业务连接池因为它有异步执行器工作线程数量和数据库连接数强相关。参数建议值说明maximum-pool-size10 ~ 20异步执行器线程数 预留余量minimum-idle2 ~ 5连接数超过活跃数较多时可以设小减少空闲占用connection-timeout3000 ~ 5000取连接等待上限任务量大时避免线程无限等待validation-timeout1000 ~ 3000连接校验超时PG 下建议配合connection-test-querypool-name自定义区分日志方便观察哪个连接池出问题Flowable 异步执行器的线程配置一般不用动但如果项目里定时流程任务特别多可以调整spring: flowable: async-executor-core-pool-size: 8 async-executor-max-pool-size: 16 async-executor-keep-alive-time: 30注意async-executor-core-pool-size和连接池maximum-pool-size之间要有合理的比例关系线程数多于连接数时多出来的线程都在等待拿连接。5.2 历史数据增长与清理流程引擎跑久了ACT_HI_ACTINST、ACT_HI_TASKINST、ACT_HI_PROCINST这几张历史表的增长速度会超出预期。如果你的业务并不需要完整的过程审计history-level没必要设成fullaudit一般就够用了。如果历史数据已经很大可以用定时任务按条件清理但要注意删除顺序先删子表再删主表。示例 SQLDELETE FROM act_hi_actinst WHERE proc_inst_id_ IN ( SELECT id_ FROM act_hi_procinst WHERE start_time_ now() - interval 180 days ); DELETE FROM act_hi_taskinst WHERE proc_inst_id_ IN ( SELECT id_ FROM act_hi_procinst WHERE start_time_ now() - interval 180 days ); DELETE FROM act_hi_procinst WHERE start_time_ now() - interval 180 days;这类清理建议在业务低峰期执行删除大量记录时注意控制批次避免把流程库的 WAL 撑爆。5.3 备份、监控和发布注意事项多数据源隔离的好处在做备份和监控时体现得最明显。PostgreSQL 下只备份流程 schemapg_dump -h host -p 5432 -U flow_user -d business_db -n flowable -F c -f flowable_backup.dumpMySQL 下直接指定库名mysqldump -h host -u flow_user -p flowable_db flowable_backup.sql监控方面重点关注三件事ACT_RU_EXECUTION有没有异常积压的未完成流程、ACT_RU_JOB里错误重试的任务数量、以及连接池活跃连接数曲线。这几个指标能提前暴露流程引擎的大多数问题。发布的时候还有个细节业务系统发版时尽量让 Flowable 引擎的database-schema-update保持稳定不要在测试环境开true、生产环境设false两套配置不一致很容易造成“测试好好的生产缺字段”的尴尬。引擎版本升级要单独排期先备份再执行升级脚本最后替换依赖发版。回到开头说的那个项目折腾完这轮多数据源配置我最大的体会是Flowable 多数据源本身不难难的是把“数据源”、“事务管理器”、“Schema”这三件事绑定在一起。大部分报错看起来像玄学其实是配置对象之间没有对上号。如果你正卡在类似问题上优先检查三件事引擎到底用了哪个 DataSource、哪个 TransactionManager、databaseSchema是不是为空。把这三个值打印出来问题基本就摊在桌面上了。项目里如果还有第二套 Flowable 环境或者流程引擎将来要拆分出去这套配置思路也能直接复用无非是多加一组数据源配置把 schema 再拆一个出来而已。
返回列表