# 流程中心表单数据存储场景说明。

流程中心表单数据存储功能是为了兼容表单外部url相关数据存储在第三方服务中,数据和表单页面由三方服务提供的场景。

流程中心表单数据存储场景分为前端调用三方保存接口、后端rest调用三方保存接口两种方式。(查询表单数据接口两种场景均统一由前端触发调用)

区别:1、事务数据一致性: 前端调用方式不能保证流程引擎和表单数据保存在同一事务下进行,无法通过事务层面保证数据一致性。需要自行对数据进行回滚操作,具体方式在前端调用三方保存接口中有说明。

​ 后端调用方式可保证流程引擎和表单数据在同一事务下进行。

​ 2、调用方式: 前端调用体现在由前端触发三方保存接口数据,成功后再进行submit提交流程接口调用。

​ 后端调用由前端直接触发submit提交流程接口调用,三方数据保存接口在后端submit接口逻辑中进行rest远程调用。

# 前端调用三方保存接口

前端调用方式不能保证流程引擎和表单数据保存在同一事务下,如需事务一致则通过监听message事件来回滚事务,如下

  • 三方应用提交接口失败时需要做回滚处理

    • rollbackFormDataHandle(bfpContext, processContext)
  • afc的提交接口失败时,监听message消息

    • 当msg为afterSaveFormDataStart时,根据 isFailed 字段判断做表单回滚保存后处理

# 后端rest调用三方保存接口

​ 前端调用submit提交流程接口时,由后端rest远程调用三方保存接口。三方服务应用地址以AFC应用管理中三方地址为主,没有配置时则获取前端调用submit接口时BfpContext对象中传入三方保存接口相关信息参数,该参数值由demo-ui中配置文件中获取,具体在开发三方应用—demo前端资源开发中有介绍。

后端调用方式可保证流程引擎和表单数据在同一事务下进行。

​ 后端调用时submit接口参数BfpContext中有对应保存接口url和header头信息,header头信息用于三方接口请求认证头,防止接口被认证拦截。

# 安装介质和三方应用创建开发部署

# 1、获取介质包

流程中心使用EOS相关介质包(${VERSION}为对应版本)

bps引擎后端介质包 BPS_Standalone__${VERSION}.tar.gz
bps引擎前端介质包 BPS_Standalone_UI_${VERSION}.tar.gz

# 2、创建三方应用

如下图。创建应用选择是否三方应用和三方应用地址,使用nacos注册中心时,三方应用地址可配置三方应用注册在nacos中的服务名。

image-20230625105646907

# 3、开发三方应用

流程设计阶段活动绑定表单url为三方应用开发页面,该页面由三方应用提供,即有独立后端服务和前端资源。以下说明均用demo名来作为三方应用名,修改文件目录以示例demo项目为准

# demo后端接口开发

# 接口规范

# 保存接口:
接口请求path 自定义
请求方式 post
入参 Map<String, Object> params
出参 String[] (必要)

说明:

Params入参中有formData、processContext两个key值属性。

formData为表单提交数据数组格式 List<Map<String, Object>>类型

processContext为流程上下文json对象 Object类型

String[] 出参为保存表单数据后返回的主键值

示例:

@PostMapping("/save")
public String[] saveFormData(@RequestBody Map<String, Object> params){
    List<Map<String, Object>> formData = (List<Map<String, Object>>)params.get("formData");
    Object processContext = params.get("processContext");
    return formDataService.saveFormData(formData,processContext);
}

# 查询接口:
请求接口path 自定义
请求方式 post
入参 Map<String, Object> params
出参 Map<String,Object> (必要)

说明:

Params入参中有bizPrimaryKeyId、bizPrimaryKeyValue、processContext三个key值属性。bizPrimaryKeyId为查询主键属性 String类型(如值为id)

bizPrimaryKeyValue 为业务主键值 List类型

processContext为流程上下文json对象 Object类型

Map<String,Object> 出参为查询返回的表单数据集

示例:

