引擎三分钟入门
一个 Go 库加 6 张表。建库、连库、发实例——你写的是业务代码,不是流程代码。
1. 初始化数据库
引擎只维护自己的 6 张工作流表,用户/角色/部门等系统表由宿主应用负责。
PostgreSQL:
bash
psql -d rulego_bpm -f scripts/00.init_bpm_pg.sqlMySQL:
bash
mysql -u root -p rulego_bpm < scripts/00.init_bpm_mysql.sql初始化脚本会先删除同名表,只能用于全新数据库。
建表清单:wf_process(流程定义)、wf_instance / wf_hi_instance(实例运行时/历史)、wf_task / wf_hi_task(任务运行时/历史)、wf_task_assignee(候选人池)。每张表的作用见数据模型。
2. 启动引擎并部署流程
go
package main
import (
"context"
"log"
"github.com/rulego/rulego-bpm/components"
"github.com/rulego/rulego-bpm/config"
"github.com/rulego/rulego-bpm/model"
"github.com/rulego/rulego-bpm/service"
"github.com/rulego/rulego-bpm/types/dto"
"github.com/rulego/rulego-bpm/types/enums"
)
func main() {
ctx := context.Background()
// 1. 数据库配置并启动引擎
cfg := &config.Config{
Database: &config.DatabaseConfig{
Driver: "postgres",
Dsn: "host=127.0.0.1 user=postgres password=postgres dbname=rulego_bpm port=5432 sslmode=disable",
},
}
engine := service.NewWorkflowEngine("demo", cfg)
if err := engine.Start(ctx); err != nil {
log.Fatalf("启动引擎失败: %v", err)
}
defer engine.Stop(ctx)
// 2. 注册工作流节点组件(userTask/serviceTask/automation/...)
// identityService 生产环境必须换成对接真实组织架构的实现
if err := components.RegisterWorkflowComponents(
engine.GetTaskService(),
engine.GetIdentityService(),
engine.GetRuntimeService(),
nil, // CCTaskCreatedListener,可选
nil, // TaskEventListener,可选
nil, // RuleChainExecutor,automation 跨池调用时传入
); err != nil {
log.Fatalf("注册组件失败: %v", err)
}
// 3. 部署流程定义(DSL 为 rulego 规则链 JSON)
_, err := engine.GetProcessService().Deploy(ctx, &model.WfProcess{
ProcessKey: "leave_approval",
Name: "请假审批",
DefinitionJSON: leaveApprovalDSL, // 见 examples/leave_approval
TenantID: "default",
CreatedBy: "admin",
}, true)
if err != nil {
log.Fatalf("部署流程失败: %v", err)
}
// 4. 发起流程实例
instanceID, err := engine.GetRuntimeService().StartProcessInstanceByKey(
ctx,
service.Identity{UserId: "emp001", TenantId: "default"},
"leave_approval",
"leave_emp001_1", // 业务键
map[string]interface{}{"days": 5, "managerId": "mgr001", "reason": "家中事务"},
false,
)
if err != nil {
log.Fatalf("发起流程失败: %v", err)
}
_ = instanceID
}3. 审批人处理待办
go
tasks, _, err := engine.GetTaskService().GetTaskList(ctx, &dto.TaskQuery{
Assignee: "mgr001",
PageRequest: dto.PageRequest{
Status: []string{string(enums.TaskStatusPending), string(enums.TaskStatusActive)},
PageSize: 10,
},
})
if err != nil || len(tasks) == 0 {
return
}
err = engine.GetTaskService().CompleteWithApproval(ctx, &service.ApprovalRequest{
TaskID: tasks[0].ID,
UserID: "mgr001",
ApprovalResult: enums.ApprovalResultApproved,
Comment: "同意",
})完整可运行示例(或签、并行会签、顺序会签)见仓库 examples/leave_approval 目录(Gitee / GitHub)。
4. 接入组织架构(IdentityService)
引擎不绑定任何用户体系。按角色/部门/主管发起的审批任务,办理人统一通过 service.IdentityService 接口解析:
go
// 实现 8 个方法,对接你自己的组织架构表
type OrgIdentityService struct {
db *gorm.DB
}
func (s *OrgIdentityService) GetUserIDsByRoleID(ctx context.Context, tenantID, roleID string) ([]string, error) {
var userIDs []string
err := s.db.WithContext(ctx).
Table("user_roles").
Where("tenant_id = ? AND role_id = ?", tenantID, roleID).
Pluck("user_id", &userIDs).Error
return userIDs, err
}
// 其余方法:GetUserIDsByDepartmentID / GetDepartmentManagerUserID /
// GetUserManagerID / GetUserManagerHierarchy /
// GetUserDepartmentID / GetRoleIDsByUserID / GetUserIDsByGroupID通过 Builder 注入:
go
engine, err := service.NewWorkflowEngineBuilder().
SetName("demo").
SetConfig(cfg).
SetIdentityService(&OrgIdentityService{db: gormDB}).
Build()TIP
不想写组织架构对接?直接用 gflow——它内置了用户/角色/部门/岗位/多租户的完整实现和全部界面,见 gflow 平台体验。