Skip to content

:new #1831 指定文件路径生成小程序二维码 #1842

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Nov 1, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
package cn.binarywang.wx.miniapp.api;

import java.io.File;

import cn.binarywang.wx.miniapp.bean.WxMaCodeLineColor;
import me.chanjar.weixin.common.error.WxErrorException;

import java.io.File;

/**
* <pre>
* 二维码相关操作接口.
Expand Down Expand Up @@ -37,6 +37,23 @@ public interface WxMaQrcodeService {
*/
byte[] createQrcodeBytes(String path, int width) throws WxErrorException;

/**
* 接口C: 获取小程序页面二维码.
* <pre>
* 适用于需要的码数量较少的业务场景
* 通过该接口,仅能生成已发布的小程序的二维码。
* 可以在开发者工具预览时生成开发版的带参二维码。
* 带参二维码只有 100000 个,请谨慎调用。
* </pre>
*
* @param path 不能为空,最大长度 128 字节
* @param width 默认430 二维码的宽度
* @param filePath 二维码生成的文件路径,例如: /var/temp
* @return 文件对象
* @throws WxErrorException 异常
*/
File createQrcode(String path, int width, String filePath) throws WxErrorException;

/**
* 接口C: 获取小程序页面二维码.
* <pre>
Expand All @@ -53,6 +70,22 @@ public interface WxMaQrcodeService {
*/
File createQrcode(String path, int width) throws WxErrorException;

/**
* 接口C: 获取小程序页面二维码.
* <pre>
* 适用于需要的码数量较少的业务场景
* 通过该接口,仅能生成已发布的小程序的二维码。
* 可以在开发者工具预览时生成开发版的带参二维码。
* 带参二维码只有 100000 个,请谨慎调用。
* </pre>
*
* @param path 不能为空,最大长度 128 字节
* @param filePath 二维码生成的文件路径,例如: /var/temp
* @return 文件对象
* @throws WxErrorException 异常
*/
File createQrcode(String path, String filePath) throws WxErrorException;

/**
* 接口C: 获取小程序页面二维码.
* <pre>
Expand Down Expand Up @@ -82,6 +115,21 @@ public interface WxMaQrcodeService {
byte[] createWxaCodeBytes(String path, int width, boolean autoColor, WxMaCodeLineColor lineColor, boolean isHyaline)
throws WxErrorException;

/**
* 接口A: 获取小程序码.
*
* @param path 不能为空,最大长度 128 字节
* @param width 默认430 二维码的宽度
* @param filePath 二维码生成的文件路径,例如: /var/temp
* @param autoColor 默认true 自动配置线条颜色,如果颜色依然是黑色,则说明不建议配置主色调
* @param lineColor auth_color 为 false 时生效,使用 rgb 设置颜色 例如 {"r":"xxx","g":"xxx","b":"xxx"}
* @param isHyaline 是否需要透明底色, isHyaline 为true时,生成透明底色的小程序码
* @return 文件对象
* @throws WxErrorException 异常
*/
File createWxaCode(String path, int width, String filePath, boolean autoColor, WxMaCodeLineColor lineColor, boolean isHyaline)
throws WxErrorException;

/**
* 接口A: 获取小程序码.
*
Expand All @@ -96,6 +144,17 @@ byte[] createWxaCodeBytes(String path, int width, boolean autoColor, WxMaCodeLin
File createWxaCode(String path, int width, boolean autoColor, WxMaCodeLineColor lineColor, boolean isHyaline)
throws WxErrorException;

/**
* 接口A: 获取小程序码.
*
* @param path 不能为空,最大长度 128 字节
* @param width 默认430 二维码的宽度
* @param filePath 二维码生成的文件路径,例如: /var/temp
* @return 文件对象
* @throws WxErrorException 异常
*/
File createWxaCode(String path, int width, String filePath) throws WxErrorException;

/**
* 接口A: 获取小程序码.
*
Expand All @@ -106,6 +165,16 @@ File createWxaCode(String path, int width, boolean autoColor, WxMaCodeLineColor
*/
File createWxaCode(String path, int width) throws WxErrorException;

/**
* 接口A: 获取小程序码.
*
* @param path 不能为空,最大长度 128 字节
* @param filePath 二维码生成的文件路径,例如: /var/temp
* @return 文件对象
* @throws WxErrorException 异常
*/
File createWxaCode(String path, String filePath) throws WxErrorException;

