• 微信公众号授权回调用户信息,获取openid


    1.--------------------用户授权登录并获取code

    授权登录方式有两个,一种为静默授权登录(scope=snsapi_base),一种为非静默授权登录(scope=snsapi_userinfo),区别为静默授权是静默授权并自动跳转到回调页的。用户感知的就是直接进入了回调页(往往是业务页面)特点:用户无感知,但是只能获取到用户的唯一标示openid和union id,无法拿到用户的微信头像、微信名称等个人信息;非静默授权这种授权需要用户手动同意,并且由于用户同意过,所以无须关注,就可在授权后获取该用户的基本信息。

    如果用户同意授权,页面将跳转至 redirect_uri并且携带"?code=CODE&state=STATE"

    2.-----------------使用第一步获得的code换取access_token

    参数说明
    appid=APPID(公众号唯一标识)
    secret=SECRET(公众号的appsecret)
    code=CODE(第一步获取的code参数)
    grant_type=authorization_code(无需更改)

    返回结果(json格式数据)
    {
    "access_token": "e1nYJFpZuehfQH1buzHFZLb7onqs_wT1cudSdy9HRlnaMXFtFpRMNFOA0euK6UxPcItrSNbAQVcXDdthbLJYX0MdH1p7-tkZSKuGqBCxVc0",
    "expires_in": 7200,
    "refresh_token": "0iVsXn4O1rBCASbO7hx8VNVUVFM1RP2Q4xS0giegd4jlIsJYOjTJNZ0b4Dsh_xcoB02ZZ3bt0WH0a47LvjIEPjWUnESJCZyl6EtY_xYZdVs",
    "openid": "o47Fa0mp9SRTf3eiKmqWm69BjG_8",
    "scope": "snsapi_userinfo"
    }

    结果解释
    access_token 网页授权接口调用凭证,注意:此access_token与基础支持的access_token不同
    expires_in access_token接口调用凭证超时时间,单位(秒)
    refresh_token 用户刷新access_token
    openid 用户唯一标识,请注意,在未关注公众号时,用户访问公众号的网页,也会产生一个用户和公众号唯一的OpenID
    scope 用户授权的作用域,使用逗号(,)分隔

    3.-----------------使用access_token获取用户信息

    -------详情参照微信官方文档,下面贴整合代码 

    @RequestMapping(value = "/AuthorizationGetUserInfo.json", produces = "application/json;charset=utf-8", method = RequestMethod.GET)
    @ResponseBody
    public void AuthorizationGetUserInfo(HttpSession session, HttpServletResponse resp, String code) throws IOException{
            if(code == null){
                log.info("code为空===");
            }
            String url = " https://api.weixin.qq.com/sns/oauth2/access_token";
            String access_tokenUrl = "appid=appid" + "&secret=secret" + "&code=" + code + "&grant_type=authorization_code";//通过code换取网页授权access_token路径
            String result = HttpRequest.sendGet(url, access_tokenUrl);
            Map<String, String> map = WXPayUtil.MapConversion(result);
            String access_token = map.get("access_token");
            String openid = map.get("openid");
            String surl = "https://api.weixin.qq.com/sns/userinfo";
            String userinfoUrl = "access_token=" + access_token + "&openid=" + openid + "&lang=zh_CN";
            String sresult = HttpRequest.sendGet(surl, userinfoUrl);
            Map<String, String> userinfoMap = WXPayUtil.MapConversion(sresult);  //标准json格式的String转json
            String str = userinfoMap.get("nickname");
            try {
                userinfoMap.put("nickname", EmojiUtil.resolveToByteFromEmoji(str));
                log.info("用户头像表情转化成字符" + userinfoMap.get("nickname"));
    
            } catch (Exception e) {
                log.info("用户信息拉取失败=========================");
                log.info("用户信息拉取失败=========================" + e.getMessage());
            }
            String suOpenid = vipMapperService.ByOpenIdQueVip(openid);//查询用户表中的openid
            log.info("session的ID" + session.getId());
            if (suOpenid != null && suOpenid != "") {
                User user = vipMapperService.selectVipInfo(userinfoMap);
    
                if (!user.getUuser().equals(userinfoMap.get("nickname"))) {
                    userinfoMap.put("nickname", user.getUuser());//修改为新的昵称
                }
                if (!user.getHeadimgurl().equals(userinfoMap.get("headimgurl"))) {
                    userinfoMap.put("headimgurl", user.getHeadimgurl());//修改为新的头像
                }
                    Integer Upresult = vipMapperService.ByWXUpVip(userinfoMap);//修改会员
                if (Upresult < 0) {
                    log.info("修改会员失败了!");
                }
            } else {
                //该openid用户表中不存在,新增用户
                Integer Addresult = vipMapperService.AddVip(userinfoMap);
                if (Addresult < 0) {
                    log.info("新增会员失败了===!");
                }
            }
                Integer Uid = vipMapperService.ByOpenIdQuUid(openid);
                Cookie cookie = new Cookie("Uid", String.valueOf(Uid));
                resp.addCookie(cookie);
                resp.sendRedirect(NowData.PROTOCOL + NowData.DOMAIN + "/WeChatpn/index.html#/mall");
        }
    ---------------------------------utils
    /**
     * 向指定URL发送GET方法的请求
     * 
     * @param url
     *            发送请求的URL
     * @param param
     *            请求参数,请求参数应该是 name1=value1&name2=value2 的形式。
     * @return URL 所代表远程资源的响应结果
     */
    public static String sendGet(String url, String param) {
       String result = "";
       BufferedReader in = null;
       try {
          String urlNameString = url + "?" + param;
          URL realUrl = new URL(urlNameString);
          // 打开和URL之间的连接
          URLConnection connection = realUrl.openConnection();
          // 设置通用的请求属性
          connection.setRequestProperty("accept", "*/*");
          connection.setRequestProperty("connection", "Keep-Alive");
          connection.setRequestProperty("user-agent", "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1;SV1)");
          // 建立实际的连接
          connection.connect();
          // 获取所有响应头字段
          Map<String, List<String>> map = connection.getHeaderFields();
          // 遍历所有的响应头字段
          for (String key : map.keySet()) {
             //System.out.println(key + "--->" + map.get(key));
          }
          // 定义 BufferedReader输入流来读取URL的响应
          in = new BufferedReader(new InputStreamReader(connection.getInputStream()));
          String line;
          while ((line = in.readLine()) != null) {
             result += line;
          }
       } catch (Exception e) {
          System.out.println("发送GET请求出现异常!" + e);
          e.printStackTrace();
       }
       // 使用finally块来关闭输入流
       finally {
          try {
             if (in != null) {
                in.close();
             }
          } catch (Exception e2) {
             e2.printStackTrace();
          }
       }
       return result;
    }
    /**
     * String转Map<String, String>
     * map
     *
     * @return
     */
    public static Map<String, String> MapConversion(String str) {
        Map<String, Object> map = JSON.parseObject(str);
        Map<String, String> NewMap = new HashMap<String, String>();
        for (String string : map.keySet()) {
            NewMap.put(string, map.get(string).toString());
        }
        return NewMap;
    }
    /**
     * 利用正则表达式判断str是否存在表情字符
     * @param str
     * @return
     */
    public static String resolveToByteFromEmoji(String str) {
       Pattern pattern = Pattern
             .compile("[^(u2E80-u9FFF\w\s`~!@#\$%\^&\*\(\)_+-?()——=\[\]{}\|;。,、《》”:;“!……’:‘"<,>\.?/\\*)]");
       Matcher matcher = pattern.matcher(str);
       StringBuffer sb2 = new StringBuffer();
       while (matcher.find()) {
          matcher.appendReplacement(sb2, encode(matcher.group(0)));
       }
       matcher.appendTail(sb2);
       //将分隔符 替换成 得到的内容就是 u1245
       return sb2.toString().replace("&ns;","\");
    }
    境随心转而悦,心随境转而烦
  • 相关阅读:
    JavaScript之判断参数的数值的详细类型
    JavaScript之不规则Table转化为可定点索引td节点的网格矩阵【插件】
    JavaScript之从浏览器一键获取教务处个人课程信息【插件】
    Linux之搭建远程数据库MySQL[Ubuntu:全过程]
    数据库之MySQL ERROR 1698 (28000) 错误:Access denied for user 'root'@'localhost'" error【摘抄】
    Linux之常用命令【service】
    Linux之激活超级用户
    计算机网络之互联网|因特网|万维网|HTTP|HTML之间的关系辨析
    [转] Linux Shell 文本处理工具集锦
    可读写的缓冲设计表现
  • 原文地址:https://www.cnblogs.com/tomingto/p/11281314.html
Copyright © 2020-2023  润新知