代码改变世界

uniapp 身份证识别 微信 百度 图片前端压缩 图片后端压缩

2021-03-15 16:25  会飞的雪鹿  阅读(448)  评论(0编辑  收藏  举报

微信:

 1 下面注释代码 HBuilder调试OK 发布微信调试失败 不知所以 
 2                 var ocrUrl = "https://api.weixin.qq.com/cv/ocr/idcard?img_url=" + self.imgUrl + "&access_token=" + self.token;
 3                 wx.chooseImage({
 4                         sourceType: ['camera'], // 可以指定来源是相册还是相机,默认二者都有
 5                         const tempFilePaths = res.tempFilePaths
 6                         wx.uploadFile({
 7                             url: ocrUrl,
 8                             filePath: tempFilePaths[0],
 9                             name: 'img',
10                             formData: {
11                                 contentType: 'image/png',
12                                 value: "",
13                             },
14                             success(res) {
15                                 const data = JSON.parse(res.data);
16                                 if (data.errcode != 0) {
17                                     self.$api.alert("识别失败!");
18                                 }
19                                 self.name = data.name;
20                                 self.idNo = data.id;
21                                 if (numberUtils.identityCodeValid(self.idNo.trim())) {
22                                     self.age = self.getAge(self.idNo.trim());
23                                 }
24                                 if (data.gender == '男') {
25                                     self.current = 0;
26                                 } else {
27                                     self.current = 1;
28                                 }
29                             },
30                             fail(res) {
31                                 self.$api.alert("识别失败!");
32                             },
33                         })

前端  转byte64 压缩  /components/image-tools/index.js

  1 function getLocalFilePath(path) {
  2     if (path.indexOf('_www') === 0 || path.indexOf('_doc') === 0 || path.indexOf('_documents') === 0 || path.indexOf('_downloads') === 0) {
  3         return path
  4     }
  5     if (path.indexOf('file://') === 0) {
  6         return path
  7     }
  8     if (path.indexOf('/storage/emulated/0/') === 0) {
  9         return path
 10     }
 11     if (path.indexOf('/') === 0) {
 12         var localFilePath = plus.io.convertAbsoluteFileSystem(path)
 13         if (localFilePath !== path) {
 14             return localFilePath
 15         } else {
 16             path = path.substr(1)
 17         }
 18     }
 19     return '_www/' + path
 20 }
 21 
 22 var index = 0
 23 function getNewFileId() {
 24     return Date.now() + String(index++)
 25 }
 26 
 27 function biggerThan(v1, v2) {
 28     var v1Array = v1.split('.')
 29     var v2Array = v2.split('.')
 30     var update = false
 31     for (var index = 0; index < v2Array.length; index++) {
 32         var diff = v1Array[index] - v2Array[index]
 33         if (diff !== 0) {
 34             update = diff > 0
 35             break
 36         }
 37     }
 38     return update
 39 }
 40 
 41 export function pathToBase64(path) {
 42     
 43     return new Promise(function(resolve, reject) {
 44         if (typeof window === 'object' && 'document' in window) {
 45             if (typeof FileReader === 'function') {
 46                 var xhr = new XMLHttpRequest()
 47                 xhr.open('GET', path, true)
 48                 xhr.responseType = 'blob'
 49                 xhr.onload = function() {
 50                     if (this.status === 200) {
 51                         let fileReader = new FileReader()
 52                         fileReader.onload = function(e) {
 53                             resolve(e.target.result)
 54                         }
 55                         fileReader.onerror = reject
 56                         fileReader.readAsDataURL(this.response)
 57                     }
 58                 }
 59                 xhr.onerror = reject
 60                 xhr.send()
 61                 return
 62             }
 63             var canvas = document.createElement('canvas')
 64             var c2x = canvas.getContext('2d')
 65             var img = new Image
 66             img.onload = function() {
 67                 canvas.width = img.width
 68                 canvas.height = img.height
 69                 c2x.drawImage(img, 0, 0)
 70                 resolve(canvas.toDataURL())
 71                 canvas.height = canvas.width = 0
 72             }
 73             img.onerror = reject
 74             img.src = path
 75             return
 76         }
 77         if (typeof plus === 'object') {
 78             plus.io.resolveLocalFileSystemURL(getLocalFilePath(path), function(entry) {
 79                 entry.file(function(file) {
 80                     var fileReader = new plus.io.FileReader()
 81                     fileReader.onload = function(data) {
 82                         resolve(data.target.result)
 83                     }
 84                     fileReader.onerror = function(error) {
 85                         reject(error)
 86                     }
 87                     fileReader.readAsDataURL(file)
 88                 }, function(error) {
 89                     reject(error)
 90                 })
 91             }, function(error) {
 92                 reject(error)
 93             })
 94             return
 95         }
 96         if (typeof wx === 'object' && wx.canIUse('getFileSystemManager')) {
 97             wx.getFileSystemManager().readFile({
 98                 filePath: path,
 99                 encoding: 'base64',
100                 success: function(res) {
101                     resolve('data:image/png;base64,' + res.data)
102                 },
103                 fail: function(error) {
104                     reject(error)
105                 }
106             })
107             return
108         }
109         reject(new Error('not support'))
110     })
111 }
112 
113 export function base64ToPath(base64) {
114     return new Promise(function(resolve, reject) {
115         if (typeof window === 'object' && 'document' in window) {
116             base64 = base64.split(',')
117             var type = base64[0].match(/:(.*?);/)[1]
118             var str = atob(base64[1])
119             var n = str.length
120             var array = new Uint8Array(n)
121             while (n--) {
122                 array[n] = str.charCodeAt(n)
123             }
124             return resolve((window.URL || window.webkitURL).createObjectURL(new Blob([array], { type: type })))
125         }
126         var extName = base64.match(/data\:\S+\/(\S+);/)
127         if (extName) {
128             extName = extName[1]
129         } else {
130             reject(new Error('base64 error'))
131         }
132         var fileName = getNewFileId() + '.' + extName
133         if (typeof plus === 'object') {
134             var basePath = '_doc'
135             var dirPath = 'uniapp_temp'
136             var filePath = basePath + '/' + dirPath + '/' + fileName
137             if (!biggerThan(plus.os.name === 'Android' ? '1.9.9.80627' : '1.9.9.80472', plus.runtime.innerVersion)) {
138                 plus.io.resolveLocalFileSystemURL(basePath, function(entry) {
139                     entry.getDirectory(dirPath, {
140                         create: true,
141                         exclusive: false,
142                     }, function(entry) {
143                         entry.getFile(fileName, {
144                             create: true,
145                             exclusive: false,
146                         }, function(entry) {
147                             entry.createWriter(function(writer) {
148                                 writer.onwrite = function() {
149                                     resolve(filePath)
150                                 }
151                                 writer.onerror = reject
152                                 writer.seek(0)
153                                 writer.writeAsBinary(base64.replace(/^data:\S+\/\S+;base64,/, ''))
154                             }, reject)
155                         }, reject)
156                     }, reject)
157                 }, reject)
158                 return
159             }
160             var bitmap = new plus.nativeObj.Bitmap(fileName)
161             bitmap.loadBase64Data(base64, function() {
162                 bitmap.save(filePath, {}, function() {
163                     bitmap.clear()
164                     resolve(filePath)
165                 }, function(error) {
166                     bitmap.clear()
167                     reject(error)
168                 })
169             }, function(error) {
170                 bitmap.clear()
171                 reject(error)
172             })
173             return
174         }
175         if (typeof wx === 'object' && wx.canIUse('getFileSystemManager')) {
176             var filePath = wx.env.USER_DATA_PATH + '/' + fileName
177             wx.getFileSystemManager().writeFile({
178                 filePath: filePath,
179                 data: base64.replace(/^data:\S+\/\S+;base64,/, ''),
180                 encoding: 'base64',
181                 success: function() {
182                     resolve(filePath)
183                 },
184                 fail: function(error) {
185                     reject(error)
186                 }
187             })
188             return
189         }
190         reject(new Error('not support'))
191     })
192 }
193 
194 /**
195 * canvas压缩图片
196 * @param {参数obj} param 
197 * @param {文件二进制流} param.file 必传
198 * @param {目标压缩大小} param.targetSize 不传初始赋值-1
199 * @param {输出图片宽度} param.width 不传初始赋值-1,等比缩放不用传高度
200 * @param {输出图片名称} param.fileName 不传初始赋值image
201 * @param {压缩图片程度} param.quality 不传初始赋值0.92。值范围0~1
202 * @param {回调函数} param.succ 必传
203 */
204 export function pressImg(param){
205   //如果没有回调函数就不执行
206   if(param && param.succ){
207      //如果file没定义返回null
208      if(param.file == undefined) return param.succ(null);
209      //给参数附初始值
210      param.targetSize = param.hasOwnProperty("targetSize") ? param.targetSize : -1;
211      param.width = param.hasOwnProperty("width") ? param.width : -1;
212      param.fileName = param.hasOwnProperty("fileName") ? param.fileName: "image";
213      param.quality = param.hasOwnProperty("quality") ? param.quality : 0.92;
214      var _this = this;
215      // 得到文件类型
216      // var fileType = param.file.type;
217      // // console.log(fileType) //image/jpeg
218      // if(fileType.indexOf("image") == -1){
219      //   console.log('请选择图片文件^_^');
220      //   return param.succ(null);
221      // }
222      // //如果当前size比目标size小,直接输出
223      // var size = param.file.size;
224      // if(param.targetSize > size){
225      //   return param.succ(param.file);
226      // }
227      // 读取file文件,得到的结果为base64位
228     // changeFileToBaseURL(param.file,function(base64){
229         var fileType = "image";
230         debugger;
231         var base64=param.file;
232        if(base64){
233          var image = new Image();
234          image.src = base64;
235          image.onload = function(){
236            // 获得长宽比例
237            var scale = this.width / this.height;
238            // console.log(scale);
239            //创建一个canvas
240            var canvas = document.createElement('canvas');
241            //获取上下文
242            var context = canvas.getContext('2d');
243            //获取压缩后的图片宽度,如果width为-1,默认原图宽度
244            canvas.width = param.width == -1 ? this.width : param.width;
245            //获取压缩后的图片高度,如果width为-1,默认原图高度
246            canvas.height = param.width == -1 ? this.height : parseInt(param.width / scale);
247            //把图片绘制到canvas上面
248            context.drawImage(image, 0, 0, canvas.width, canvas.height);
249            //压缩图片,获取到新的base64Url
250            var newImageData = canvas.toDataURL(fileType,param.quality);
251            //将base64转化成文件流
252            // var resultFile = dataURLtoFile(newImageData,param.fileName);
253            // //判断如果targetSize有限制且压缩后的图片大小比目标大小大,就弹出错误
254            // if(param.targetSize != -1 && param.targetSize < resultFile.size){
255            //   console.log("图片上传尺寸太大,请重新上传^_^");
256            //   param.succ(null);
257            // }else{
258            //   //返回文件流
259            //   param.succ(resultFile);
260            // }
261            param.succ(newImageData);
262          }
263        }
264     // });
265   }
266  }
267  
268  /**
269   * 将base64转换为文件
270   * @param {baseURL} dataurl 
271   * @param {文件名称} filename 
272   * @return {文件二进制流}
273  */
274  function dataURLtoFile(dataurl, filename) {
275      var arr = dataurl.split(','), mime = arr[0].match(/:(.*?);/)[1],
276          bstr = atob(arr[1]), n = bstr.length, u8arr = new Uint8Array(n);
277      while(n--){
278          u8arr[n] = bstr.charCodeAt(n);
279      }
280      return new File([u8arr], filename, {type:mime});
281   }
282   
283   /**
284   * @param {二进制文件流} file 
285   * @param {回调函数,返回base64} fn 
286   */
287   function changeFileToBaseURL(file,fn){
288     // 创建读取文件对象
289         var fileReader = new FileReader();
290         //如果file没定义返回null
291         if(file == undefined) return fn(null);
292         // 读取file文件,得到的结果为base64位
293         fileReader.readAsDataURL(file);
294         fileReader.onload = function(){
295           // 把读取到的base64
296           var imgBase64Data = this.result;
297           fn(imgBase64Data);
298         }
299       }
转格式 js
 1     引入工具 index.js
 2 import {
 3         pathToBase64,
 4         base64ToPath,
 5         pressImg
 6     } from '@/components/image-tools/index.js'
 7 
 8                 uni.chooseImage({
 9                     count: 1, // 默认9
10                     sizeType: ['compressed'], // 可以指定是原图还是压缩图,默认二者都有
11                     sourceType: ['album', 'camera'], // 可以指定来源是相册还是相机,默认二者都有
12                     type: 'file',
13                     success(res) {
14                         debugger;
15                         const tempFilePaths = res.tempFilePaths;
16                         var that = res.tempFilePaths[0];
17                         // 地址转成Base64
18                         pathToBase64(res.tempFilePaths[0])
19                             .then(base64 => {
20                                 //Base64 进行10倍压缩返回 Base64
21                                 pressImg({
22                                     file: base64,
23                                     targetSize: 2 * 1024 * 1024,
24                                     quality: 0.1,
25                                     width: 600,
26                                     succ: function(resultFile) {
27                                         //如果不是null就是压缩成功
28                                         if (resultFile) {
29                                             //TODO
30                                             self.$api.request.post('/OCRIdCard/getIdCard', JSON.stringify(resultFile), function(res) {
31                                                 if (res && res.code == "0" && res.data) {
32                                                     const data = res.data;
33                                                     self.name = data.words_result.姓名.words;
34                                                     self.idNo = data.words_result.公民身份号码.words;
35                                                     if (numberUtils.identityCodeValid(self.idNo)) {
36                                                         self.age = self.getAge(self.idNo);
37                                                     }
38                                                     if (data.words_result.性别.words == '男') {
39                                                         self.current = 0;
40                                                     } else {
41                                                         self.current = 1;
42                                                     }
43                                                 } else {
44                                                     if (res.data)
45                                                         self.$api.alert("识别失败!" + res.data);
46                                                     else
47                                                         self.$api.alert("识别失败!");
48                                                 }
49 
50                                             }, function(res) {
51                                                 uni.showToast({
52                                                     icon: 'none',
53                                                     title: '未连接到服务,请联系管理员' + JSON.stringify(res),
54                                                 });
55                                             }, function() {
56 
57                                                 uni.hideLoading();
58                                             });
59                                         }
60                                     }
61                                 })
62                             });
前端压缩 传后台调百度api

java调百度api 工具类

引入两个包 一个Json 用 一个 压缩用

<dependency>
<groupId>org.json</groupId>
<artifactId>json</artifactId>
<version>20160810</version>
</dependency>
<dependency>
<groupId>net.coobird</groupId>
<artifactId>thumbnailator</artifactId>
<version>0.4.8</version>
</dependency>
package XXXXXXX;


import java.awt.image.BufferedImage;
import java.io.*;
import java.math.BigDecimal;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;
import java.util.Base64;
import java.util.List;
import java.util.Map;

import net.coobird.thumbnailator.Thumbnails;
import org.json.JSONObject;

import javax.imageio.ImageIO;


public class BaiDuCardIdentification {




    public static String getIdCardMessage(String accessToken,String imgByte64) {
        // 请求url
        String url = "https://aip.baidubce.com/rest/2.0/ocr/v1/idcard";
        try {


            imgByte64=imgByte64.replaceAll("data:image/(.*);base64,","");

            byte[] imgData= commpressPicCycle(Base64.getDecoder().decode(imgByte64), 300, 0.5f);


            String imgStr = Base64Util.encode((byte[])imgData);
            String imgParam = URLEncoder.encode(imgStr, "UTF-8");

            String param = "id_card_side=" + "front" + "&image=" + imgParam;

            // 注意这里仅为了简化编码每一次请求都去获取access_token,线上环境access_token有过期时间, 客户端可自行缓存,过期后重新获取。

            String result = HttpUtil.post(url, accessToken, param);
            System.out.println(result);
            return result;
        } catch (Exception e) {
            return "身份证识别次数没有了,请联系管理员";
        }
    }

    public static String getAuth(String ak, String sk) {
        // 获取token地址
        String authHost = "https://aip.baidubce.com/oauth/2.0/token?";
        String getAccessTokenUrl = authHost
                // 1. grant_type为固定参数
                + "grant_type=client_credentials"
                // 2. 官网获取的 API Key
                + "&client_id=" + ak
                // 3. 官网获取的 Secret Key
                + "&client_secret=" + sk;
        try {
            URL realUrl = new URL(getAccessTokenUrl);
            // 打开和URL之间的连接
            HttpURLConnection connection = (HttpURLConnection) realUrl.openConnection();
            connection.setRequestMethod("GET");//设置请求方式
            connection.connect();//发送url
            // 获取所有响应头字段
            Map<String, List<String>> map = connection.getHeaderFields();
            // 遍历所有的响应头字段
            for (String key : map.keySet()) {
                System.err.println(key + "--->" + map.get(key));
            }
            // 定义 BufferedReader输入流来读取URL的响应
            BufferedReader in = new BufferedReader(new InputStreamReader(connection.getInputStream()));
            String result = "";
            String line;
            while ((line = in.readLine()) != null) {
                result += line;
            }
            /**
             * 返回结果示例
             */

            JSONObject jsonObject = new JSONObject(result);
            String access_token = jsonObject.getString("access_token");
            return access_token;
        } catch (Exception e) {
            return "获取token失败";
        }

    }




    /**
     *
     * @param bytes 原图片字节数组
     * @param desFileSize 指定图片大小,单位 kb
     * @param accuracy 精度,递归压缩的比率,建议小于0.9
     * @return
     */
    public static byte[] commpressPicCycle(byte[] bytes, long desFileSize, double accuracy) throws IOException {
        // 获取目标图片
//        File imgFile = new File(desPath);
//        long fileSize = imgFile.length();
        long fileSize = bytes.length;
        System.out.println("=====fileSize======== "+fileSize);
        // 判断图片大小是否小于指定图片大小
        if(fileSize <= desFileSize * 1024){
            return bytes;
        }
        //计算宽高
        BufferedImage bim = ImageIO.read(new ByteArrayInputStream(bytes));
        int imgWidth = bim.getWidth();
        System.out.println(imgWidth+"====imgWidth=====");
        int imgHeight = bim.getHeight();
        int desWidth = new BigDecimal(imgWidth).multiply( new BigDecimal(accuracy)).intValue();
        System.out.println(desWidth+"====desWidth=====");
        int desHeight = new BigDecimal(imgHeight).multiply( new BigDecimal(accuracy)).intValue();
        ByteArrayOutputStream baos = new ByteArrayOutputStream(); //字节输出流(写入到内存)
        Thumbnails.of(new ByteArrayInputStream(bytes)).size(desWidth, desHeight).outputQuality(accuracy).toOutputStream(baos);
        //如果不满足要求,递归直至满足要求
        return commpressPicCycle(baos.toByteArray(), desFileSize, accuracy);
    }


}
 1  @RequestMapping(value = "/getIdCard", method = RequestMethod.POST)
 2     @WithoutAuthentication
 3     public Result getIdCard(@RequestBody Object file){
 4 
 5         Result result = new Result();
 6         String auth = BaiDuCardIdentification.getAuth("client_id","client_secret");//获取access_token
 7         //识别身份证信息  是要传入的两个参数  一个是access_token  另一个是文件的路径
 8         String idcard = BaiDuCardIdentification.getIdCardMessage(auth, file.toString());
 9         JSONObject parse =  JSONObject.parseObject(idcard); //将百度返回给我们的身份证信息 转换为json对象
10         String idcard_number_type = parse.get("idcard_number_type").toString();//获取idcard_number_type判断身份证是否合法
11 
12         if (idcard.contains("edit_tool")) {//如果你的身份证图片被修改过  会返回这个字段  值为哪一个软件编辑过
13             result.setCode("300");
14             result.setData("身份证被"+parse.get("edit_tool").toString()+"编辑过,请重新上传");
15             return result;
16         }
17         if (parse.get("image_status").toString().equals("non_idcard")) {//判断你上传的这张图片是否是个身份证图片
18             result.setCode("300");
19             result.setData("身份证不合格,请上传身份证照片面图片");
20             return result;
21         }
22         if (idcard_number_type.equals("1")) {//只有idcard_number_type值为1的时候是合格的  其他的均为不合格
23             result.setCode("0");
24             result.setData(parse);
25             return result;
26 
27         }
28         //身份证不合格的就返回它的错误码  可以到官方文档查看具体的错误类型
29         result.setCode("200");
30         result.setData("身份证不合法错误码为:"+idcard_number_type);
31         return result;
32 
33     }