微信公众号开发调用摄像头、拍摄或选择图片、OCR识别

 一 、准备工作      

  <1>域名认证准备工作

  在需要调用摄像头的接口页面引入微信的js,具体地址为:(支持https):http://res.wx.qq.com/open/js/jweixin-1.2.0.js

  首先JS安全接口域名认证:

    

    具体可参考开发文档:https://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1421141115

    填写规则(必须是备案通过的域名):

            若域名类似为:xxx.xxx.xxx.com   则接口域名为:xxx.xxx.com 

            若域名类似为:xxx.xxx.com   则接口域名为:xxx.com 

            若域名类似为:xxx.xxx.com:8080   则接口域名为:xxx.com:8080 

    <2>OCR识别准备工作

    注册百度云服务账号,网址:https://cloud.baidu.com/index.html?track=cp:npinzhuan|pf:pc|pp:left|ci:|pu:495

    点击智能控制台>>产品服务>>人工智能>>文字识别>>创建应用

    填写相关信息选择对应的需求

    点击创建应用>>查看详情:appid、apikey、secretkey是我们所需要的

二、具体代码实现

在需要调用微信js的jsp页面引入js,做如下操作:


 
 
  1. $( function (){
  2. wx.config({
  3. debug: true, // 开启调试模式,调用的所有api的返回值会在客户端alert出来,测试完成后需要关闭。
  4. appId: $( '#appId').val(), // 必填,公众号的唯一标识
  5. timestamp: $( '#timestamp').val(), // 必填,生成签名的时间戳
  6. nonceStr: $( '#nonceStr').val(), // 必填,生成签名的随机串
  7. signature: $( '#signature').val(), // 必填,签名(加密后,下文有实现)
  8. jsApiList: [ 'chooseImage', 'uploadImage'] // 必填,需要使用的JS接口列表,开发文档上有所有接口名称,根据需要选用就好。
  9. });
  10. });
  11. function openCamera(){
  12. wx.chooseImage({
  13. count: 1, // 默认9
  14. sizeType: [ 'original', 'compressed'], // 指定是原图还是压缩图,默认都有
  15. sourceType: [ 'album', 'camera'], // 指定来源是相册还是相机,默认都有
  16. success: function (res) {
  17. var localIds = res.localIds; // 返回选定照片的本地ID列表,localId可以作为img标签的src属性显示图片
  18. wx.uploadImage({
  19. localId: localIds.toString(), // 需要上传的图片的ID,由chooseImage接口获得
  20. isShowProgressTips: 1, // 进度提示
  21. success: function (res) {
  22. var mediaId = res.serverId; // 返回图片的服务器端ID,即mediaId
  23. //将获取到的 mediaId 传入后台 方法savePicture
  24. $.post(path+ "/getImage/savePicture",{ "mediaId":mediaId, "tmp": "填写证件的正反面参数"}, function(res){
  25. //填写你自己的业务逻辑
  26. });
  27. },
  28. fail: function (res) {
  29. alertModal( '图片上传失败,请重试');
  30. }
  31. });
  32. }
  33. });
  34. }

