钉钉考勤
This commit is contained in:
@@ -22,6 +22,9 @@ import org.springframework.stereotype.Service;
|
|||||||
|
|
||||||
import java.math.BigDecimal;
|
import java.math.BigDecimal;
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
|
import java.util.concurrent.ExecutorService;
|
||||||
|
import java.util.concurrent.Executors;
|
||||||
|
import java.util.concurrent.Future;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
@Service
|
@Service
|
||||||
@@ -80,6 +83,10 @@ public class DingService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public Map<String, String> getColumns(String key, String secret, Long shopId) {
|
public Map<String, String> getColumns(String key, String secret, Long shopId) {
|
||||||
|
Object value = redisService.get("ding_columns:" + shopId);
|
||||||
|
if (value instanceof String && StrUtil.isNotBlank((String) value)) {
|
||||||
|
return JSONObject.parseObject((String) value, Map.class);
|
||||||
|
}
|
||||||
DingTalkClient client = new DefaultDingTalkClient("https://oapi.dingtalk.com/topapi/attendance/getattcolumns");
|
DingTalkClient client = new DefaultDingTalkClient("https://oapi.dingtalk.com/topapi/attendance/getattcolumns");
|
||||||
OapiAttendanceGetattcolumnsRequest req = new OapiAttendanceGetattcolumnsRequest();
|
OapiAttendanceGetattcolumnsRequest req = new OapiAttendanceGetattcolumnsRequest();
|
||||||
OapiAttendanceGetattcolumnsResponse rsp = null;
|
OapiAttendanceGetattcolumnsResponse rsp = null;
|
||||||
@@ -102,6 +109,7 @@ public class DingService {
|
|||||||
})
|
})
|
||||||
.collect(Collectors.toMap(item -> ((JSONObject) item).getLong("id").toString(), item -> ((JSONObject) item).getString("name")));
|
.collect(Collectors.toMap(item -> ((JSONObject) item).getLong("id").toString(), item -> ((JSONObject) item).getString("name")));
|
||||||
|
|
||||||
|
redisService.set("ding_columns:" + shopId, JSONObject.toJSONString(columMap));
|
||||||
return columMap;
|
return columMap;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -177,39 +185,54 @@ public class DingService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public ArrayList<DingUserVO> getUserList(String name,String key, String secret, Long shopId, String userId) {
|
public ArrayList<DingUserVO> getUserList(String name, String key, String secret, Long shopId, String userId) {
|
||||||
try {
|
try {
|
||||||
DingTalkClient client = new DefaultDingTalkClient("https://oapi.dingtalk.com/topapi/v2/department/listsub");
|
DingTalkClient client = new DefaultDingTalkClient("https://oapi.dingtalk.com/topapi/v2/department/listsub");
|
||||||
OapiV2DepartmentListsubRequest req = new OapiV2DepartmentListsubRequest();
|
OapiV2DepartmentListsubRequest req = new OapiV2DepartmentListsubRequest();
|
||||||
req.setDeptId(1L);
|
req.setDeptId(1L);
|
||||||
req.setLanguage("zh_CN");
|
req.setLanguage("zh_CN");
|
||||||
|
|
||||||
OapiV2DepartmentListsubResponse rsp = client.execute(req, getToken(key, secret, shopId));
|
OapiV2DepartmentListsubResponse rsp = client.execute(req, getToken(key, secret, shopId));
|
||||||
Set<Long> deptIdList = getData(rsp, true).getJSONArray("result").stream().map(item -> ((JSONObject) item)
|
|
||||||
.getLong("dept_id")).collect(Collectors.toSet());
|
|
||||||
|
|
||||||
ArrayList<DingUserVO> dingUserVOS = new ArrayList<>();
|
Set<Long> deptIdList = getData(rsp, true).getJSONArray("result")
|
||||||
for (Long dptId : deptIdList) {
|
.stream()
|
||||||
dingUserVOS.addAll(getUserByDeptId(dptId, key, secret, shopId));
|
.map(item -> ((JSONObject) item).getLong("dept_id"))
|
||||||
}
|
.collect(Collectors.toSet());
|
||||||
if (StrUtil.isNotBlank(name)) {
|
|
||||||
return dingUserVOS.stream().filter(item -> {
|
|
||||||
boolean flag = true;
|
|
||||||
if (StrUtil.isNotBlank(userId)) {
|
|
||||||
flag = item.getUserid().equals(userId);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (StrUtil.isNotBlank(name)) {
|
// 线程池:按 CPU 核数 * 2
|
||||||
flag = item.getName().contains(name);
|
ExecutorService pool = Executors.newFixedThreadPool(
|
||||||
}
|
Math.min(deptIdList.size(), Runtime.getRuntime().availableProcessors() * 2)
|
||||||
return flag;
|
);
|
||||||
}).collect(Collectors.toCollection(ArrayList::new));
|
|
||||||
|
List<Future<List<DingUserVO>>> futures = new ArrayList<>();
|
||||||
|
|
||||||
|
// 并发拉取
|
||||||
|
for (Long deptId : deptIdList) {
|
||||||
|
futures.add(pool.submit(() -> getUserByDeptId(deptId, key, secret, shopId)));
|
||||||
}
|
}
|
||||||
return dingUserVOS;
|
|
||||||
}catch (Exception e) {
|
// 汇总结果
|
||||||
|
List<DingUserVO> allUsers = new ArrayList<>();
|
||||||
|
for (Future<List<DingUserVO>> f : futures) {
|
||||||
|
allUsers.addAll(f.get());
|
||||||
|
}
|
||||||
|
|
||||||
|
pool.shutdown();
|
||||||
|
|
||||||
|
// 正确过滤逻辑
|
||||||
|
return allUsers.stream().filter(item -> {
|
||||||
|
if (StrUtil.isNotBlank(userId) && !item.getUserid().equals(userId)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return !StrUtil.isNotBlank(name) || item.getName().contains(name);
|
||||||
|
}).collect(Collectors.toCollection(ArrayList::new));
|
||||||
|
|
||||||
|
} catch (Exception e) {
|
||||||
throw new RuntimeException(e);
|
throw new RuntimeException(e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public ArrayList<DingAttendanceStatsVO> getUserReport(Long shopId, String key, String secret, DateTime startTime, DateTime endTime, String name, String userId) {
|
public ArrayList<DingAttendanceStatsVO> getUserReport(Long shopId, String key, String secret, DateTime startTime, DateTime endTime, String name, String userId) {
|
||||||
Map<String, String> columns = getColumns(key, secret, shopId);
|
Map<String, String> columns = getColumns(key, secret, shopId);
|
||||||
ArrayList<DingUserVO> userList = getUserList(name, key, secret, shopId, userId);
|
ArrayList<DingUserVO> userList = getUserList(name, key, secret, shopId, userId);
|
||||||
|
|||||||
Reference in New Issue
Block a user