justauth/JustAuth · error · AuthException
${errmsg}
Error message
${errmsg} What it means
AbstractAuthDingtalkRequest.getUserInfo posts the tmp_auth_code to https://oapi.dingtalk.com/sns/getuserinfo_bycode and checks the errcode field. Any non-zero errcode (plus errmsg) is rethrown as an AuthException carrying DingTalk's own message. Common codes: invalid/expired tmp_auth_code, signature problems, or wrong appId/appSecret on the qs/sns side.
Source
Thrown at src/main/java/me/zhyd/oauth/request/AbstractAuthDingtalkRequest.java:49
public AbstractAuthDingtalkRequest(AuthConfig config, AuthSource source, AuthStateCache authStateCache) {
super(config, source, authStateCache);
}
@Override
public AuthToken getAccessToken(AuthCallback authCallback) {
return AuthToken.builder().accessCode(authCallback.getCode()).build();
}
@Override
public AuthUser getUserInfo(AuthToken authToken) {
String code = authToken.getAccessCode();
JSONObject param = new JSONObject();
param.put("tmp_auth_code", code);
String response = new HttpUtils(config.getHttpConfig()).post(userInfoUrl(authToken), param.toJSONString()).getBody();
JSONObject object = JSON.parseObject(response);
if (object.getIntValue("errcode") != 0) {
throw new AuthException(object.getString("errmsg"));
}
object = object.getJSONObject("user_info");
AuthToken token = AuthToken.builder()
.openId(object.getString("openid"))
.unionId(object.getString("unionid"))
.build();
return AuthUser.builder()
.rawUserInfo(object)
.uuid(object.getString("unionid"))
.nickname(object.getString("nick"))
.username(object.getString("nick"))
.gender(AuthUserGender.UNKNOWN)
.source(source.toString())
.token(token)
.build();
}
/**View on GitHub (pinned to 694bbf1b01)
Solutions
- Exchange the tmp_auth_code immediately upon callback — it is one-time and expires within minutes; do not retry with the same code.
- Verify the DingTalk scan-login app's appId/appSecret in AuthConfig match the app created in the DingTalk open platform.
- Log the raw response before parsing to capture the exact errcode; handle errcode by re-prompting the QR scan when the code is invalid.
- If the message mentions signature, prefer the DingTalk-signed request variants (AuthDingTalkRequest with sdk-based signing) instead of the raw POST.
Example fix
// before
// callback endpoint retries on failure with the same code -> errmsg 'code been used'
// after
// process the callback exactly once, store the result, and on AuthException re-run the QR flow:
try { return request.login(callback); }
catch (AuthException e) { log.warn("dingtalk login failed: {}", e.getMessage()); return restartScanLogin(); } Defensive patterns
Strategy: try-catch
Validate before calling
if (StringUtils.isEmpty(callback.getCode())) { throw new IllegalArgumentException("DingTalk callback missing code"); } Try / catch
try { return request.login(callback); } catch (AuthException e) { log.warn("DingTalk userinfo errcode: {}", e.getMessage()); return restartQrLogin(); } Prevention
- Exchange the DingTalk tmp_auth_code exactly once, immediately on callback.
- Store the login result keyed by code so retries do not re-consume it.
- Verify scan-login appId/secret match the DingTalk open platform app.
- Log the raw DingTalk response for errcode diagnosis.
When it happens
Trigger: Calling login() or getUserInfo() where the code is stale (tmp_auth_code is single-use and short-lived), was already consumed, or the DingTalk app credentials are wrong; clock skew or network proxies mangling the POST body.
Common situations: User sits on the callback page before the server processes it and the code expires; retrying the callback (idempotency issue) reuses a consumed code; wrong appId/secret configured for the scan-login app; DingTalk API changes to getuserinfo_bycode (which historically required a signature).
Related errors
AI-assisted analysis of justauth/JustAuth@694bbf1b01 (2026-08-14).
Data as JSON: /api/errors/851318b2881fcfbd.
Report an issue: GitHub.