wx.login请求服务器返回数据data,获取session_key和openid
发布于 1 年前 作者 mintang 875 次浏览 来自 分享

小程序端代码:

wx.login({

success: res => {

if (res.code) {

//let URL = 'https://api.weixin.qq.com/sns/jscode2session?appid=aaaaaaaa&secret=aaaaaaaaaaaaaaaa&js_code='+res.code+'&grant_type=authorization_code' // 这个url在服务器端代码调用

//http://10.221.129.198:8080/request?type=100

let URL = 'http://10.221.129.198:8080/request?login_code='+res.code

console.log(URL)

wx.request({

url: URL ,

timeout: 100000,

success:function(res){

//res.data中有openid

console.log(res)

console.log('login request success')

fail: function (res) {

console.log(res)

console.log('login request failed')

fail: function (res) {

console.log('login failed')

console.log(res)


服务器端代码:

[@Controller](/user/Controller)

public class ServerController {

[@RequestMapping](/user/RequestMapping)(value = "/request")

public [@ResponseBody](/user/ResponseBody)

String request([@RequestParam](/user/RequestParam)(value="login_code") String code) {

String res = null;

if ( !code.equals(' ') ) {

// 向微信申请获取用户id信息

// https://api.weixin.qq.com/sns/jscode2session?

// appid=aaaaaaaaaaaaaaaa&secret=aaaaaaaaaaaaaaaa

// js_code=code

// &grant_type=authorization_code

String str_url = "https://api.weixin.qq.com/sns/jscode2session?appid=aaaaaaaaaaaaa&secret=bbbbbbbbbbbbbb&js_code='+code+'&grant_type=authorization_code";

InputStream in = null;

OutputStream out = null;

try {

URL url = new URL(str_url);

HttpURLConnection connection = (HttpURLConnection) url.openConnection();

connection.setRequestProperty("User-Agent","Mozilla/4.0 (compatible; MSIE 5.0; Windows NT; DigExt)");

in = new BufferedInputStream(connection.getInputStream());

out = new BufferedOutputStream(new FileOutputStream("/home/lys/package-app-NewHomeService/login.txt", true));

byte[] bytes = new byte[1024];

int len = 0;

if((len = in.read(bytes)) != -1) {

res = bytes.toString();

} catch (MalformedURLException e) {

e.printStackTrace();

} catch (IOException e) {

e.printStackTrace();

// HttpServletRequest request = null;

// HttpServletResponse response = null;

} else {

res = "request value error!";

return res;


小程序端返回的res最后打印出来的数据:和服务器端断点看到的url返回值一样

{data: "null[B[@c35210c](/user/c35210c)", header: {…}, statusCode: 200, cookies: Array(0), errMsg: "request:ok"}cookies: []

data: "null[B[@c35210c](/user/c35210c)"

errMsg: "request:ok"

header: Connection: "keep-alive"Content-Length: "14"Content-Type: "text/plain;charset=UTF-8"Date: "Thu, 23 Feb 2023 09:39:00 GMT"Keep-Alive: "timeout=60"

__proto__: ObjectstatusCode: 200__proto__: Object

login request success

login调用期间,小程序没用弹出确认登陆的弹窗,data: "null[B[@c35210c](/user/c35210c)"是乱码。


----------------------------------------



以上代码需要修改,修改如下:

(看到有人说:服务端curl证书验证关闭就好了 true=>false,没试,感觉配置ssl还挺麻烦的,目测应该是不需要)


上文的url错误,="+code+"会被直接拼接到字符串,要改成

String string = "https://api.weixin.qq.com/sns/jscode2session?appid=xxx&secret=xxx&js_code="+code+"&grant_type=authorization_code";

URL url = new URL(string);


用户通过login()方法获取code,然后把code传给开发后台,后台通过code 以及appid以及密钥获取openid和sessionkey 进行登陆,然后返回一个token给前端,



目前直接在浏览器访问网页,肉眼可见返回值是json,{"session_key":"R+DEI9Q9xxxxxaMS\/gdnQ==","openid":"o4LDU5Rbyxxxxxmp6JVbuZg"}这样子,或者{"errcode":40163,"errmsg":"code been used, rid: 63f7638f-5cfd2279-5802ec1a"}

小程序端console输出res是data: "null[B[@c35210c](/user/c35210c)",应该是正确的返回值,但是数据格式转换有问题。


但是我用idea搭建的服务器没用jsonobject,只有jsonpobject,没办法直接转成json数据,就很迷现在,等解决了再来改评论

63f7638f-5cfd2279-5802ec1a和c35210c每次重新刷新网页或重新申请都会变,应该也是临时数据吧

----

byte[] request([@RequestParam](/user/RequestParam)(value="login_code") String code) {

byte[] res = null;

.....

byte[] bytes = new byte[1024];

if ((len = in.read(bytes)) != -1) {

断点调试打印byte[] bytes,发现为ascii码数组,对照ascii转换后发现是session_key和openid

// bytes = 123 34 115s 101e 115s 115s 105i 111o 110n 95_ 107k 101e 121y... == {"sessi.....

// ascii: {"session_key":"lV+hmiQWeFYzOl\/WspCamw==","openid":"o4LDU5Rbyoz6HvMpIyNmp6JVbuZg"}

res = bytes;

return res;

前端不能正确获取数据,是因为服务器不能直接将字符数组转换成字符串,bytes.toString()是有问题的,所以将服务端请求返回值类型改成字符数组,直接返回给前端处理,由前端将字符数组类型转换为json类型

至此,前端可以成功拿到session_key和openid


回到顶部