@PostMapping("/query")
public Map<String,Object> queryFormData(@RequestBody Map<String, Object> params){
    String  bizPrimaryKeyId = (String)params.get("bizPrimaryKeyId");
    List<String> bizPrimaryKeyValue = (List) params.get("bizPrimaryKeyValue");
    Object processContext = params.get("processContext");
    return formDataService.queryFormData(bizPrimaryKeyId,bizPrimaryKeyValue,processContext);
}

# demo前端资源开发

# 前端调用保存查询相关配置

前端通过postmessage实现跨域通信和页面间数据通信,实现三方系统表单页面来触发保存接口,该过程由前端调用。

  • 表单demo修改配置 \demo_vue\config.js

    • 配置 demo 应用流程中心 postMessage 收发消息地址
    // postMessage 消息相关地址
    const postMessageConfig = {
      // afc(bfp)地址, 即iframe表单发消息的目标地址
      targetOrigin: "http://localhost:8000",
      // targetOrigin: "http://127.0.0.1:14082",
    
      // 可接收的afc页面地址
      acceptableUrlList: [
        "http://localhost:8000",
        "http://127.0.0.1:14082",
      ],
    };
    
    • 是否调用三方应用提交接口
    const isTrilateralSubmit = true; // bfp前端提交
    // const isTrilateralSubmit = false; // bfp后端提交
    
    • 配置三方应用接口地址
    const dataUrl = {
      save: "http://127.0.0.1:28082/demo-formdata/api/form-data/save", // 保存表单
      query: "http://127.0.0.1:28082/demo-formdata/api/form-data/query", // 加载表单
    };
    
    • 配置三方应用认证头
    const headers = { apple: "11", baby: "22", canon: "33" };
    
  • BPS_Standalone_UI包中修改配置

    • 配置流程中心 postMessage 接收消息地址 static\js\iframeConfig.js
    window.iframeFormMessageConfig = {
      // 三方表单页面所在地址  
      acceptableUrlList: [
          "http://127.0.0.1:5500",
          "http://127.0.0.1:5501",
          "http://127.0.0.1:5502",
      ],
    }
    

# 后端调用保存相关配置

​ bfp后端接口rest远程调用三方保存数据接口来实现,该场景修改配置步骤和前端调用保存查询相关配置一致,区别在于以下

  • 是否调用三方应用提交接口
// const isTrilateralSubmit = false; // bfp前端提交
const isTrilateralSubmit = true; // bfp后端提交

# demo前后端示例资源包

后端示例源码

前端示例源码

# 4、三方应用部署

# nginx配置修改

其中proxy_set_header X-BPS-TenantId 设置被代理服务器接收到的header信息,X-BPS-TenantId为多租户场景时bps的租户id。

当存在多个不同三方应用对应不同租户场景时,需要在对应nginx配置中添加此配置。

 server {
     listen       28082;
     proxy_set_header Host $host;
     proxy_set_header X-Real-IP $remote_addr;
     proxy_set_header X-Real-Port $remote_port;
     proxy_set_header REMOTE-HOST $remote_addr;
     proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
     location / {
            root  /opt/taskcenter/web/nginxweb-data;
            # 配置页面不缓存html和htm结尾的文件
    		if ($request_filename ~* .*\.(?:htm|html)$) 
    		{
    			add_header Cache-Control "private, no-store, no-cache, must-revalidate, proxy-revalidate";
    		}
            index  index.html index.htm;
            try_files $uri /index.html;
        }

        location /afc/{
                proxy_pass http://127.0.0.1:28083/;
        }
        location /AFCENTER/{
                proxy_pass http://127.0.0.1:28083/;
        }
    	#三方应用路由地址
        location /demo1 {
        		proxy_set_header X-BPS-TenantId bbbbb111;
                proxy_pass http://127.0.0.1:28083/;
        }
    	#三方应用路由地址
        location /demo2 {
        		proxy_set_header X-BPS-TenantId bbbbb222;
                proxy_pass http://127.0.0.1:28083/;
        }    
    }

# 三方表单页面使用