/**
* 接口A: 获取小程序码.
*
Expand Down Expand Up @@ -137,6 +206,29 @@ File createWxaCode(String path, int width, boolean autoColor, WxMaCodeLineColor
byte[] createWxaCodeUnlimitBytes(String scene, String page, int width, boolean autoColor,
WxMaCodeLineColor lineColor, boolean isHyaline) throws WxErrorException;

/**
* 接口B: 获取小程序码(永久有效、数量暂无限制).
* <pre>
* 通过该接口生成的小程序码,永久有效,数量暂无限制。
* 用户扫描该码进入小程序后,将统一打开首页,开发者需在对应页面根据获取的码中 scene 字段的值,再做处理逻辑。
* 使用如下代码可以获取到二维码中的 scene 字段的值。
* 调试阶段可以使用开发工具的条件编译自定义参数 scene=xxxx 进行模拟,开发工具模拟时的 scene 的参数值需要进行 urlencode
* </pre>
*
* @param scene 最大32个可见字符,只支持数字,大小写英文以及部分特殊字符:!#$&'()*+,/:;=?@-._~,
* 其它字符请自行编码为合法字符(因不支持%,中文无法使用 urlencode 处理,请使用其他编码方式)
* @param page 必须是已经发布的小程序页面,例如 "pages/index/index" ,如果不填写这个字段,默认跳主页面
* @param filePath 二维码生成的文件路径,例如: /var/temp
* @param width 默认false 自动配置线条颜色,如果颜色依然是黑色,则说明不建议配置主色调
* @param autoColor 默认true 自动配置线条颜色,如果颜色依然是黑色,则说明不建议配置主色调
* @param lineColor auth_color 为 false 时生效,使用 rgb 设置颜色 例如 {"r":"xxx","g":"xxx","b":"xxx"}
* @param isHyaline 是否需要透明底色, is_hyaline 为true时,生成透明底色的小程序码
* @return 文件对象
* @throws WxErrorException 异常
*/
File createWxaCodeUnlimit(String scene, String page, String filePath, int width, boolean autoColor,
WxMaCodeLineColor lineColor, boolean isHyaline) throws WxErrorException;

/**
* 接口B: 获取小程序码(永久有效、数量暂无限制).
* <pre>
Expand All @@ -159,6 +251,24 @@ byte[] createWxaCodeUnlimitBytes(String scene, String page, int width, boolean a
File createWxaCodeUnlimit(String scene, String page, int width, boolean autoColor,
WxMaCodeLineColor lineColor, boolean isHyaline) throws WxErrorException;

/**
* 接口B: 获取小程序码(永久有效、数量暂无限制).
* <pre>
* 通过该接口生成的小程序码,永久有效,数量暂无限制。
* 用户扫描该码进入小程序后,将统一打开首页,开发者需在对应页面根据获取的码中 scene 字段的值,再做处理逻辑。
* 使用如下代码可以获取到二维码中的 scene 字段的值。
* 调试阶段可以使用开发工具的条件编译自定义参数 scene=xxxx 进行模拟,开发工具模拟时的 scene 的参数值需要进行 urlencode
* </pre>
*
* @param scene 最大32个可见字符,只支持数字,大小写英文以及部分特殊字符:!#$&'()*+,/:;=?@-._~,
* 其它字符请自行编码为合法字符(因不支持%,中文无法使用 urlencode 处理,请使用其他编码方式)
* @param page 必须是已经发布的小程序页面,例如 "pages/index/index" ,如果不填写这个字段,默认跳主页面
* @param filePath 二维码生成的文件路径,例如: /var/temp
* @return 文件对象
* @throws WxErrorException 异常
*/
File createWxaCodeUnlimit(String scene, String page, String filePath) throws WxErrorException;

