1、后端调用方法获取AccessToken的工具类
import com.alibaba.fastjson2.JSON;import com.alibaba.fastjson2.JSONObject;import org.springframework.web.client.RestTemplate;import java.util.Map;public class qrUtils {// private static final String ACCESS_TOKEN_URL = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid={appId}&secret={secret}";; private static final String ACCESS_TOKEN_URL = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid='输入自己的小程序ID'&secret='输入自己的小程序密钥'";; /** * 获取微信的appId的工具类,字符串之后需要JSON.parseObject转化。 * * @param * @param * @return 获取结果 */ public static String getAccessToken() { String accesstoken=new String(); String requestUrl = ACCESS_TOKEN_URL;// //传入参数替换// requestUrl = requestUrl.replaceAll("appId", appId);// requestUrl = requestUrl.replaceAll("secret", secret); //超时,需要重新请求接口 RestTemplate restTemplate = new RestTemplate(); String result = restTemplate.getForObject(requestUrl, String.class); JSONObject jsonObject = JSON.parseObject(result.toString()); accesstoken = jsonObject.getString("access_token"); return result; }}
2、获取完AccessToken后调用微信小程序接口,写一个微信小程序工具类
import com.alibaba.fastjson2.JSON;import com.alibaba.fastjson2.JSONObject;import com.ruoyi.common.core.controller.BaseController;import org.springframework.http.ResponseEntity;import org.springframework.web.client.RestTemplate;import com.ruoyi.*;import java.io.BufferedReader;import java.io.IOException;import java.io.InputStream;import java.io.InputStreamReader;import java.net.HttpURLConnection;import java.net.URL;import java.util.HashMap;import java.util.Map;public class WeChatUtil {// 这是获取不受限制的小程序码,官网还有其他两种 private static final String WX_CODE_URL = "https://api.weixin.qq.com/wxa/getwxacodeunlimit?access_token=AccessToken";// public static WxCodeUnlimitedResponseParam getUnlimitedCode(String accessToken, String scene, String page) { public static WxCodeUnlimitedResponseParam getUnlimitedCode(String accessToken) { JSONObject jsonObject = JSON.parseObject(accessToken.toString()); String accesstoken1 = jsonObject.getString("access_token"); // url请求参数值 Map<String, Object> params = new HashMap<String, Object>(); //**注意:接口文档错误需要将access_token参数放到url中,否则请求会失败 //scene为你需要传入得参数类似“id=????&code=222”,为参数名和值组成得字符串。 // 这些参数微信小程序上官网上有,根据需求添加 params.put("scene", "type=1"); params.put("page", "page/index/index"); params.put("width", 200); params.put("auto_color", true); params.put("check_path",false); params.put("line_color", null); params.put("is_hyaline", false); byte[] byteArray = null; /** 第一种方式:使用RestTemplate。项目采用了这种方式。 **/ // 调用微信接口 WxCodeUnlimitedResponseParam res = new WxCodeUnlimitedResponseParam(); try { RestTemplate restTemplate = new RestTemplate(); String request =WX_CODE_URL.replaceAll("AccessToken",accesstoken1); ResponseEntity<byte[]> entity = restTemplate.postForEntity( request, JSONObject.toJSONString(params), byte[].class); // 如果你十分确认微信正确返回了图片,那么byteArray已经是你想要的结果了。 byteArray = entity.getBody(); // 微信返回内容,byte[]转为string String wxReturnStr = new String(byteArray); if (wxReturnStr.indexOf("errCode") != -1) { JSONObject json = JSONObject.parseObject(wxReturnStr); res.setErrCode(json.get("errCode").toString()); res.setErrMsg(json.get("errMsg").toString()); } else { res.setErrCode("0"); res.setErrMsg("ok"); res.setBuffer(byteArray); } } catch (Exception e) { System.out.println("右岸顶针"); System.out.println("微信小程序码getUnlimited接口调用失败"); } System.out.println(res); return res; }}
3、后端controller类,编写一个接口来调用以上工具类生成二维码并转换成base64的方式传回前端
/** * 生辰二维码 */ @GetMapping("/getInviteCode") @ResponseBody public String getInviteCode(HttpServletResponse response) throws IOException { String accessToken=qrUtils.getAccessToken(); WxCodeUnlimitedResponseParam res= WeChatUtil.getUnlimitedCode(accessToken);// //以流的方式返回给前端 InputStream inputStream = new ByteArrayInputStream(res.getBuffer()); BufferedImage bufferedImage = ImageIO.read(inputStream); ByteArrayOutputStream baos = new ByteArrayOutputStream(); if (bufferedImage != null){ String format = "jpeg"; System.out.println(bufferedImage); ImageIO.write(bufferedImage, format, baos); byte[] imageBytes = baos.toByteArray(); baos.close(); return Base64.getEncoder().encodeToString(imageBytes); } return null; }
4、前端用的是vue2+elementUI
<!-- 查看二维码对话框 --> <el-dialog :title="title" :visible.sync="open_qr_code" width="700px" append-to-body v-dialogDrag custom-class="center-dialog"> <el-card shadow="always"> <el-image :src="QRcodeSrc"></el-image> </el-card> <div slot="footer" class="dialog-footer"> <el-button type="primary" @click="handleDownloadQrIMg(QRcodeSrc)">点击下载</el-button> <el-button type="primary" @click="cancel_detail">关 闭</el-button> </div> </el-dialog>
/** * 生成二维码 * */ createQRCode() { this.loading = true; createQRcode().then(response => { this.QRcodeSrc = "data:image/png;base64," + response; this.open_qr_code = true; this.loading = false; }) }, /** * 下载图片 * @returns {string} */ //imageBase64是后台传回来的base64数据 handleDownloadQrIMg(imageBase64) { // 这里是获取到的图片base64编码,这里只是个例子哈,要自行编码图片替换这里才能测试看到效果 const imgUrl = `${imageBase64}`; // 如果浏览器支持msSaveOrOpenBlob方法(也就是使用IE浏览器的时候),那么调用该方法去下载图片 if (window.navigator.msSaveOrOpenBlob) { const bstr = atob(imgUrl.split(',')[1]); let n = bstr.length; const u8arr = new Uint8Array(n); while (n--) { u8arr[n] = bstr.charCodeAt(n); } const blob = new Blob([u8arr]); window.navigator.msSaveOrOpenBlob(blob, '签到码.jpg'); } else { // 这里就按照chrome等新版浏览器来处理 const a = document.createElement('a'); a.href = imgUrl; a.setAttribute('download', 'filename.jpg'); a.click(); } }
然后就大功告成了!!!!!