三方应用开发部署完成后提供具体三方表单页面url,流程引擎中创建流程环节绑定对应url以实现表单数据三方保存场景。如下图为在afc中资源管理里针对三方应用可以新建流程。

image-20230626104230299

image-20230626104539663

流程引擎接口以表单url为http或https开头来确定是三方表单请求,具体体现在接口参数processContext对象的actionURL属性中。

示例:

image-20230626110401010

# 特殊说明

# demo表单开发规范参考

# 页面风格

  • 主体风格参考 element-ui,组件为mini 尺寸, 字体14px。

  • 为避免出现横竖滚动条,不要设置页面的宽度和高度, 不要设置背景色,避免嵌套多层iframe,尽量不要使用弹窗组件。

# 安全问题

  • 推荐将第三方表单和afcenter 部署在同域下

  • 如二者不同域, 需在afcenter代理服务器上设置 X-Frame-Options ALLOW-FROM, 指定受信域名列表。

# 表单开发

  • vue示例,需引入vue、element-ui资源

  • jquery示例,需引入jquery、jquery.validate资源

  • 表单页面使用以下钩子函数和 bfp 交互数据

    • getAnchors(bfpContext, processContext)

      • 处理表单的分隔符锚点数据数据,表单页面左侧显示纵向导航条

      • 在页面上添加带有class和id序号的分隔符组件

        <el-divider content-position="left">
            <span class="anchor" id="anchor-1">活动名称</span>
        </el-divider>
        
    • loadFormData(bfpContext, processContext)

      • 载入表单时的动作
    • beforeSaveFormData(bfpContext, processContext)

      • 保存前的动作,可以在此对表单内容做校验
    • saveFormData(bfpContext, processContext)

      • 保存时的动作,需要返回表单数据
      • 根据 isTrilateralSubmit 的值决定是否调用三方应用保存接口
      • 三方应用提交接口失败时需要做回滚处理
        • rollbackFormDataHandle(bfpContext, processContext)
    • afterSaveFormData(bfpContext, processContext)

      • 保存后的动作
      • 根据 isFailed 字段判断做表单回滚保存后处理
  • bfp与iframe表单页面通信

    • 通信建议使用 window.parent.postMessage,尽量不要使用window.top, window.history ,window.location 等对象刷新页面, 建议使用内部路由实现页面切换。
    • targetOrigin
      • 表单页面postMessage可发送消息地址,即bfp地址
    • acceptableUrlList
      • postMessage可接收消息地址列表,至少包含bfp地址
  • 消息接收处理方法 msgReceiveHandler

    • 根据msg的做不同处理
  • 消息发送处理方法 msgSendHandler

    • 通过postMessage发送消息数据给父页面bfp
  • 监听消息

  • 发起消息

    mounted() {
        const msgJson = JSON.stringify({
          msg: "iframeFormIsLoaded",
        });
    	window.parent.postMessage(msgJson, postMessageConfig.targetOrigin);
    },
    
  • iframe表单调用提交、加载表单接口

    • 提交和加载需要另外完成,分别在saveFormData 和 loadFormData中
    • demo中设置变量 isTrilateralSubmit,表示是否采用三方应用提交接口
    • isTrilateralSubmit 置为 true 时
      • 采用三方应用提交保存接口(bfp前端提交),且需要将接口返回的bizPrimaryKeyValue值塞入form表单中
      • 采用三方应用加载表单接口
    • isTrilateralSubmit 置为 false 时
      • 不调用三方应用提交保存接口(bfp后端提交),需要将表单页面设置的dataSaveUrl、headers值塞入form表单中
      • 采用三方应用加载表单接口
  • 主键ID数组 bizPrimaryKeyValue

    • 流程的发起环节和中间环节
      • saveFormData方法将三方提交接口返回的主键数组 bizPrimaryKeyValue发送给bfp,bfp加入参数后再调用自己的提交接口
    • 流程表单load加载时
      • 需要将 bizPrimaryKeyValue 参数加入后再调用加载接口
      • bizPrimaryKeyValue获取路径,bfpContext.formData. bizPrimaryKeyValue
上次更新: 2023/7/20下午12:25:28