谁悲失路之人
Springboot钉钉免密登录集成(钉钉小程序和H5微应用)

RT,因为业务需要把我们系统集成到钉钉里面一个小程序和一个H5应用,并且在钉钉平台上面实现无感登录,用户打开我们系统后不需要再输入密码即可登录进系统,查阅文档实际操作过之后记录一下过程

准备工作

首先就是需要在钉钉开发者平台申请账号资格,开发者后台管理,通过链接进去注册或者加入团队
然后就是从平台创建应用,平台有很多种不同类型的应用,我所需要创建的是企业内部应用,一个小程序,一个H5微应用,其他应用具体可以参考钉钉应用介绍的文档:https://open.dingtalk.com/document/orgapp/application-types
在这里插入图片描述
创建好了应用之后需要拿到应用的AppKey和AppSecret,点击应用详情里面能够看到,把这两个复制下来后面需要用到
在这里插入图片描述然后根据我的实际经验还需要设置几个东西,保证后面使用顺畅

在开发管理中将自己调用的公网ip配置进去

在这里插入图片描述

在权限管理中把个人权限和通讯录权限进行申请授权,我的设置是全部员工,然后把全部申请授权

在这里插入图片描述
在这里插入图片描述

开发集成

这里我采用的是springboot进行开发,官方推荐的是maven来进行构建,但是我们使用的是gradle开发,这里我把两种的都列出来

maven

1
2
3
4
5
<dependency>
<groupId>com.aliyun</groupId>
<artifactId>alibaba-dingtalk-service-sdk</artifactId>
<version>2.0.0</version>
</dependency>

gradle

1
implementation 'com.aliyun:alibaba-dingtalk-service-sdk:2.0.0'

然后在application.yml配置文件中配置好之前保存的AppKey和AppSecret

1
2
3
4
#钉钉开放平台
dingTalk:
appkey: AppKey
appSecret: AppSecret

获取token工具类

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
/**
* 获取access_token工具类
*/
@Slf4j
@Component
public class AccessTokenUtil {

//钉钉开发平台配置appkey
public static String APP_KEY;

//钉钉开发平台配置appsecret
public static String APP_SECRET;

@Value("${dingTalk.appkey}")
public void setAppKey(String appKey){
AccessTokenUtil.APP_KEY = appKey;
}

@Value("${dingTalk.appSecret}")
public void setAppSecret(String appSecret){
AccessTokenUtil.APP_SECRET = appSecret;
}

/**
* 钉钉网关gettoken地址
*/
public static final String URL_GET_TOKKEN = "https://oapi.dingtalk.com/gettoken";

public static String getToken() throws RuntimeException {
try {
DefaultDingTalkClient client = new DefaultDingTalkClient(URL_GET_TOKKEN);
OapiGettokenRequest request = new OapiGettokenRequest();

request.setAppkey(APP_KEY);
request.setAppsecret(APP_SECRET);
request.setHttpMethod("GET");
OapiGettokenResponse response = client.execute(request);
String accessToken = response.getAccessToken();
return accessToken;
} catch (ApiException e) {
log.error("getAccessToken failed", e);
throw new RuntimeException();
}

}

public static void main(String[] args)throws ApiException{
String accessToken = AccessTokenUtil.getToken();
System.out.println(accessToken);
}
}

然后写一个接口测试

1
2
3
4
5
6
7
8
9
10
11
12
13
@Resource
private DingTalkService dingTalkService;


/**
* 钉钉免密登录
* @param authCode authCode码
* @return
*/
@GetMapping("/login")
public Result dingLogin(@RequestParam("authCode") String authCode){
return Result.success(dingTalkService.dingLogin(authCode));
}

在service中处理

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
	public static final String URL_GET_USER_INFO = "https://oapi.dingtalk.com/user/getuserinfo";

/**
* 获取用户信息的接口
*/
public static final String URL_USERINFO_GET = "https://oapi.dingtalk.com/topapi/v2/user/get";


public Object dingLogin(String authCode) {
//获取accessToken,注意正是代码要有异常流处理
String token = AccessTokenUtil.getToken();

//获取用户信息
DefaultDingTalkClient client = new DefaultDingTalkClient(URL_GET_USER_INFO);
OapiUserGetuserinfoRequest request = new OapiUserGetuserinfoRequest();
request.setCode(authCode);
request.setHttpMethod("GET");

OapiUserGetuserinfoResponse response;
try {
response = client.execute(request, token);
//当前用户id
String userId = response.getUserid();
OapiV2UserGetResponse userInfoResp = getUserInfo(token, userId);
OapiV2UserGetResponse.UserGetResponse result = userInfoResp.getResult();
//拿到用户信息之后进行业务处理,这里我是通过unionid和数据库中用户的unionid进行匹配,然后再走我们自己的登录逻辑

} catch (Exception e) {
e.printStackTrace();
}
}

public OapiV2UserGetResponse getUserInfo(String access_token, String userId){

try {
DingTalkClient client = new DefaultDingTalkClient(URL_USERINFO_GET);
OapiV2UserGetRequest req = new OapiV2UserGetRequest();
req.setUserid(userId);
req.setLanguage("zh_CN");
OapiV2UserGetResponse rsp = null;
rsp = client.execute(req, access_token);
System.out.println(rsp.getBody());
return rsp;
} catch (ApiException e) {
e.printStackTrace();
return null;
}
}

上面返回的Result是自定义封装的一个返回实体,可以根据情况替换成自己的返回类型,大概的流程就是如此,前端获取authcode码之后请求接口,这边再访问钉钉的api接口,通过token和code码获取到用户的信息,然后就可以根据自己系统的业务进行相关的登录判断操作,整个过程还是挺简单的,只要把准备工作做好还是比较顺畅

SpringBoot钉钉通讯录信息同步
青城山游
© 2019-2024 Fueen
Powered by hexo