/**
* 接口B: 获取小程序码(永久有效、数量暂无限制).
* <pre>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
import cn.binarywang.wx.miniapp.bean.WxaCode;
import cn.binarywang.wx.miniapp.bean.WxaCodeUnlimit;
import cn.binarywang.wx.miniapp.util.QrcodeBytesRequestExecutor;
import cn.binarywang.wx.miniapp.util.QrcodeFileRequestExecutor;
import cn.binarywang.wx.miniapp.util.QrcodeRequestExecutor;
import lombok.AllArgsConstructor;
import me.chanjar.weixin.common.error.WxErrorException;
Expand Down Expand Up @@ -107,4 +108,51 @@ public File createWxaCodeUnlimit(String scene, String page) throws WxErrorExcept
return this.createWxaCodeUnlimit(scene, page, 430, true, null, false);
}

@Override
public File createQrcode(String path, int width, String filePath) throws WxErrorException {
final QrcodeFileRequestExecutor executor = new QrcodeFileRequestExecutor(this.wxMaService.getRequestHttp(), filePath);
return this.wxMaService.execute(executor, CREATE_QRCODE_URL, new WxMaQrcode(path, width));
}

@Override
public File createQrcode(String path, String filePath) throws WxErrorException {
return createQrcode(path, 430, filePath);
}

@Override
public File createWxaCode(String path, int width, String filePath, boolean autoColor, WxMaCodeLineColor lineColor, boolean isHyaline)
throws WxErrorException {
final QrcodeFileRequestExecutor executor = new QrcodeFileRequestExecutor(this.wxMaService.getRequestHttp(), filePath);
return this.wxMaService.execute(executor, GET_WXACODE_URL, WxaCode.builder()
.path(path)
.width(width)
.autoColor(autoColor)
.lineColor(lineColor)
.isHyaline(isHyaline)
.build());
}

@Override
public File createWxaCode(String path, int width, String filePath) throws WxErrorException {
return this.createWxaCode(path, width, filePath, true, null, false);
}

@Override
public File createWxaCode(String path, String filePath) throws WxErrorException {
return this.createWxaCode(path, 430, filePath);
}

@Override
public File createWxaCodeUnlimit(String scene, String page, String filePath, int width, boolean autoColor,
WxMaCodeLineColor lineColor, boolean isHyaline) throws WxErrorException {
return this.wxMaService.execute(new QrcodeFileRequestExecutor(this.wxMaService.getRequestHttp(), filePath),
GET_WXACODE_UNLIMIT_URL,
this.buildWxaCodeUnlimit(scene, page, width, autoColor, lineColor, isHyaline));
}

@Override
public File createWxaCodeUnlimit(String scene, String page, String filePath) throws WxErrorException {
return this.createWxaCodeUnlimit(scene, page, filePath, 430, true, null, false);
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
package cn.binarywang.wx.miniapp.util;

import cn.binarywang.wx.miniapp.bean.AbstractWxMaQrcodeWrapper;
import me.chanjar.weixin.common.enums.WxType;
import me.chanjar.weixin.common.error.WxError;
import me.chanjar.weixin.common.error.WxErrorException;
import me.chanjar.weixin.common.util.fs.FileUtils;
import me.chanjar.weixin.common.util.http.RequestHttp;
import me.chanjar.weixin.common.util.http.apache.InputStreamResponseHandler;
import me.chanjar.weixin.common.util.http.apache.Utf8ResponseHandler;
import org.apache.commons.lang3.StringUtils;
import org.apache.http.Header;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.ContentType;
import org.apache.http.entity.StringEntity;

import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.nio.file.Paths;
import java.util.UUID;

/**
* @author <a href="https://github.com/gentryhuang">gentryhuang</a>
*/
public class QrcodeFileRequestExecutor extends QrcodeRequestExecutor {
/**
* 二维码生成的文件路径,例如: /var/temp
*/
private final String filePath;

public QrcodeFileRequestExecutor(RequestHttp requestHttp, String filePath) {
super(requestHttp);
this.filePath = filePath;
}

/**
* 执行http请求.
*
* @param uri uri
* @param qrcodeWrapper 数据
* @param wxType 微信模块类型
* @return 响应结果
* @throws WxErrorException 自定义异常
* @throws IOException io异常
*/
@Override
public File execute(String uri, AbstractWxMaQrcodeWrapper qrcodeWrapper, WxType wxType) throws WxErrorException, IOException {
HttpPost httpPost = new HttpPost(uri);
if (requestHttp.getRequestHttpProxy() != null) {
httpPost.setConfig(
RequestConfig.custom().setProxy(requestHttp.getRequestHttpProxy()).build()
);
}

httpPost.setEntity(new StringEntity(qrcodeWrapper.toJson(), ContentType.APPLICATION_JSON));

try (final CloseableHttpResponse response = requestHttp.getRequestHttpClient().execute(httpPost);
final InputStream inputStream = InputStreamResponseHandler.INSTANCE.handleResponse(response)) {
Header[] contentTypeHeader = response.getHeaders("Content-Type");
if (contentTypeHeader != null && contentTypeHeader.length > 0
&& ContentType.APPLICATION_JSON.getMimeType()
.equals(ContentType.parse(contentTypeHeader[0].getValue()).getMimeType())) {
String responseContent = Utf8ResponseHandler.INSTANCE.handleResponse(response);
throw new WxErrorException(WxError.fromJson(responseContent, wxType));
}
if (StringUtils.isBlank(filePath)) {
return FileUtils.createTmpFile(inputStream, UUID.randomUUID().toString(), "jpg");
}

return FileUtils.createTmpFile(inputStream, UUID.randomUUID().toString(), "jpg", Paths.get(filePath).toFile());
} finally {
httpPost.releaseConnection();
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -55,4 +55,22 @@ public void testCreateWxaCodeUnlimitBytes() throws WxErrorException {
final byte[] wxCode = this.wxService.getQrcodeService().createWxaCodeUnlimitBytes("111", null, 122, true, null, false);
assertThat(wxCode).isNotNull();
}

@Test
public void testCreateQrcodeByFile() throws WxErrorException {
final File qrCode = this.wxService.getQrcodeService().createQrcode("111", "/opt/logs");
assertThat(qrCode).isNotNull();
}

@Test
public void testCreateWxaCodeByFile() throws WxErrorException {
final File wxCode = this.wxService.getQrcodeService().createWxaCode("111", "/opt/logs");
assertThat(wxCode).isNotNull();
}

@Test
public void testCreateQrcodeUnlimitByFile() throws WxErrorException {
final File wxCode = this.wxService.getQrcodeService().createWxaCodeUnlimit("111",null,"/opt/logs");
assertThat(wxCode).isNotNull();
}
}