使用码上登录实现微信扫码登录

现如今使用微信的人越来越多,很多网站都实现了让用户直接扫码就能登录网站,正是这种方式给用户带来了极多的好处,最重要的是用户不用担心自己总记不住账户密码,从而登录不了网站。

为了方便用户登录,我也想接入微信扫码登录。但因为微信开发者需要企业认证,所以没办法接入个人网站实现微信扫码登录。最近我发现了一个小程序“码上登录”,对个人开发者提供了免费的微信扫一扫登录入口,其实就是一个桥接入口,为我们去获取用户扫码之后的信息,从而在发给我们,我们接收再返回信息即可。

好了,撸起袖子直接干吧!

准备工作

在码上登录注册,然后创建自己的应用并指定回调地址,会生成一个secretKey,后面获取二维码链接用得到

 

微信登录时序图

首先我们向码上登录的服务器发送请求获取二维码信息,然后用户扫码,用户跳转到登录的小程序,用户点击登录,授权,码上登录服务器向自己的服务器回调入口返回数据,然后我们返回登录状态信息。

后台开发

向码上登录服务器发送请求,返回二维码数据信息

secretKey(即我们创建应用时生成的secretKey)调用码上登录服务器时候需要进行验证的凭据
@FeignClient(name = "wx", url = "https://server01.vicy.cn")
public interface UserFeignClient {

    /**
     * 向码上登录服务器请求二维码
     */
    @GetMapping(value = "/8lXdSX7FSMykbl9nFDWESdc6zfouSAEz/wxLogin/tempUserId")
    String getQrCode(@RequestParam(required = true, value = "secretKey") String secretKey);

}

@FeignClient标签的常用属性如下:

  • name:指定FeignClient的名称,如果项目使用了Ribbon,name属性会作为微服务的名称,用于服务发现
  • url: url一般用于调试,可以手动指定@FeignClient调用的地址
  • decode404:当发生http 404错误时,如果该字段位true,会调用decoder进行解码,否则抛出FeignException
  • configuration: Feign配置类,可以自定义Feign的Encoder、Decoder、LogLevel、Contract
  • fallback: 定义容错的处理类,当调用远程接口失败或超时时,会调用对应接口的容错逻辑,fallback指定的类必须实现@FeignClient标记的接口
  • fallbackFactory: 工厂类,用于生成fallback类示例,通过这个属性我们可以实现每个接口通用的容错逻辑,减少重复的代码
  • path: 定义当前FeignClient的统一前缀

发送请求

获取登录二维码信息

@Value(value = "${justAuth.clientSecret.wechat}")
private String wechatClientSecret;

@ApiOperation(value = "获取码上登录微信二维码链接", notes = "获取码上登录微信二维码链接")
    @GetMapping("/getWechatQrCodeReturnUrl")
    public String getWechatQrCodeReturnUrl () {
        // 将传递过来的转换成大写
        String source = SysConf.WECHAT;
        Boolean isOpenLoginType = webConfigService.isOpenLoginType(source.toUpperCase());
        if (!isOpenLoginType) {
            return ResultUtil.result(SysConf.ERROR, "后台未开启该登录方式!");
        }
        return ResultUtil.result(SysConf.SUCCESS,userService.getWechatQrCodeReturnUrl(wechatClientSecret));
    }

实现类


@Service
public class UserServiceImpl implements UserService {
    @Resource
    private UserFeignClient userFeignClient;

    @Override
    public String getWechatQrCodeReturnUrl(String wechatClientSecret) {

        String result = userFeignClient.getQrCode(wechatClientSecret);
        return result;
    }
}

返回数据

{"errcode":0,"data":{"qrCodeReturnUrl":"http://login.vicy.cn?tempUserId=18d55e78f66848e781bc7ce65a1fe5b4",
"tempUserId":"18d55e78f66848e781bc7ce65a1fe5b4"},"message":"成功"}

errcode:错误码

message:描述信息

data:存放二维码信息集合

        tempUserId:登录会话临时凭证

        qrCodeReturnUrl:发送给前端用于生成二维码

回调地址