wx.config这个函数是进行js域名验证所必须的操作,具体实现如下:


 
 
  1.              //-------------------------初始化js-sdk--------begin----------------------------
  2.     SortedMap<Object, Object> params = new TreeMap<Object, Object>();
  3.     String access_token = WechatAppUtil.getAccessToken(appid,appSecret); // 建议放redis放缓存中(access_token )
  4.     String jsapi_ticket = WechatAppUtil.getJsapiTicket(access_token);
  5.     String noncestr = WechatSignUtil.getNonceStr();
  6. String timestamp = WechatSignUtil.getTimestamp();
  7. params.put( "noncestr", noncestr);
  8. params.put( "jsapi_ticket", jsapi_ticket);
  9. params.put( "timestamp", timestamp);
  10. StringBuffer url = cRequest.getRequestURL();
  11. Enumeration<String> headerNames = cRequest.getHeaderNames();
  12. if (headerNames != null) {
  13. while (headerNames.hasMoreElements()) {
  14. String header = headerNames.nextElement();
  15. log.info( "Header: {}, Value={}", header, cRequest.getHeader(header));
  16. }
  17. }
  18. String httpFlag = cRequest.getHeader( "X-Forwarded-Proto");
  19. if (httpFlag != null && httpFlag.equals( "https")) {
  20. url.replace( 0, 5, "https");
  21. }
  22. String queryString = cRequest.getQueryString();
  23. log.info( "queryString={}", queryString);
  24. if (StringUtil.isNotEmpty(queryString)) {
  25. url.append( "?").append(cRequest.getQueryString());
  26. }
  27. params.put( "url", url.toString());
  28. log.info( "url---------------->:"+url.toString());
  29. String sign = WechatSignUtil.createSignBySha1(params);
  30. log.info( "sign---------------->:"+sign);
  31. //-------------------------初始化js-sdk--------end----------------------------
  32. ModelAndView tView = new ModelAndView(LoginPageConstant.STAFF_REGIST2);
  33. tView.addObject( "appId", appid);
  34. tView.addObject( "timestamp", timestamp);
  35. tView.addObject( "nonceStr", noncestr);
  36. tView.addObject( "signature", sign);  return tView;

 
 
  1. /**
  2. * @Title: getAccessToken
  3. * @Description: 获取公众号access_token
  4. * @param @param appId
  5. * @param @param appSecret
  6. * @param @return
  7. * @return String 返回类型
  8. * @throws
  9. */
  10. public static String getAccessToken(String appId,String appSecret){
  11. final String param = "grant_type=client_credential" + "&appid=" + appId + "&secret=" + appSecret;
  12. final String data = HttpClientUtil.get(GET_ACCESS_TOKEN_PATH, param);
  13. JSONObject resultJson = JSON.parseObject(data);
  14. String access_token = resultJson.getString( "access_token");
  15. return access_token;
  16. }
  17. /**
  18. *
  19. * @Title: getJsapiTicket
  20. * @Description: 获取JsapiTicket
  21. * @param @param access_token
  22. * @param @return
  23. * @return String 返回类型
  24. * @throws
  25. */
  26. public static String getJsapiTicket(String access_token){
  27. final String param = "access_token="+access_token+ "&type=jsapi";
  28. final String data = HttpClientUtil.get(GET_JSAPI_TICKET, param);
  29. JSONObject resultJson = JSON.parseObject(data);
  30. String jsapi_ticket = resultJson.getString( "ticket");
  31. return jsapi_ticket;
  32. } /**
  33. *
  34. * @Title: getNonceStr
  35. * @Description: 生成随机字符串
  36. * @param @return
  37. * @return String 返回类型
  38. * @throws
  39. */
  40. public static String getNonceStr() {
  41. String currT = getCurrTime();
  42. String strT = currT.substring( 8, currT.length());
  43. String strRandom = buildRandom( 4) + "";
  44. return strT + strRandom;
  45. }
  46. /**
  47. *
  48. * @Title: buildRandom
  49. * @Description: 生成随机数
  50. * @param @param length
  51. * @param @return
  52. * @return int 返回类型
  53. * @throws
  54. */
  55. public static int buildRandom(int length) {
  56. int mm= 1;
  57. double random = Math.random();
  58. if (random < 0.1) {
  59. random = random + 0.1;
  60. }
  61. for ( int i = 0; i < length; i++) {
  62. mm= mm* 10;
  63. }
  64. return ( int) ((random * mm));
  65. }
  66. /**
  67. *
  68. * @Title: getCurrTime
  69. * @Description: 获取当前时间
  70. * @param @return
  71. * @return String 返回类型
  72. * @throws
  73. */
  74. public static String getCurrTime() {
  75. Date date = new Date();
  76. SimpleDateFormat of= new SimpleDateFormat( "yyyyMMddHHmmss");
  77. String s = of.format(date);
  78. return s;
  79. }
  80. /**
  81. *
  82. * @Title: createSignBySha1
  83. * @Description: 生成签名
  84. * @param @param params
  85. * @param @return
  86. * @return String 返回类型
  87. * @throws
  88. */
  89.      @SuppressWarnings( "rawtypes")
  90. public static String createSignBySha1(SortedMap<Object, Object> params) {
  91. StringBuffer sb = new StringBuffer();
  92. Set es = params.entrySet();
  93. Iterator it = es.iterator();
  94. while (it.hasNext()) {
  95. Map.Entry entry = (Map.Entry) it.next();
  96. String k = (String) entry.getKey();
  97. String v = (String) entry.getValue();
  98. if (v != null && !v.equals( "")) {
  99. sb.append(k + "=" + v + "&");
  100. }
  101. }
  102. String result = sb.toString().substring( 0, sb.toString().length()- 1);
  103. return getSHA1(result);
  104. }
  105. /**
  106. *
  107. * @Title: getTimestamp
  108. * @Description: 获取时间戳(秒)
  109. * @param @return 参数
  110. * @return String 返回类型
  111. * @throws
  112. */
  113. public static String getTimestamp() {
  114. return String.valueOf(System.currentTimeMillis() / 1000);
  115.      }
  116. /**
  117. *
  118. * @Title: getSHA1
  119. * @Description: SHA1签名生成
  120. * @param @param str
  121. * @param @return 参数
  122. * @return String 返回类型
  123. * @throws
  124. */
  125. public static String getSHA1(String str){
  126. StringBuffer hexstr = new StringBuffer();
  127. try {
  128.     MessageDigest md = MessageDigest.getInstance( "SHA-1");
  129.     md.update(str.getBytes());
  130.      byte[] digest = md.digest();
  131.      String shaHex = "";
  132.      for ( int i = 0; i < digest.length; i++) {
  133.      shaHex = Integer.toHexString(digest[i] & 0xFF);
  134.      if (shaHex.length() < 2) {
  135.      hexstr.append( 0);
  136.     }
  137.      hexstr.append(shaHex);
  138.      }
  139. } catch (NoSuchAlgorithmException e) {
  140.     e.printStackTrace();
  141. }
  142. return hexstr.toString();
  143. }

