瀏覽代碼

钉钉通过排班接口获取出差记录

QuYueTing 8 月之前
父節點
當前提交
71450115a4

+ 8 - 0
fhKeeper/formulahousekeeper/management-platform/src/main/java/com/management/platform/controller/DingDingController.java

@@ -194,6 +194,14 @@ public class DingDingController {
     public HttpRespMsg refreshUserCardTime(Integer companyId, String userId, String date) {
         return dingDingService.refreshUserCardTime(companyId, userId, date);
     }
+    @RequestMapping("/listUserScheduleByDay")
+    public HttpRespMsg listUserScheduleByDay(Integer companyId, String userId, String date) {
+        HttpRespMsg msg = new HttpRespMsg();
+        UserDingdingTime time = dingDingService.listUserScheduleByDay(companyId, userId, date);
+        msg.data = time;
+        return msg;
+    }
+
 //
 //    @RequestMapping("/syncLeaveTime")
 //    public HttpRespMsg syncLeaveTime(Integer companyId, String userId, String startDate, String endDate) {

+ 7 - 1
fhKeeper/formulahousekeeper/management-platform/src/main/java/com/management/platform/entity/UserDingdingTime.java

@@ -19,7 +19,7 @@ import org.springframework.format.annotation.DateTimeFormat;
  * </p>
  *
  * @author Seyason
- * @since 2022-04-26
+ * @since 2024-11-03
  */
 @Data
 @EqualsAndHashCode(callSuper = false)
@@ -66,6 +66,12 @@ public class UserDingdingTime extends Model<UserDingdingTime> {
     @TableField("work_hours")
     private Float workHours;
 
+    /**
+     * 是否是出差
+     */
+    @TableField("is_offi_business")
+    private Integer isOffiBusiness;
+
 
     @Override
     protected Serializable pkVal() {

+ 3 - 0
fhKeeper/formulahousekeeper/management-platform/src/main/java/com/management/platform/service/DingDingService.java

@@ -2,6 +2,7 @@ package com.management.platform.service;
 
 import com.alibaba.fastjson.JSONArray;
 import com.management.platform.entity.CompanyDingding;
+import com.management.platform.entity.UserDingdingTime;
 import com.management.platform.util.HttpRespMsg;
 import com.taobao.api.ApiException;
 
@@ -62,4 +63,6 @@ public interface DingDingService {
     HttpRespMsg getAuthInfo(String corpid) throws Exception;
 
     HttpRespMsg refreshUserCardTime(Integer companyId, String userId, String date);
+
+    UserDingdingTime listUserScheduleByDay(Integer companyId, String userId, String date);
 }

+ 125 - 0
fhKeeper/formulahousekeeper/management-platform/src/main/java/com/management/platform/service/impl/DingDingServiceImpl.java

@@ -2455,6 +2455,19 @@ public class DingDingServiceImpl implements DingDingService {
         }
     }
 
+    private String listUserScheduleByDay(CompanyDingding dingding, String userDingdingId, String accessToken, long dateTime) throws ApiException {
+        DingTalkClient client = new DefaultDingTalkClient("https://oapi.dingtalk.com/topapi/attendance/schedule/listbyday");
+        OapiAttendanceScheduleListbydayRequest req = new OapiAttendanceScheduleListbydayRequest();
+        System.out.println("管理员id=="+dingding.getAuthUserId());
+        req.setOpUserId(dingding.getAuthUserId());//获取管理员id
+        req.setUserId(userDingdingId);
+        req.setDateTime(dateTime);
+        OapiAttendanceScheduleListbydayResponse rsp = client.execute(req, accessToken);
+        System.out.println("获得排班结果=="+rsp.getErrcode()+", "+rsp.getBody()+",错误消息:"+rsp.getErrmsg());
+        return rsp.getBody();
+    }
+
+
 
     //同步公司全部人员的假期余额
     private void syncQuotaList(String leaveCode,String oaManagerDid, CompanyDingding dingding, List<User> userList, long offset) {
@@ -2723,10 +2736,122 @@ public class DingDingServiceImpl implements DingDingService {
         List<UserDingdingTime> timeList = userDingdingTimeMapper.selectList(new QueryWrapper<UserDingdingTime>().eq("company_id", companyId).eq("user_id", userId).eq("work_date", date));
         if (timeList.size() > 0) {
             msg.setData(timeList.get(0));
+        } else {
+            //尝试查询出差记录
+            if (userId != null) {
+                msg.data = listUserScheduleByDay(companyId, userId, date);
+            }
         }
         return msg;
     }
 
+    @Override
+    public UserDingdingTime listUserScheduleByDay(Integer companyId, String userId, String date) {
+        CompanyDingding dingding = companyDingdingMapper.selectOne(new QueryWrapper<CompanyDingding>().eq("company_id", companyId));
+        try {
+            //date为yyyy-MM-dd格式,转化为时间戳
+            long time = LocalDateTime.parse(date+"T00:00:00").toEpochSecond(ZoneOffset.ofHours(8))*1000;
+            User user = userMapper.selectById(userId);
+            String result = listUserScheduleByDay(dingding, user.getDingdingUserid(), getCorpAccessToken(dingding), time);
+            //抽取出差时间
+            JSONObject json = JSONObject.parseObject(result);
+            JSONArray array = json.getJSONArray("result");
+            String startTime = null;
+            String endTime = null;
+            String realPlanStartTime = null;
+            String realPlanEndTime = null;
+            for (int i=0;i<array.size(); i++) {
+                JSONObject obj = array.getJSONObject(i);
+                //出差类型
+                System.out.println(obj);
+                if (obj.getInteger("approve_biz_type") == 2) {
+                    if (obj.getString("check_type").equals("OnDuty")) {
+                        //出差开始时间
+                        System.out.println("出差开始时间=="+obj.getString("check_date_time"));
+                        startTime = obj.getString("check_date_time");
+                        realPlanStartTime = obj.getString("real_plan_time");
+                    } else {
+                        //出差结束时间
+                        System.out.println("出差结束时间=="+obj.getString("check_date_time"));
+                        endTime = obj.getString("check_date_time");
+                        realPlanEndTime = obj.getString("real_plan_time");
+                    }
+                }
+            }
+            if (startTime != null && endTime != null) {
+                //获取到出差的时间,计算时长
+                DateTimeFormatter dtf = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
+                LocalDateTime start = LocalDateTime.parse(startTime, dtf);
+                LocalDateTime end = LocalDateTime.parse(endTime, dtf);
+                UserDingdingTime userDingdingTime = new UserDingdingTime();
+                userDingdingTime.setUserId(userId);
+                userDingdingTime.setIsOffiBusiness(1);//出差
+                userDingdingTime.setDingdingUserid(user.getDingdingUserid());
+                userDingdingTime.setDingdingCorpid(dingding.getCorpid());
+                userDingdingTime.setCompanyId(companyId);
+                userDingdingTime.setWorkDate(LocalDate.parse(date));
+                DateTimeFormatter mmFormat = DateTimeFormatter.ofPattern("HH:mm");
+                userDingdingTime.setStartTime(start.format(mmFormat));
+                userDingdingTime.setEndTime(end.format(mmFormat));
+                //计算周几
+                userDingdingTime.setWeekDay(userDingdingTime.getWorkDate().getDayOfWeek().getValue());
+                userDingdingTime.setWeekDayTxt(DateTimeUtil.getWeekDayTxt(userDingdingTime.getWeekDay()));
+                if (start.getDayOfYear() != end.getDayOfYear()) {
+                    //可能是跨天的情况,要计算,判断
+                    //转化为yyyy-MM-dd格式
+                    String startDateStr = startTime.substring(0, 10);
+                    String endDateStr = endTime.substring(0, 10);
+                    if (startDateStr.equals(date)) {
+                        //第一天
+                        long seconds = end.toEpochSecond(ZoneOffset.ofHours(8)) - start.toEpochSecond(ZoneOffset.ofHours(8));
+                        double workHours = DateTimeUtil.getHoursFromDouble(DateTimeUtil.getHoursFromSeconds((int) seconds));
+                        System.out.println("出差时长=="+workHours);
+                        userDingdingTime.setWorkHours((float)workHours);
+                    } else if (endDateStr.equals(date)) {
+                        //最后一天
+                        long seconds = end.toEpochSecond(ZoneOffset.ofHours(8)) - start.toEpochSecond(ZoneOffset.ofHours(8));
+                        double workHours = DateTimeUtil.getHoursFromDouble(DateTimeUtil.getHoursFromSeconds((int) seconds));
+                        System.out.println("出差时长=="+workHours);
+                        userDingdingTime.setWorkHours((float)workHours);
+                    } else {
+                        //中间天,就是全天
+                        LocalDateTime normalStart = LocalDateTime.parse(realPlanStartTime);
+                        LocalDateTime normalEnd = LocalDateTime.parse(realPlanEndTime);
+                        userDingdingTime.setStartTime(normalStart.format(mmFormat));
+                        userDingdingTime.setEndTime(normalEnd.format(mmFormat));
+                        //计算realPlanEndTime-realPlanStartTime
+                        long seconds = normalEnd.toEpochSecond(ZoneOffset.ofHours(8)) - normalStart.toEpochSecond(ZoneOffset.ofHours(8));
+                        double workHours = DateTimeUtil.getHoursFromDouble(DateTimeUtil.getHoursFromSeconds((int) seconds));
+                        userDingdingTime.setWorkHours((float)(workHours));
+                    }
+                } else {
+                    //就是当天,计算时长
+                    long seconds = end.toEpochSecond(ZoneOffset.ofHours(8)) - start.toEpochSecond(ZoneOffset.ofHours(8));
+                    double workHours = DateTimeUtil.getHoursFromDouble(DateTimeUtil.getHoursFromSeconds((int) seconds));
+                    System.out.println("出差时长=="+workHours);
+                    userDingdingTime.setWorkHours((float)workHours);
+                }
+                if (userDingdingTime.getWorkHours() > 8.0) {
+                    //全天的情况,要减去中间的休息时间
+                    double restTime = 1.0f;
+                    userDingdingTime.setWorkHours(userDingdingTime.getWorkHours()-1.0f);
+                }
+                //保存数据
+                UserDingdingTime ddTime = userDingdingTimeMapper.selectOne(new QueryWrapper<UserDingdingTime>().eq("company_id", companyId).eq("user_id", userId).eq("work_date", date));
+                if (ddTime != null) {
+                    userDingdingTime.setId(ddTime.getId());
+                    userDingdingTimeMapper.updateById(userDingdingTime);
+                } else {
+                    userDingdingTimeMapper.insert(userDingdingTime);
+                }
+                return userDingdingTime;
+            }
+        } catch (ApiException e) {
+            throw new RuntimeException(e);
+        }
+        return null;
+    }
+
     private boolean judgeIsLeader(String userId) {
         int cnt = projectAuditorMapper.selectCount(new QueryWrapper<ProjectAuditor>().eq("auditor_id", userId));
         return cnt>0;

+ 2 - 1
fhKeeper/formulahousekeeper/management-platform/src/main/resources/mapper/UserDingdingTimeMapper.xml

@@ -15,11 +15,12 @@
         <result column="week_day" property="weekDay" />
         <result column="week_day_txt" property="weekDayTxt" />
         <result column="work_hours" property="workHours" />
+        <result column="is_offi_business" property="isOffiBusiness" />
     </resultMap>
 
     <!-- 通用查询结果列 -->
     <sql id="Base_Column_List">
-        id, work_date, dingding_userid, user_id, dingding_corpid, company_id, start_time, end_time, week_day, week_day_txt, work_hours
+        id, work_date, dingding_userid, user_id, dingding_corpid, company_id, start_time, end_time, week_day, week_day_txt, work_hours, is_offi_business
     </sql>
 
 </mapper>

+ 1 - 1
fhKeeper/formulahousekeeper/timesheet/src/views/workReport/daily.vue

@@ -417,7 +417,7 @@
                     </el-form-item>
                     <!--考勤时长显示-->
                     <el-form-item :label="$t('other.attendancePunch')" v-if="workForm.showRefresh || user.companyId == 5978">
-                        <span v-if="workForm.time">{{workForm.time.startTime}}-{{workForm.time.endTime}}, 工作{{workForm.time.workHours}}{{$t('time.hour')}}
+                        <span v-if="workForm.time">{{workForm.time.startTime}}-{{workForm.time.endTime}}, {{workForm.time.isOffiBusiness?'出差':'工作'}}{{workForm.time.workHours}}{{$t('time.hour')}}
                         <span v-if="workForm.time.askLeaveTime">|&nbsp;{{ $t('other.AskForLeave') }}{{ workForm.time.askLeaveTime }}{{$t('time.hour')}}</span>
                         <span v-if="workForm.time.otTime" style="color:#FFA500;">|&nbsp;加班{{ workForm.time.otTime }}{{$t('time.hour')}}</span>
                         </span>