{"record":{"id":"8e991362d5296113","repo":"apache/shenyu","slug":"token-is-error","errorCode":null,"errorMessage":"token is error.","messagePattern":"token is error\\.","errorType":"exception","errorClass":"AuthenticationException","httpStatus":401,"severity":"error","filePath":"shenyu-admin/src/main/java/org/apache/shenyu/admin/shiro/config/ShiroRealm.java","lineNumber":120,"sourceCode":"            throw new AuthenticationException(\"userName is null\");\n        }\n\n        DashboardUserVO dashboardUserVO = dashboardUserService.findByUserName(userName);\n        if (Objects.isNull(dashboardUserVO)) {\n            throw new AuthenticationException(String.format(\"userName(%s) can not be found.\", userName));\n        }\n        if (!Boolean.TRUE.equals(dashboardUserVO.getEnabled())) {\n            throw new AuthenticationException(String.format(\"user(%s) is disabled.\", userName));\n        }\n        String clientIdFromToken = JwtUtils.getClientId(token);\n        if (StringUtils.isNotEmpty(clientIdFromToken)\n                && StringUtils.isNotEmpty(dashboardUserVO.getClientId())\n                && !StringUtils.equals(dashboardUserVO.getClientId(), clientIdFromToken)) {\n            throw new AuthenticationException(\"clientId is invalid or does not match\");\n        }\n\n        if (!JwtUtils.verifyToken(token, jwtProperties.getSecretKey())) {\n            throw new AuthenticationException(\"token is error.\");\n        }\n\n        return new SimpleAuthenticationInfo(UserInfo.builder()\n                .userName(userName)\n                .userId(dashboardUserVO.getId())\n                .build(), token, this.getName());\n    }\n}\n","sourceCodeStart":102,"sourceCodeEnd":129,"githubUrl":"https://github.com/apache/shenyu/blob/567142e07261b3e615ae8850b30f4421f455cc5d/shenyu-admin/src/main/java/org/apache/shenyu/admin/shiro/config/ShiroRealm.java#L102-L129","documentation":"Final step of ShiroRealm authentication: JwtUtils.verifyToken(token, jwtProperties.getSecretKey()) returned false, so the JWT signature/timestamp does not validate against the configured secret key and 'token is error.' is thrown.","triggerScenarios":"Token expired, signature tampered, or token signed with a different secret than shenyu.jwt.secret-key configured on the admin; also tokens carried over between deployments where the JWT key changed.","commonSituations":"JWT secret changed or different across admin replicas after config update; clock skew making an unexpired-looking token verify as expired; copy-pasted token truncated; default secret mismatch between environments.","solutions":["Re-login to obtain a fresh token","Verify shenyu.jwt.secret-key (jwtProperties) is identical across all admin instances and unchanged since the token was issued","Decode the JWT and check the exp claim; discard expired tokens client-side","Ensure the token is transmitted intact (no truncation, correct Authorization header format)"],"exampleFix":"// before (application.yml)\nshenyu:\n  jwt:\n    secret-key: dev-only-key\n// after — align key across environments/replicas\nshenyu:\n  jwt:\n    secret-key: ${JWT_SECRET_KEY}","handlingStrategy":"try-catch","validationCode":"// client-side expiry check before calling\nboolean notExpired = parseClaims(token).exp * 1000L > System.currentTimeMillis();","typeGuard":"boolean isWellFormedJwt(String t) { return t != null && t.split(\"\\\\.\").length == 3; }","tryCatchPattern":"try { call(token); } catch (AuthenticationException e) { if (\"token is error.\".equals(e.getMessage())) { token = relogin(); retryOnce(); } }","preventionTips":["Keep shenyu.jwt.secret-key identical and stable across admin instances","Rotate the secret only together with forced re-login of all clients","Check exp claim and refresh the token before it expires","Avoid copy/paste truncation of tokens in scripts"],"tags":["jwt","token-verification","authentication","admin"],"backgroundTag":"jwt-token-expired","analyzedSha":"567142e07261b3e615ae8850b30f4421f455cc5d","analyzedAt":"2026-09-12T10:08:21.293Z","contentChangedAt":"2026-09-12T10:08:21.293Z","schemaVersion":2},"datasetVersion":"2026-09-16T04:17:20.429Z"}