验证完成后台实现如下:


 
 
  1. /**
  2. *
  3. * @Title: savePicture
  4. * @Description: 接收图片
  5. * @param @param request
  6. * @param @return    
  7. * @return String    返回类型
  8. * @throws
  9. */
  10. @ResponseBody
  11. @RequestMapping( "/savePicture")
  12. public String savePicture(HttpServletRequest request) {
  13. String mediaId = request.getParameter( "mediaId");
  14. String tmp = request.getParameter( "tmp");
  15. String filename = saveImageToDisk(mediaId,tmp,request);
  16. log.info( "filename----------->:"+filename);
  17. return "success";
  18. }
  19. /**
  20. *
  21. * @Title: saveImageToDisk
  22. * @Description: 存盘
  23. * @param @param mediaId
  24. * @param @return    
  25. * @return String    返回类型
  26. * @throws
  27. */
  28. private String saveImageToDisk(String mediaId,String tmp,HttpServletRequest request){
  29. String filename = "";
  30. InputStream inputStream = getMedia(mediaId);
  31. byte[] data = new byte[ 1024];
  32. int len = 0;
  33. FileOutputStream fileOutputStream = null;
  34. try {
  35. //服务器存图路径
  36. String path = request.getServletContext().getRealPath( "你需要存放的服务器路径");
  37. filename = System.currentTimeMillis() + WechatSignUtil.getNonceStr() + ".jpg";
  38. fileOutputStream = new FileOutputStream(path + filename);
  39. while ((len = inputStream.read(data)) != - 1) {
  40. fileOutputStream.write(data, 0, len);
  41. }
  42. WeChatUser idCardMsg = getIdCardMsg(tmp,path + filename);
  43. } catch (IOException e) {
  44. e.printStackTrace();
  45. } finally {
  46. if (inputStream != null) {
  47. try {
  48. inputStream.close();
  49. } catch (IOException e) {
  50. e.printStackTrace();
  51. }
  52. }
  53. if (fileOutputStream != null) {
  54. try {
  55. fileOutputStream.close();
  56. } catch (IOException e) {
  57. e.printStackTrace();
  58. }
  59. }
  60. }
  61. return filename;
  62. }
  63. /**
  64. *
  65. * @Title: getMedia
  66. * @Description: 获取图片
  67. * @param @param mediaId
  68. * @param @return    参数
  69. * @return InputStream    返回类型
  70. * @throws
  71. */
  72. private InputStream getMedia(String mediaId) {
  73. String url = "https://api.weixin.qq.com/cgi-bin/media/get";
  74. String access_token = WechatAppUtil.getAccessToken( "**********", "*************");
  75. String params = "access_token=" + access_token + "&media_id=" + mediaId;
  76. InputStream is = null;
  77. try {
  78. String urlNameString = url + "?" + params;
  79. URL urlGet = new URL(urlNameString);
  80. HttpURLConnection http = (HttpURLConnection) urlGet.openConnection();
  81. http.setRequestMethod( "GET"); // 必须是get方式请求
  82. http.setRequestProperty( "Content-Type", "application/x-www-form-urlencoded");
  83. http.setDoOutput( true);
  84. http.setDoInput( true);
  85. http.connect();
  86. // 获取文件转化为byte流
  87. is = http.getInputStream();
  88. } catch (Exception e) {
  89. e.printStackTrace();
  90. }
  91. return is;
  92. }
  93. /**
  94. *
  95. * @Title: getIdCardMsg
  96. * @Description:
  97. * @param @param tmp
  98. * @param @param imgUrl 图片路径
  99. * @param @return    
  100. * @return WeChatUser    返回类型
  101. * @throws
  102. */
  103. private WeChatUser getIdCardMsg(String tmp,String imgUrl){
  104. // 初始化一个AipOcr
  105. AipOcr client = new AipOcr(APP_ID, API_KEY, SECRET_KEY);
  106. // 可选:设置网络连接参数
  107. client.setConnectionTimeoutInMillis( 2000);
  108. client.setSocketTimeoutInMillis( 60000);
  109. // 传入可选参数调用接口
  110. HashMap<String, String> options = new HashMap<String, String>();
  111. options.put( "detect_direction", "true");
  112. options.put( "detect_risk", "false");
  113. String idCardSide = tmp;
  114. // 参数为图片路径
  115. String image = imgUrl;
  116. JSONObject res = client.idcard(image, idCardSide, options);
  117. 具体返回信息处理请参考开发文档:https: //cloud.baidu.com/doc/OCR/OCR-Java-SDK.html#.E6.8E.A5.E5.8F.A3.E8.83.BD.E5.8A.9B
  118. }

              

  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 5
    评论
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值