泛微OAe9-自定义资源看板

泛微OAe9-自定义资源看板

文章目录

    • 泛微OAe9-自定义资源看板
      • 前言
      • 一、搭建车辆信息资源
        • [1 后端->建模引擎->表单:新建车辆信息](#1 后端->建模引擎->表单:新建车辆信息)
        • [2 后端->建模引擎->模块:新建车辆信息模块](#2 后端->建模引擎->模块:新建车辆信息模块)
        • [3 后端->建模引擎->查询:新建车辆信息查询](#3 后端->建模引擎->查询:新建车辆信息查询)
        • [4 搭建车辆信息的浏览框:车辆信息_clxx](#4 搭建车辆信息的浏览框:车辆信息_clxx)
      • 二、搭建车辆预约
        • [1 后端->建模引擎->表单:新建用车申请](#1 后端->建模引擎->表单:新建用车申请)
        • [2 后端->建模引擎->模块:用车申请模块-最关键](#2 后端->建模引擎->模块:用车申请模块-最关键)
          • [2.1 新建模块,最重要](#2.1 新建模块,最重要)
          • [2.2 冲突字段字段属性](#2.2 冲突字段字段属性)
          • [2.3 配置数据审批](#2.3 配置数据审批)
      • 三、搭建资源看板
      • 四、验证

前言

OA中,有一个很好用的功能:会议室预约。对于一间设立的会议室,同一时间段内,肯定会有不同的人预约同一间会议室,并且,在资源看板里,能看清各个时间段会议室的占用情况,可是会议室资源是有限的,显然不可能让多个人在同一时间段内预约同一间会议室,如会议室已占用,其他人再次申请时,应当拒绝预约。

废话不多说,下面我引入一个实际的案例,展示如何自定义搭建一个资源看板,下面我举例公司的用车预约:即把公司的车辆当作一间会议室去预约,当公司员工有出差自驾需求时,可自行预约。

一、搭建车辆信息资源

对于车辆的预约,肯定是先有车辆,才能预约,站在数据库的角度,则对应一张车辆表、一张预约表。

1 后端->建模引擎->表单:新建车辆信息

字段可自定义,此处我展示我所建立的字段:

对于车辆表,肯定需要有一个唯一标识,此处我把车牌号、车辆id作为一辆车的唯一标识。即在车辆表里,不能插入同一个车牌号的不同车辆(实际情况下车牌号如同人的身份证号,可以唯一区分每一辆车)。

2 后端->建模引擎->模块:新建车辆信息模块

对于模块,同步搭建即可,这里对应插入数据时显示的模板,再者把模块的权限维护好,比如车辆管理员可插入数据等,此处不过多赘述。

3 后端->建模引擎->查询:新建车辆信息查询

车辆信息查询和模块类似,不必进行过多的配置,这里重点需要配置好权限。

对于车牌号,可以设置成自定义链接,点击车牌号的时候,可以跳转到显示模板,展示车辆的各项属性信息:

车牌号的自定义链接:

text 复制代码
/spa/cube/index.html#/main/cube/card?type=$type$&modeId=$modeId$&formId=$formId$&billid=$billid$&opentype=$opentype$&customid=$customid$&viewfrom=$viewfrom$


4 搭建车辆信息的浏览框:车辆信息_clxx

步骤1-3搭建的车辆信息,本质上是作为一个浏览按钮字段,在用车预约的时候,车辆资源引用,具体引用见下文用车预约。

浏览框截图:

二、搭建车辆预约

车辆预约就是用车申请,需按照车辆资源的步骤配置一遍。

1 后端->建模引擎->表单:新建用车申请

字段说明:

  • 车辆资源:必须,并且是浏览按钮,需引用上面的车辆信息。
  • 冲突字段:必须,文本框,用于预约时判断是否冲突。
  • 审批流程:必须,浏览按钮-流程,预约单填写成功后,可自动触发审批流,若不触发审批流也可以不用此字段。
  • 用车人:必须,单人力资源,车辆预约人。
  • 用车部门:必须,部门。
  • 标题:非必须,自定义标题,建议加一个标题字段。
  • 用车开始日期:必须,日期字段。
  • 用车开始时间:必须,时间字段。
  • 预计用车结束日期:必须,日期字段。
  • 预计用车结束时间:必须,时间字段。
  • 用车说明:非必须,多文本。
  • 申请号:非必须,如有审批流程字段,本字段也需加上,用于判断流程是否为触发流程,下文演示。
  • 备注:非必须。

重复校验建议把所有字段加上,出现预约单一模一样时,直接阻断提交。

2 后端->建模引擎->模块:用车申请模块-最关键

先是正常配置三个布局:

2.1 新建模块,最重要

新建模块内,需对开始日期,结束日期做一些约束,比如:结束日期肯定不能在开始日期前。新建模块内,也需配置冲突字段的逻辑,需查预约表,判断当前预约单是否冲突。

模板及 fieldid 截图:fieldid会在字段属性、插入代码中使用。

代码块的日期约束:

js 复制代码
window.checkCustomize = function(){ 
    var flag = true;
    var value = ModeForm.getFieldValue("field108183"); // 冲突字段
    if(value !="" ){
      flag = false; // 冲突字段有值,代表冲突,不可提交
      //alert("您预约的时间与"+value+"冲突!请重新选择预约时间!");
      ModeForm.showModalMsg("系统提示","<div style='color:red;'>您用车的时间有冲突!请重新选择用车时间!</div>", 2);
      ModeForm.changeFieldValue("field108184",{value:""});
      ModeForm.changeFieldValue("field108185",{value:""});
      ModeForm.changeFieldValue("field108186",{value:""});
      ModeForm.changeFieldValue("field108187",{value:""});
      ModeForm.changeFieldValue("field108183",{value:""});
    }
    // 用车开始日期、时间,必须在结束日期、时间之后
    var ycksrq = ModeForm.getFieldValue("field108184"); // 用车开始日期
    var yckssj = ModeForm.getFieldValue("field108185"); // 用车开始时间
    var yjycjsrq = ModeForm.getFieldValue("field108186"); // 预计用车结束日期
    var yjycjssj = ModeForm.getFieldValue("field108187"); // 预计用车结束时间
    var startTime = ycksrq +" "+ yckssj;
    var endTime = yjycjsrq +" "+ yjycjssj;
    var sum = compareDates(startTime, endTime);
    if(sum == 1 || sum == 0) { // 用车结束日期,不能在开始日期之前
      ModeForm.showModalMsg("系统提示","<div style='color:red;'>结束时间需大于开始时间!</div>", 2);
      flag = false;
    }
    return flag;  // 同步提交
}
ModeForm.bindFieldChangeEvent("field108184,field108185,field108186,field108187",function(obj,id,value){   
    // 用车开始日期、时间,必须在结束日期、时间之后
    var ycksrq2 = ModeForm.getFieldValue("field108184"); // 用车开始日期
    var yckssj2 = ModeForm.getFieldValue("field108185"); // 用车开始时间
    var yjycjsrq2 = ModeForm.getFieldValue("field108186"); // 预计用车结束日期
    var yjycjssj2 = ModeForm.getFieldValue("field108187"); // 预计用车结束时间
    var startTime2 = ycksrq2 +" "+ yckssj2;
    var endTime2 = yjycjsrq2 +" "+ yjycjssj2;
    var sum2 = compareDates(startTime2, endTime2);
    if(sum2 == 1 || sum2 == 0) { // 用车结束日期,不能在开始日期之前
      ModeForm.showModalMsg("系统提示","<div style='color:red;'>结束时间需大于开始时间!</div>", 2);
    }
});

function compareDates(dateStr1, dateStr2) {
    // 将字符串转换为日期对象
    const date1 = new Date(dateStr1.replace(" ", "T"));
    const date2 = new Date(dateStr2.replace(" ", "T"));
    // 比较日期对象
    if (date1 > date2) {
        return 1;
    } else if (date1 < date2) {
        return -1;
    } else {
        return 0;
    }
}
2.2 冲突字段字段属性

冲突字段的字段属性:读者也可以自行更改sql,sql就是用于判断新预约和预约表里历史数据,是否冲突。

方案一:

sql 复制代码
select ycsm from uf_ycsq where (
    ((ycksrq+' '+yckssj)>=('$108184$'+' '+'$108185$') and (ycksrq+' '+yckssj)<('$108186$'+' '+'$108187$'))
    or 
    ((ycksrq+' '+yckssj)<('$108184$'+' '+'$108185$') and (yjycjsrq+' '+yjycjssj)>('$108184$'+' '+'$108185$'))
) and clzy=$108179$

方案二:本人分析对于冲突的情况,有如下4种,4种情况组合起来,就是冲突的逻辑。

对于其它方案,读者自行分析。

2.3 配置数据审批

由于我演示的案例设置了自动触发审批流,因此需要在模块里进行配置,配置后,每新建一个预约单,都有发起审批流,给相应的人审批。

上文用车申请的申请号字段,就是用于触发审批流时,自动生成一个申请号,然后对接到流程里,这样就能区别是自动触发的还是手动新建流程的。

三、搭建资源看板

四、验证

此时可以在前端的维护里,查看到车辆预约的资源看板,也可以在里面进行相应的预约。

如果在同一时间段内预约了同一辆车,则会有冲突提醒:

演示结束。

相关推荐
im_AMBER14 分钟前
java复习 11
java·开发语言
郭尘帅66616 分钟前
Spring依赖注入的四种方式(面)
java·后端·spring
潘小磊18 分钟前
高频面试之10 Spark Core & SQL
sql·面试·spark
风象南25 分钟前
SpringBoot防重放攻击的5种实现方案
java·spring boot·后端
[email protected]26 分钟前
Asp.Net Core SignalR导入数据
前端·后端·asp.net·.netcore
callJJ1 小时前
从 0 开始理解 Spring 的核心思想 —— IoC 和 DI(1)
java·开发语言·spring boot·后端·spring·restful·ioc di
编程乐学(Arfan开发工程师)7 小时前
56、原生组件注入-原生注解与Spring方式注入
java·前端·后端·spring·tensorflow·bug·lua
周某某~7 小时前
七.适配器模式
java·设计模式·适配器模式
Elcker9 小时前
Springboot+idea热更新
spring boot·后端·intellij-idea