# jlflow
**Repository Path**: carro/jlflow
## Basic Information
- **Project Name**: jlflow
- **Description**: No description available
- **Primary Language**: Unknown
- **License**: Not specified
- **Default Branch**: master
- **Homepage**: None
- **GVP Project**: No
## Statistics
- **Stars**: 0
- **Forks**: 0
- **Created**: 2026-07-19
- **Last Updated**: 2026-07-20
## Categories & Tags
**Categories**: Uncategorized
**Tags**: None
## README
# JLFlow 微流程引擎
> 轻量级、零 Spring 依赖的微流程引擎:纯 Java + JDBC + 内置 UI(HTML + Vue3 + LogicFlow),开箱即用。
JLFlow 是一个面向中小型业务的轻量微流程引擎。它不绑定 Spring、不依赖 MyBatis、不引入 JPA,仅通过原生 JDBC + Servlet API 提供完整流程能力:部署、版本快照、实例运行、任务办理、撤回、驳回、委托、加签减签、超时自动审批、流程图可视化编辑与监控。引擎通过 SPI 与 Listener 钩子与宿主解耦,可无缝接入 SpringBoot / SpringMVC / 普通 Java 三类工程。
- 仓库地址:https://gitee.com/carro/jlflow
- 引擎版本:1.0.0
- groupId:`site.jlopen.jlflow`
---
## 特性
- **零 Spring 依赖**:核心包 `jlflow-engine-core` 仅依赖 `slf4j-api`,不引入 Spring / MyBatis / JPA,可在任意 Java 工程使用。
- **内置可视化 UI**:`jlflow-engine-ui` 提供 LogicFlow 流程图设计器 + 管理后台(部署 / 实例 / 任务 / 日志 / 委托 / 超时规则),开箱即用。
- **雪花 ID(BIGINT)**:所有主键统一使用 `BIGINT` 雪花 ID(Java 中为 `Long`),便于跨服务传递与排序。
- **多租户**:通过 `tenant_id` 字段 + `AuthContext` 线程上下文实现逻辑隔离,可按需开关。
- **SPI 扩展点**:`IdentityProvider` / `ExpressionEvaluator` / `JsonSerializer` 三个 SPI,宿主可替换默认实现。
- **Listener 钩子**:`InstanceListener` / `TaskListener` / `RouteListener` / `ErrorListener`,覆盖实例生命周期、任务办理、路由计算、异常告警等关键节点。
- **版本快照机制**:发布即生成不可变版本(`jl_flow_deploy_version`),实例运行时再生成运行时快照(`jl_flow_instance_version`),支持已发布流程热升级不影响存量实例。
- **高级场景**:撤回(withdraw)、委托(delegate)、加签减签(counter sign / reduce sign)、超时自动审批(auto approve / reject / remind)、驳回回退(reject to node)等开箱即用。
- **REST API + 内置 UI**:基于 Servlet 实现,宿主只需声明依赖即可在 Web 容器中自动挂载到 `/jlflow` 路径。
---
## 工程模块
JLFlow 采用 Maven 多模块组织,共 4 个子模块:
| 模块 | artifactId | 说明 |
| --- | --- | --- |
| 核心引擎 | `jlflow-engine-core` | 引擎核心:API、Engine、Repository、JDBC、SPI、Listener,零 Spring 依赖 |
| Spring 适配 | `jlflow-engine-spring` | SpringBoot/SpringMVC 适配包:读 `application.yml` + 自动注入 + DataSource 自动检测 |
| 内置 UI | `jlflow-engine-ui` | 静态资源包:HTML + Vue3 + LogicFlow 流程图设计器与管理后台 |
| 示例工程 | `jlflow-engine-samples` | 示例聚合模块(含 `jlflow-sample-springboot`) |
依赖关系:
```
jlflow-engine-core ← jlflow-engine-spring ← jlflow-engine-samples
← jlflow-engine-ui ←
```
---
## 快速开始
只需 3 步即可在 SpringBoot 工程中接入 JLFlow:
### 第 1 步:引入依赖
```xml
site.jlopen.jlflow
jlflow-engine-spring
1.0.0
site.jlopen.jlflow
jlflow-engine-ui
1.0.0
com.mysql
mysql-connector-j
com.zaxxer
HikariCP
com.google.code.gson
gson
```
### 第 2 步:配置数据源与引擎
在 `application.yml` 中:
```yaml
jlflow:
enabled: true
datasource:
mode: self # self / auto / external
url: jdbc:mysql://127.0.0.1:3306/jlflow?useUnicode=true&characterEncoding=utf8&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
username: root
password: 123456
max-pool-size: 10
min-idle: 2
connection-timeout: 30000
ui:
enabled: true
context-path: /jlflow
api:
enabled: true
context-path: /jlflow/api
schedule:
enabled: true
timeout-scan-interval: 60 # 超时扫描间隔(秒)
```
并执行建表脚本:`jlflow-engine-core/src/main/resources/sql/jlflow-mysql.sql`
### 第 3 步:启动应用
启动 SpringBoot 应用后:
- 内置 UI 入口:`http://localhost:8080/jlflow`
- REST API 根路径:`http://localhost:8080/jlflow/api`
在 UI 中点击「部署管理」→「新建部署」→ 进入流程图编辑器设计并发布,再发起实例即可。
---
## 接入方式
### 方式一:SpringBoot
引入 `jlflow-engine-spring`,自动配置 `JLFlowAutoConfiguration` 会扫描 `jlflow.*` 配置并自动启动引擎与 UI。无需任何 Java 代码。
### 方式二:SpringMVC(传统 Spring)
引入 `jlflow-engine-core` + `jlflow-engine-ui`,在 Spring 配置类中手动构造:
```java
@Configuration
public class JlflowConfig {
@Bean(destroyMethod = "shutdown")
public JLFlowEngine jlFlowEngine(DataSource dataSource) {
JLFlowConfig config = ConfigLoader.load(); // 读 classpath:jlflow.properties
JLFlowEngine engine = JLFlowEngine.create(dataSource, config);
engine.start();
return engine;
}
}
```
### 方式三:常规 Java(非 Spring)
```java
// 1. 加载配置
JLFlowConfig config = ConfigLoader.load();
// 2. 创建并启动引擎
JLFlowEngine engine = JLFlowEngine.create(config);
engine.start();
// 3. 使用 API
JLFlowApis apis = engine.apis();
apis.deploy().create(deployDto);
apis.instance().start(startDto);
apis.task().complete(completeDto);
// 4. 应用关闭时
engine.shutdown();
```
非 Web 环境不加载内置 UI,仅使用核心 API。
---
## 配置项说明
所有配置以 `jlflow.*` 为前缀,支持 `application.yml` / `application.properties` / `jlflow.properties` / JVM 参数 `-Djlflow.xxx` / 环境变量 `JLFLOW_XXX` 五种来源。
| 配置项 | 默认值 | 说明 |
| --- | --- | --- |
| `jlflow.enabled` | `true` | 引擎总开关 |
| `jlflow.id-generator` | `snowflake` | ID 生成器(仅 snowflake) |
| `jlflow.auto-create-table` | `false` | 是否自动建表(建议生产环境手动执行 SQL) |
| `jlflow.table.prefix` | `jl_flow_` | 表前缀 |
| `jlflow.tenant.enabled` | `false` | 是否启用多租户 |
| `jlflow.tenant.default` | `_DEFAULT_` | 默认租户 ID |
| `jlflow.tenant.resolver` | `threadlocal` | 租户解析器(threadlocal / header) |
| `jlflow.datasource.mode` | `self` | 数据源模式:`self` 自建 / `auto` 自动检测 / `external` 外部注入 |
| `jlflow.datasource.url` | - | JDBC URL(self 模式必填) |
| `jlflow.datasource.driver-class-name` | - | JDBC Driver 类名 |
| `jlflow.datasource.username` | - | 数据库用户名 |
| `jlflow.datasource.password` | - | 数据库密码 |
| `jlflow.datasource.max-pool-size` | `10` | 最大连接数 |
| `jlflow.datasource.min-idle` | `2` | 最小空闲连接 |
| `jlflow.datasource.connection-timeout` | `30000` | 连接超时(毫秒) |
| `jlflow.ui.enabled` | `true` | 是否启用内置 UI |
| `jlflow.ui.context-path` | `/jlflow` | UI 上下文路径 |
| `jlflow.ui.auth.enabled` | `false` | 是否启用 UI Basic 认证 |
| `jlflow.ui.auth.username` | `admin` | UI 认证用户名 |
| `jlflow.ui.auth.password` | `jlflow123` | UI 认证密码 |
| `jlflow.api.enabled` | `true` | 是否启用 REST API |
| `jlflow.api.context-path` | `/jlflow/api` | API 上下文路径 |
| `jlflow.schedule.enabled` | `true` | 是否启用超时扫描调度 |
| `jlflow.schedule.timeout-scan-interval` | `60` | 超时扫描间隔(秒) |
| `jlflow.router.strict-mode` | `false` | 路由严格模式:true 时未命中任何出边将抛异常 |
---
## 数据库表结构
JLFlow 共 14 张表,全部使用 `BIGINT` 雪花 ID 主键,引擎 `InnoDB`,字符集 `utf8mb4`。
| 序号 | 表名 | 说明 | 主键 | 含租户 |
| --- | --- | --- | --- | --- |
| 1 | `jl_flow_deploy` | 流程部署主表 | `deploy_id` | ✅ |
| 2 | `jl_flow_deploy_version` | 部署版本快照(含 graph_json LONGTEXT) | `version_id` | ❌ |
| 3 | `jl_flow_node` | 节点定义 | `node_id` | ❌ |
| 4 | `jl_flow_edge` | 连线定义 | `edge_id` | ❌ |
| 5 | `jl_flow_agent` | 节点经办规则 | `agent_id` | ❌ |
| 6 | `jl_flow_agent_link` | 经办绑定(候选人/黑名单) | `link_id` | ❌ |
| 7 | `jl_flow_instance` | 流程实例 | `instance_id` | ✅ |
| 8 | `jl_flow_instance_version` | 实例运行时版本快照(含 graph_snapshot LONGTEXT) | `version_id` | ❌ |
| 9 | `jl_flow_task` | 任务 | `task_id` | ✅ |
| 10 | `jl_flow_task_assign` | 任务经办人 | `assign_id` | ❌ |
| 11 | `jl_flow_log` | 运行日志 | `log_id` | ✅ |
| 12 | `jl_flow_delegate` | 委托关系 | `delegate_id` | ✅ |
| 13 | `jl_flow_counter_sign` | 加签记录 | `counter_sign_id` | ✅ |
| 14 | `jl_flow_timeout_rule` | 超时规则 | `rule_id` | ✅ |
DDL 脚本:[jlflow-engine-core/src/main/resources/sql/jlflow-mysql.sql](./jlflow-engine-core/src/main/resources/sql/jlflow-mysql.sql)
---
## SPI 扩展点
引擎通过 `site.jlopen.jlflow.spi.SpiRegistry` 管理三类 SPI,宿主可在启动前注入自定义实现。
### 1. IdentityProvider(身份/组织)
```java
public interface IdentityProvider {
List userList();
List sectorsList();
List userInSectors(String deployCode, String instanceKey, String taskCode, String sectorId);
JLFlowUser sectorLeader(String sectorId, String leaderType);
List blackList();
JLFlowUser directLeader(String userId);
}
```
用于办理人解析、加签选人、委托代理、回退目标选择等场景。宿主需实现该接口以接入本地用户/组织数据。
### 2. ExpressionEvaluator(表达式求值)
```java
public interface ExpressionEvaluator {
Object evaluate(String expression, Map params);
boolean validate(String expression);
}
```
用于连线条件、跳转策略、办理人脚本等场景。默认实现 `DefaultExpressionEvaluator` 支持简单 `${var}` 占位与等值/比较运算,可替换为 SpEL / Aviator / QLExpress 等。
### 3. JsonSerializer(JSON 序列化)
```java
public interface JsonSerializer {
String toJson(Object obj);
T fromJson(String json, Class type);
T fromJson(String json, Type type);
}
```
用于持久化流程变量、任务参数、流程图快照等。默认实现基于 Gson,可替换为 Jackson / Fastjson 等。
---
## Listener 钩子
引擎在关键节点提供 4 类监听器,所有方法均默认空实现,宿主按需覆写。
### 1. InstanceListener(实例生命周期)
`beforeStart` → `afterStart` → `afterFinish` / `afterStop` / `afterSuspend` / `afterWithdraw`
### 2. TaskListener(任务生命周期)
`afterCreate` → `injectVariables` → `beforeComplete` → `afterComplete` / `beforeReject` → `afterReject` / `onError` / `afterWithdraw` / `afterCounterSign` / `afterDelegate`
### 3. RouteListener(路由计算)
`beforeRoute` → `afterRoute(nextNodeIds)` / `onNoMatch(ctx)` 兜底
### 4. ErrorListener(异常告警)
`onError(ctx)`:引擎运行过程中产生未捕获异常时触发,可在此实现告警、日志、补偿等逻辑。
注册方式:
```java
SpiRegistry spi = new SpiRegistry();
spi.addListener(myInstanceListener, "leave_process"); // 仅对 leave_process 部署生效
spi.addListener(myTaskListener); // 全局生效
Engine engine = Engine.build(dataSource, spi, config);
```
---
## 高级场景
### 撤回(Withdraw)
发起人或上一步办理人可在后续任务未办理前撤回,引擎自动回退到撤回发起节点。
```java
apis.withdraw().withdraw(new WithdrawDTO(instanceId, taskId, userId, "撤回原因"));
```
### 委托(Delegate)
A 长期委托 B 代办某流程或全部流程的任务,引擎在分配任务时自动转给 B,并标记 `assign_type=1`。
```java
apis.delegate().create(new DelegateDTO("userA", "userB", "leave_process", startTime, endTime));
```
### 加签 / 减签(Counter Sign)
支持 4 种加签类型:前加签、后加签、并加签、减签。
```java
apis.counterSign().add(new CounterSignDTO(taskId, signType, signUserIds, operatorUserId));
```
### 超时自动审批
为节点配置超时规则,到期后引擎自动执行「自动通过 / 自动驳回 / 催办提醒」。
```java
apis.timeoutRule().create(new TimeoutRuleDTO(deployId, nodeId, 60, 1, 5, true));
// 含义:60 分钟超时,动作=自动通过,提前 5 分钟催办
```
---
## 内置 UI
`jlflow-engine-ui` 提供基于 HTML + Vue3 + LogicFlow 的可视化界面,启动后访问 `http://host:port/jlflow` 即可使用,包含以下页面:
| 页面 | 路径 | 说明 |
| --- | --- | --- |
| 首页 | `/jlflow/index.html` | 控制台入口 |
| 部署管理 | `/jlflow/pages/deploy.html` | 创建/发布/停用流程部署 |
| 流程图编辑器 | `/jlflow/pages/graph-editor.html` | 基于 LogicFlow 的可视化设计器 |
| 实例管理 | `/jlflow/pages/instance.html` | 查看/挂起/终止实例 |
| 任务管理 | `/jlflow/pages/task.html` | 待办/已办/办理/驳回 |
| 运行日志 | `/jlflow/pages/log.html` | 实例/任务日志查询 |
| 委托管理 | `/jlflow/pages/delegate.html` | 委托关系配置 |
| 超时规则 | `/jlflow/pages/timeout-rule.html` | 节点超时规则配置 |
UI 默认无需认证,生产环境建议开启 Basic 认证或前置网关鉴权。
---
## 版本与路线图
| 版本 | 状态 | 关键特性 |
| --- | --- | --- |
| 1.0.0 | ✅ 已发布 | 部署/实例/任务/撤回/驳回/委托/加签/超时/UI/SPI |
| 1.1.0 | 🚧 规划中 | 子流程、并行网关、条件分支增强 |
| 1.2.0 | 📋 规划中 | PostgreSQL 支持、分布式调度、流程实例归档 |
---
## 开源协议
[Apache License, Version 2.0](https://www.apache.org/licenses/LICENSE-2.0.txt)
---
## 仓库地址
- Gitee:https://gitee.com/carro/jlflow