| | |
| | | builder.append("&response_type=code"); |
| | | // 应用授权作用域。 |
| | | // snsapi_base:静默授权,可获取成员的的基础信息(UserId与DeviceId); |
| | | //builder.append("&scope=snsapi_base"); |
| | | builder.append("&scope=snsapi_privateinfo"); // 手动授权作用域 |
| | | builder.append("&scope=snsapi_base");//静默授权 |
| | | //builder.append("&scope=snsapi_privateinfo"); // 手动授权作用域 |
| | | // 重定向后会带上state参数,长度不可超过128个字节 |
| | | builder.append("&state=").append(state); |
| | | builder.append("&agentid=").append(config.getAgentId()); // 补充AgentID |
| | | //builder.append("&agentid=").append(config.getAgentId()); // 补充AgentID(手动授权时需要) |
| | | // 终端使用此参数判断是否需要带上身份信息 |
| | | builder.append("#wechat_redirect"); |
| | | url = builder.toString(); |
| | |
| | | } |
| | | } |
| | | |
| | | //企业微信适配手动授权接口调整 |
| | | ///** |
| | | // * 企业微信/钉钉 OAuth2登录回调 |
| | | // * |
| | | // * @param code |
| | | // * @param state |
| | | // * @param response |
| | | // * @return |
| | | // */ |
| | | //@ResponseBody |
| | | //@GetMapping("/oauth2/{source}/callback") |
| | | //public String oauth2LoginCallback( |
| | | // @PathVariable("source") String source, |
| | | // // 企业微信返回的code |
| | | // @RequestParam(value = "code", required = false) String code, |
| | | // // 钉钉返回的code |
| | | // @RequestParam(value = "authCode", required = false) String authCode, |
| | | // @RequestParam("state") String state, |
| | | // @RequestParam(value = "is_reject", required = false) String isReject, |
| | | // HttpServletResponse response) { |
| | | // SysUser loginUser; |
| | | // if (ThirdAppConfig.WECHAT_ENTERPRISE.equalsIgnoreCase(source)) { |
| | | // log.info("【企业微信】OAuth2登录进入callback:code=" + code + ", state=" + state); |
| | | // // 1. 判定用户拒绝授权的3种场景: |
| | | // // - 场景1:is_reject=true(企业微信明确标识拒绝) |
| | | // // - 场景2:code为null(未返回有效授权凭证) |
| | | // // - 场景3:code存在但无效(调用API失败) |
| | | // boolean isUserReject = "true".equals(isReject) || code == null; |
| | | // if (isUserReject) { |
| | | // log.info("用户明确拒绝企业微信授权(is_reject={}, code={}", isReject, code); |
| | | // // 构造含error=access_denied的重定向地址,前端据此识别 |
| | | // String errorRedirect = buildErrorRedirect(state, "access_denied"); |
| | | // try { |
| | | // response.sendRedirect(errorRedirect); |
| | | // return "用户拒绝授权,已重定向"; |
| | | // } catch (IOException e) { |
| | | // log.error("拒绝授权重定向失败", e); |
| | | // return "重定向失败"; |
| | | // } |
| | | // } |
| | | // |
| | | // // 2. 尝试用code获取用户信息(code存在但可能无效) |
| | | // loginUser = thirdAppWechatEnterpriseService.oauth2Login(code); |
| | | // if (loginUser == null) { |
| | | // log.info("企业微信授权失败(code无效)"); |
| | | // String errorRedirect = buildErrorRedirect(state, "invalid_code"); |
| | | // try { |
| | | // response.sendRedirect(errorRedirect); |
| | | // return "授权失败,已重定向"; |
| | | // } catch (IOException e) { |
| | | // log.error("授权失败重定向失败", e); |
| | | // return "重定向失败"; |
| | | // } |
| | | // } |
| | | // loginUser = thirdAppWechatEnterpriseService.oauth2Login(code); |
| | | // if (loginUser == null) { |
| | | // return "登录失败"; |
| | | // } |
| | | // } else if (ThirdAppConfig.DINGTALK.equalsIgnoreCase(source)) { |
| | | // log.info("【钉钉】OAuth2登录进入callback:authCode=" + authCode + ", state=" + state); |
| | | // loginUser = thirdAppDingtalkService.oauth2Login(authCode); |
| | | // if (loginUser == null) { |
| | | // return "登录失败"; |
| | | // } |
| | | // } else { |
| | | // return "不支持的source"; |
| | | // } |
| | | // try { |
| | | // |
| | | // //update-begin-author:taoyan date:2022-6-30 for: 工作流发送消息 点击消息链接跳转办理页面 |
| | | // String redirect = ""; |
| | | // if (state.indexOf("?") > 0) { |
| | | // String[] arr = state.split("\\?"); |
| | | // state = arr[0]; |
| | | // if(arr.length>1){ |
| | | // redirect = arr[1]; |
| | | // } |
| | | // } |
| | | // |
| | | // String token = saveToken(loginUser); |
| | | // // ============ 新增 Shiro 登录逻辑 ============ |
| | | // JwtToken jwtToken = new JwtToken(token); |
| | | // SecurityUtils.getSubject().login(jwtToken); |
| | | // state += "/h5/oauth2-app/login?oauth2LoginToken=" + URLEncoder.encode(token, "UTF-8"); |
| | | // //update-begin---author:wangshuai ---date:20220613 for:[issues/I5BOUF]oauth2 钉钉无法登录------------ |
| | | // state += "&thirdType=" + source; |
| | | // //state += "&thirdType=" + "wechat_enterprise"; |
| | | // if (redirect != null && redirect.length() > 0) { |
| | | // state += "&" + redirect; |
| | | // } |
| | | // //update-end-author:taoyan date:2022-6-30 for: 工作流发送消息 点击消息链接跳转办理页面 |
| | | // |
| | | // //update-end---author:wangshuai ---date:20220613 for:[issues/I5BOUF]oauth2 钉钉无法登录------------ |
| | | // log.info("OAuth2登录重定向地址: " + state); |
| | | // try { |
| | | // response.sendRedirect(state); |
| | | // return "ok"; |
| | | // } catch (IOException e) { |
| | | // e.printStackTrace(); |
| | | // return "重定向失败"; |
| | | // } |
| | | // } catch (UnsupportedEncodingException e) { |
| | | // e.printStackTrace(); |
| | | // return "解码失败"; |
| | | // } |
| | | //} |
| | | // |
| | | ///** |
| | | // * 构造企业微信授权拒绝时的错误重定向地址 |
| | | // * 适配规则:state参数长度≤128字节,保留原始业务参数,附加error标识 |
| | | // */ |
| | | //private String buildErrorRedirect(String originalState, String errorCode) { |
| | | // // 1. 拆分原始state中的基础路径和业务参数(避免破坏原有state结构) |
| | | // String baseState = originalState; |
| | | // String businessParams = ""; |
| | | // if (originalState.contains("?")) { |
| | | // String[] stateParts = originalState.split("\\?", 2); // 只拆分成两部分 |
| | | // baseState = stateParts[0]; // 基础路径(如https://fastwoke.cn:8087) |
| | | // businessParams = stateParts[1]; // 原始业务参数(如redirect=xxx) |
| | | // } |
| | | // |
| | | // // 2. 构造错误参数(error=xxx),并拼接原始业务参数 |
| | | // StringBuilder errorParams = new StringBuilder(); |
| | | // errorParams.append("error=").append(errorCode); // 核心错误标识 |
| | | // if (!businessParams.isEmpty()) { |
| | | // errorParams.append("&").append(businessParams); // 附加原始业务参数 |
| | | // } |
| | | // |
| | | // // 3. 拼接完整的重定向地址(格式:baseState/h5/oauth2-app/login?errorParams) |
| | | // // 注意:企业微信要求重定向地址需与授权链接中的redirect_uri域名一致 |
| | | // StringBuilder errorRedirect = new StringBuilder(baseState); |
| | | // errorRedirect.append("/h5/oauth2-app/login?").append(errorParams); |
| | | // |
| | | // // 4. 校验state长度(企业微信限制≤128字节),超长时截断非关键参数 |
| | | // String redirectUrl = errorRedirect.toString(); |
| | | // if (redirectUrl.getBytes().length > 128) { |
| | | // log.warn("错误重定向地址超长,截断处理: {}", redirectUrl); |
| | | // // 只保留基础路径和error参数,舍弃其他业务参数 |
| | | // redirectUrl = baseState + "/h5/oauth2-app/login?error=" + errorCode; |
| | | // } |
| | | // |
| | | // log.info("企业微信拒绝授权重定向地址: {}", redirectUrl); |
| | | // return redirectUrl; |
| | | //} |
| | | |
| | | } |