@ApiOperation(value = "码上登录回调地址", notes = "码上登录回调地址")
    @PostMapping(value = "/callback")
    public JSONObject backUserScanedInfo(
            @RequestParam(value = "userId",required = false)  String userId,
            @RequestParam(value = "tempUserId",required = false) String tempUserId,
            @RequestParam(value = "nickname",required = false) String nickname,
            @RequestParam(value = "avatar",required = false) String avatar,
            @RequestParam(value = "ipAddr",required = false) String ipAddr,
            HttpServletResponse httpServletResponse) throws IOException {
        log.info("用户信息============\r\n"+ "【userId】"+userId+ " 【tempUserId】 "+tempUserId+ " 【nickname】 "+nickname+ " 【headimgurl】 "+avatar+ " 【ipAddr】"+ipAddr);

        // TODO 写自己的逻辑 保存用户或更新用户信息到数据库

        // 返回状态码
        JSONObject jsonObject = new JSONObject();
        if (userId != null){
            jsonObject.put("errcode",0);
            jsonObject.put("message","success");
        }else {
            jsonObject.put("errcode",1);
            jsonObject.put("message","error");
        }
        return jsonObject;
    }

前端实现

<template>
  <div>
        <div v-if="showPasswordLogin == false" style="text-align: center" class="block">
          <el-image :src="qrcode" style="width: 250px;" id="qrcode" ref="qrCodeUrl">
            <div slot="error" class="image-slot" @click="getWechatQrCodeReturnUrl">
              <i class="el-icon-refresh" style="height: 250px; line-height: 250px; cursor: pointer">点击刷新</i>
            </div>
          </el-image>
        </div>

  </div>
</template>

<script>
import {getWechatQrCodeReturnUrl} from '@/api/user'
import QRCode from "qrcode";
export default {
  name: 'share',
  data () {
    return {
      url: "http://www.baidu.com",  //识别二维码后跳转的地址
      qrcode:'' //存储二维码地址
    }
  },
  components: {},
  created () {
    
  },
  methods: {
    // 获取码上登录返回的数据生成二维码
    getWechatQrCodeReturnUrl: function () {
      let that = this
      getWechatQrCodeReturnUrl().then(response => {
        // eslint-disable-next-line eqeqeq
        if (response.code == this.$ECode.SUCCESS) {
          this.showPasswordLogin = false
          let dataz = JSON.parse(response.data);
          this.url = dataz.data.qrCodeReturnUrl

          QRCode.toDataURL(this.url,{
            version: 7,
            errorCorrectionLevel: 'Q',
            width: 280,
            height: 280,
            margin: 0,
          }).then(url => {
              // console.log(url);
              this.qrcode = url
          }).catch(err => {
              // console.error(err)
          })

          this.tempUserId = dataz.data.tempUserId
          let count = 0
          let interval = setInterval(() => {
            count++
            if (count > 5) {
              this.qrcode = ''
              clearInterval(interval)
            }
            let params = new URLSearchParams()
            params.append('ticket', this.tempUserId)
            getUserLoginStatus(params).then(response => {
              console.log('获取用户登录状态', response)
              if (response.code == that.$ECode.SUCCESS) {
                let token = this.tempUserId
                if (token != undefined) {
                  setCookie('token', token, 7)
                }
                this.setUserInfo(response.data)
                this.setLoginState(true)
                // location.reload()
                // 跳转到首页
                location.replace(this.vueXqCodingWebUrl + '/#/?token=' + token)
                //window.location.reload()
              }
            })
          }, 3000)

        } else {
          this.$message.error(response.message)
        }
      })
    }
  }
}
</script>

效果

 

  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
Spring Boot框架是一种轻量级、开箱即用的Java开发框架,它大大简化了企业级应用的开发过程。要实现微信扫码登录,可以使用Spring Boot框架结合微信开放平台的API来实现。以下是实现微信扫码登录的步骤: 1. 注册微信开放平台账号并创建应用,获取AppID和AppSecret。 2. 创建Spring Boot项目并导入相关依赖,如web、httpclient等。 3. 在配置文件application.properties中配置微信开放平台的AppID和AppSecret。 4. 创建一个控制器,用于处理登录相关的请求。 5. 定义一个生成微信扫码登录链接的方法,该方法使用AppID、重定向URI和state等参数生成微信登录链接。 6. 在控制器中定义一个登录请求的接口,该接口返回生成的微信扫码登录链接。 7. 创建一个回调接口,用于处理微信登录成功后的回调请求。 8. 在回调接口中获取微信的授权code,通过code和AppID、AppSecret等参数向微信服务器发送请求,获取用户的唯一标识openid。 9. 将获取到的openid存储到数据库或Session中,表示用户已登录。 10. 在需要验证用户登录状态的接口中,通过openid验证用户是否已登录。 以上是使用Spring Boot实现微信扫码登录的基本步骤,通过控制器处理登录和回调接口,以及与微信服务器的交互,可以实现用户使用微信扫码登录系统的功能。当然,具体实现中还需要考虑安全性、数据持久化等问题,以及前端页面的设计和展示等方面的内容。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值