飞书开放接口JavaSDK是飞书官方开发的一套封装了飞书开放平台请求的Java借口,便于企业应用整合到飞书平台。
具体可参考飞书官方开源仓库(可以拉取源码,查看官方demo):
https://github.com/larksuite/oapi-sdk-java
建议直接查看对应Service源码,官方demo过于简单(小声吐槽)。
本次实现主要针对飞书平台的基础通讯录功能(ContantService)的使用
这里使用的是1.0.17-rc2版本,自己开发可以选用更新的版本。
com.larksuite.oapi
larksuite-oapi
1.0.17-rc2
1.本地建立两张飞书信息表(feishu_user和feishu_dept)
2.对线上飞书平台的操作返回成功(response.getCode == 0)后,将信息都存入本地飞书表
3.比对飞书信息表和本地架构信息表,查找出需要 增、删、改 的部门和用户
4.批量操作同步数据
在创建ContactService时,SDK会自动进行access_token的封装,实现开箱即用。
只要传入app_id和app_secret即可获取通讯录对应的权限。
@Configuration
public class FeishuConfig {
//app_id和app_secret在飞书平台的开发者后台-企业自建应用-凭证与基础信息可找到
private static final AppSettings appSettings = Config
.createInternalAppSettings(Constants.APP_ID,Constants.APP_SECRET,null,null);
//要使用时直接使用@Resource注解即可自动注入
@Bean(name = "contactService")
public ContactService getContactService(){
final Config config = new Config(Domain.FeiShu, appSettings,new DefaultStore());
return new ContactService(config);
}
}
注意事项: 必须先创建父部门(本地oa部门一般都有部门层级字段,按层级排序即可),然后才能创建子部门
Department department = new Department();//Department为API中封装好的实体类
//对department的必要参数进行设置
//略,具体请查询官方API文档(不可设置leaderUserId,因为leader可能没有创建)
//顶级部门的parentDepartmentId为“0”
Response<DepartmentCreateResult> response = contactService.getDepartments()
.create(department)
.setDepartmentIdType(Constants.CUSTOM_DEPT_ID_TYPE)//使用自己设置的department_id
.setUserIdType(Constants.CUSTOM_USER_ID_TYPE)//使用自己设置的user_id
.execute();
if(response.getCode() == 0){
//如果创建成功,将飞书部门信息录入本地
maaper.insert();//略
System.out.println("更新成功部门号"+dept.getDepartmentId());
}else{
System.out.println("更新失败部门号"+dept.getDepartmentId()+response.getMsg());
}
Department dept = new Department();
//设置dept的必要参数
//略
//只有更新部门时才设置leaderId,因为创建部门时leader可能还没有被创建
dept.setLeaderUserId(leaderId);
Response<DepartmentUpdateResult> response = contactService.getDepartments()
.update(dept)
.setDepartmentId(dept.getDepartmentId())
.setDepartmentIdType(Constants.CUSTOM_DEPT_ID_TYPE)
.setUserIdType(Constants.CUSTOM_USER_ID_TYPE).execute();
if(response.getCode() == 0){
//更新本地的飞书信息
System.out.println("更新成功部门号"+dept.getDepartmentId());
}else{
System.out.println("更新失败部门号"+dept.getDepartmentId()+response.getMsg());
}
飞书对于部门的删除要求较为严格,必须保证部门中没有子部门且没有用户。
在数据同步过程中,必须先删除用户,再递归删除空部门(没有用户的部门)。
/**
* 查询某个部门的直属子部门
*/
public List<String> selectSubDept(String deptId) throws Exception {
Response<DepartmentListResult> response = contactService.getDepartments().list()
.setParentDepartmentId(deptId)
.setDepartmentIdType(Constants.CUSTOM_DEPT_ID_TYPE)
.execute();
if(response.getCode() == 0 && null != response.getData().getItems()){
//将获取的子部门dept_id存入list并返回
List<String> list = Arrays.stream(response.getData().getItems())
.map(item -> item.getDepartmentId())
.collect(Collectors.toList());
return list;
}else{
return new ArrayList<>();
}
}
/**
* 删除部门号为deptId的 部门及其子部门
*/
public void deleteAllDept(String deptId) throws Exception {
List<String> subIds = feishuService.selectSubDept(deptId);
//如果当前部门存在子部门,则继续删除其子部门
if(subIds.size()>0){
for (String subId : subIds) {
deleteAllDept(subId);
}
}
//子部门删除后 删除当前部门
delDept(deptId);
}
/**
* 删除飞书平台的某个部门
*/
public void delDept(String deptId) throws Exception {
Response<EmptyData> response = contactService.getDepartments()
.delete()
.setDepartmentIdType(Constants.CUSTOM_DEPT_ID_TYPE)
.setDepartmentId(deptId).execute();
if(response.getCode() == 0){
//删除本地飞书信息
System.out.println("删除成功部门:"+deptId+ response.getMsg());
}else{
System.out.println("删除失败部门号:"+deptId+response.getMsg());
}
}
User user = new User();
//设置user的必要参数(暂时不设置leder)
Response<UserCreateResult> response = contactService.getUsers()
.create(user)
.setUserIdType(Constants.CUSTOM_USER_ID_TYPE)
.setDepartmentIdType(Constants.CUSTOM_DEPT_ID_TYPE)
.execute();
if(response.getCode() == 0){
//将user信息存入本地
System.out.println("创建成功用户:"+user.getUserId());
}else{
System.out.println("创建失败用户:"+user.getUserId()+response.getMsg());
}
User user = new User();
//设置user必要参数
//并更新leader信息
user.setLeaderUserId(employee.getDirectorCode());
Response<UserUpdateResult> response = contactService.getUsers()
.update(user)
.setUserIdType(Constants.CUSTOM_USER_ID_TYPE)
.setDepartmentIdType(Constants.CUSTOM_DEPT_ID_TYPE)
.setUserId(user.getUserId()).execute();
if(response.getCode() == 0){
//将更新后的user存入本地
System.out.println("更新成功用户:"+user.getUserId());
}else{
System.out.println("更新失败用户:"+user.getUserId()+response.getMsg());
}
Response<EmptyData> response = contactService.getUsers()
.delete(new UserDeleteReqBody())
.setUserId(userId)
.setUserIdType(Constants.CUSTOM_USER_ID_TYPE)
.execute();
if(response.getCode() == 0){
//将本地的user信息删除
System.out.println("删除成功用户号:"+userId);
}else{
System.out.println("删除失败用户号:"+userId+response.getMsg());
}
获取contactService
确定具体要操作的对象(用户、部门、用户组、人员类型等)和 某种操作
具体的API格式大致为:
xxxService.getXXXXs.()
.todo()
.setParam()
.execute();
例如:
contactService
.getDepartments()
.create(department)
.setDepartmentIdType(department_id")
.execute();
创建部门和删除部门时,需要确认部门的层级关系(是否有父部门或子部门)
设置部门leader或用户leader时,需保证leader用户已经被创建