通过网页调用身份证阅读器http websocket方法-华视电子————仙盟创梦IDE

发布于:2025-08-16 ⋅ 阅读:(20) ⋅ 点赞:(0)

读取代码

<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Document</title>
</head>

<body>
    <h1>读身份证+M1卡示例</h1><br>
    <div id="message"></div>
    <div>
        <button id="OcrRecognition" onclick="OcrRecognition()">连接服务</button>
        <tr>
            <td align="right">超时(毫秒ms):</td>
            <td><input type="text" id="timeOut" size="49" style="width:100px;" value="10000"></td>
        </tr>
        <tr>
            <td align="right">日志:</td>
            <td><input type="text" id="partyLog" size="49" style="width:400px;" readonly="readonly"></td>
        </tr>
    </div>
    <h1>M1卡</h1><br>
    <div>
        <tr>
            <td align="right">块号:</td>
            <td><input type="text" id="Block" size="49" style="width: 100px;" value="2"></td>
        </tr>
        <tr>
            <td align="right">密码:</td>
            <td><input type="text" id="KeyBuf" size="49" style="width:200px;" value="FF FF FF FF FF FF"></td>
        </tr>
        <tr>
            <td align="right">写入值:</td>
            <td><input type="text" id="WriteBuf" size="49" style="width:200px;" value="01 02 03 04 05 06"></td>
        </tr>
    </div>
    <div>
        <button id="RequestM1" onclick="Request()" style="width:160px;">M1卡认证</button>
        <button id="ReadM1" onclick="ReadM1()" style="width:160px;">读M1卡</button>
        <button id="WriteM1" onclick="WriteM1()" style="width:160px;">写M1卡</button>
        <button id="GetFisCardID" onclick="GetFisCardID()" style="width:160px;">银行卡信息</button>
    </div>
    <h1>读身份证</h1><br>
    <div>

        <button id="TimeOutReadIDCard" onclick="TimeOutReadIDCard()">时间段内读取身份证</button>
        <button id="ReadIDCard" onclick=" ReadIDCard()">读取身份证</button>
        <button id="ReadIDCardNoJudge" onclick="ReadIDCardNoJudge()">不拿起读身份证</button>
        <button id="ReadSAMID" onclick="ReadSAMID()">获取安全模块号</button>
    </div>

    <table border="0" width="100%" cellpadding="0" cellspacing="10">
       
        <tr>
            <td align="right">姓名:</td>
            <td><input type="text" id="partyName" size="49" style="width:400px;" readonly="readonly"></td>
        </tr>
        <tr>
            <td align="right">性别:</td>
            <td><input type="text" id="gender" size="49" style="width:400px;" readonly="readonly"></td>
        </tr>
        <tr>
            <td align="right">民族:</td>
            <td><input type="text" id="nation" size="49" style="width:400px;" readonly="readonly"></td>
        </tr>
        <tr>
            <td align="right">出生日期:</td>
            <td><input type="text" id="bornDay" size="49" style="width:400px;" readonly="readonly">(要求格式为:yyyyMMdd,长度为8)</td>
        </tr>
        <tr>
            <td align="right">住址:</td>
            <td><input type="text" id="certAddress" size="49" style="width:400px;" readonly="readonly"></td>
        </tr>
        <tr>
            <td align="right">身份证号:</td>
            <td><input type="text" id="certNumber" size="49" style="width:400px;" readonly="readonly">(居民身份号码,长度18位)</td>
        </tr>
        <tr>
            <td align="right">签发机关:</td>
            <td><input type="text" id="certOrg" size="49" style="width:400px;" readonly="readonly"></td>
        </tr>
        <tr>
            <td align="right">开始期限:</td>
            <td><input type="text" id="effDate" size="49" style="width:400px;" readonly="readonly">(要求格式为:yyyyMMdd,长度为8)</td>
        </tr>
        <tr>
            <td align="right">结束期限:</td>
            <td><input type="text" id="expDate" size="49" style="width:400px;" readonly="readonly">(要求格式为:yyyyMMdd,长度为8,或者是“长期”)</td>
        </tr>
        <tr>
            <td align=right>照片:</td>
            <td><IMG style="WIDTH: 124px; HEIGHT: 150px" name=PhotoDisplay></td>
        </tr>
    </table>
</body>
<script type="text/javascript">
    let websockets;
    let isconncet = false;
    let Command = 1;
    
    //创建一个数组对象用于存放当前的连接的状态,以便在页面上实时展示出来当前的状态
    let statusArr = [
        { state: 0, value: '正在连接' },
        { state: 1, value: '已建立连接' },
        { state: 2, value: '正在关闭连接' },
        { state: 3, value: '已关闭连接' },
    ]
    /**
    *   建立连接
    *
    */
    function OcrRecognition() {
        if (!isconncet) {
            // 1. 创建websockets对象,参数为服务器websockets地址
            let hostname = location.hostname;
            var url = "ws:127.0.0.1:9001"
            websockets = new WebSocket(url);

            // 2.监听websocket的状态变化,接收的信息,关闭时的状态

            //监听连接状态的变化
            websockets.onopen = (event) => socketChange();

            //监听接收消息的情况
            websockets.onmessage = (res) => {
                if (res.data == "failed to obtain ID card information") {
                    document.querySelector("#message").innerHTML += `<p>接收数据: ${res.data}</p>`
                    return;
                }
                var alldata = res.data.split("|");
                if (Command < 6) {
                    // 读身份证
                    if (alldata.length >= 17) {
                        document.getElementById("partyLog").value = "读卡成功";
                        document.getElementById("partyName").value = alldata[3];
                        document.getElementById("nation").value = alldata[5];
                        document.getElementById("gender").value = alldata[4];
                        document.getElementById("certAddress").value = alldata[7];
                        document.getElementById("bornDay").value = alldata[6];
                        document.getElementById("certNumber").value = alldata[8];
                        document.getElementById("certOrg").value = alldata[9];
                        document.getElementById("effDate").value = alldata[10];
                        document.getElementById("expDate").value = alldata[11];
                        document.all['PhotoDisplay'].src = 'data:image/bmp;base64,' + alldata[19];
                    }
                    else {
                        document.getElementById("partyLog").value = res.data;
                    }
                }
                else {
                    // 读M1卡
                    if (Command == 6) {
                        // 卡认证
                        if (alldata.length >= 2) {
                            document.getElementById("partyLog").value = "卡序列号:" + alldata[0] + " 卡类型:" + alldata[1];
                        }
                        else {
                            document.getElementById("partyLog").value = res.data;
                        }
                    }
                    if (Command == 7) {
                        // 读M1卡
                        if (alldata.length >= 2) {
                            document.getElementById("partyLog").value = "卡序列号:" + alldata[0] + " 块数据:" + alldata[1];
                        }
                        else {
                            document.getElementById("partyLog").value = res.data;
                        }
                    }
                    if (Command == 8) {
                        // 写M1卡
                        document.getElementById("partyLog").value = res.data;
                    }
                    if (Command == 9) {
                        // 读银行卡卡号和有效期
                        if (alldata.length >= 2) {
                            document.getElementById("partyLog").value = "银行卡卡号:" + alldata[0] + " 有效期:" + alldata[1];
                        }
                        else {
                            document.getElementById("partyLog").value = res.data;
                        }
                        
                    }
                }
            }
            //监听关闭时的状态变化
            websockets.onclose = (event) => socketChange();

        }
        else {
            closeConnect();
            document.getElementById("OcrRecognition").innerHTML = "连接服务";
        }
    }
    function TimeOutReadIDCard() {
        if (!isconncet) {
            document.getElementById("partyLog").value = "未连接服务";
        } else {
            Command = 2;
            clear();
            let paramTimeOut = document.querySelector("#timeOut").value;
            paramTimeOut = "timeout=" + paramTimeOut;
            var parameterAll = paramTimeOut;
            let val = "02?" + parameterAll;
            websockets.send(val);
        }
    }
    function ReadIDCard() {
        if (!isconncet) {
            document.getElementById("partyLog").value = "未连接服务";
        } else {
            Command = 3;
            clear();
            let paramTimeOut = document.querySelector("#timeOut").value;
            paramTimeOut = "timeout=" + paramTimeOut;
            var parameterAll = paramTimeOut;
            let val = "03?" + parameterAll;
            websockets.send(val);
        }
    }
    function ReadIDCardNoJudge() {
        if (!isconncet) {
            document.getElementById("partyLog").value = "未连接服务";
        } else {
            Command = 4;
            clear();
            let paramTimeOut = document.querySelector("#timeOut").value;
            paramTimeOut = "timeout=" + paramTimeOut;
            var parameterAll = paramTimeOut;
            let val = "04?" + parameterAll;
            websockets.send(val);
        }
    }
    function ReadSAMID() {
        if (!isconncet) {
            document.getElementById("partyLog").value = "未连接服务";
        } else {
            Command = 5;
            clear();
            let paramTimeOut = document.querySelector("#timeOut").value;
            paramTimeOut = "timeout=" + paramTimeOut;
            var parameterAll = paramTimeOut;
            let val = "05?" + parameterAll;
            websockets.send(val);
        }
    }
    function Request() {
        if (!isconncet) {
            document.getElementById("partyLog").value = "未连接服务";
        } else {
            Command = 6;
            clear();
            let paramTimeOut = document.querySelector("#timeOut").value;
            paramTimeOut = "timeout=" + paramTimeOut;
            var parameterAll = paramTimeOut;
            let val = "06?" + parameterAll;
            websockets.send(val);
        }
    }
    function ReadM1() {
        if (!isconncet) {
            document.getElementById("partyLog").value = "未连接服务";
        } else {
            Command = 7;
            clear();
            var ValuesBlock = document.querySelector("#Block").value;
            ValuesBlock = "Block=" + ValuesBlock;
            var ValuesKey = document.querySelector("#KeyBuf").value;
            ValuesKey = "Key=" + ValuesKey;
            var val = "07?" + ValuesBlock + "|" + ValuesKey;
            websockets.send(val);

        }
    }
    function WriteM1() {
        if (!isconncet) {
            document.getElementById("partyLog").value = "未连接服务";
        } else {
            Command = 8;
            clear();
            var ValuesBlock = document.querySelector("#Block").value;
            ValuesBlock = "Block=" + ValuesBlock;
            var ValuesKey = document.querySelector("#KeyBuf").value;
            ValuesKey = "Key=" + ValuesKey;
            var  ValuesWriteBuf = document.querySelector("#WriteBuf").value;
            ValuesWriteBuf = "WriteBuf=" + ValuesWriteBuf;
            var val = "08?" + ValuesBlock + "|" + ValuesKey + "|" + ValuesWriteBuf;
            websockets.send(val);
  
        }
    }
    function GetFisCardID() {
        if (!isconncet) {
            document.getElementById("partyLog").value = "未连接服务";
        } else {
            Command = 9;
            clear();
            let paramTimeOut = document.querySelector("#timeOut").value;
            paramTimeOut = "timeout=" + paramTimeOut;
            var parameterAll = paramTimeOut;
            let val = "09?" + parameterAll;
            websockets.send(val);
        }
    }

    /**
    *   socket状态变化
    *
    */
    function socketChange() {
        let state = websockets.readyState;
        let val = statusArr.map((item) => {
            if (item.state == state) {
                return item.value
            }
        });

        //实时显示状态的变化
        document.getElementById("partyLog").value = val;
        //读身份证
        if (1 == state) {
            isconncet = true;
            document.getElementById("OcrRecognition").innerHTML = "断开服务";
        }
        if (3 == state) {
            isconncet = false;
        }
    }
    /**
    *   关闭连接
    *
    */
    function closeConnect() {
        websockets.close();
    }
    /**
    *   关闭连接
    *
    */
    function clear() {
        document.getElementById("partyLog").value = "";
        document.getElementById("partyName").value = "";
        document.getElementById("nation").value = "";
        document.getElementById("gender").value = "";
        document.getElementById("certAddress").value = "";
        document.getElementById("bornDay").value = "";
        document.getElementById("certNumber").value = "";
        document.getElementById("certOrg").value = "";
        document.getElementById("effDate").value = "";
        document.getElementById("expDate").value = "";
        document.all['PhotoDisplay'].src = "";
    }

</script>

</html>

身份证与 M1 卡读取交互页面功能概述

在酒店、金融、政务等需要身份核验与卡证交互的场景中,便捷高效的读卡工具至关重要。以下介绍的 HTML 页面便是一款集成身份证与 M1 卡读取功能的交互界面,通过 WebSocket 技术实现前端与后端服务的实时通信,为各类场景下的卡证信息采集提供了完整解决方案。

核心功能架构

该页面以模块化设计整合了两类核心功能:身份证信息读取与 M1 卡交互。整体界面分为功能控制区与信息展示区,通过简洁的按钮操作触发不同的读卡指令,配合输入框配置参数,最终将读取结果实时显示在对应区域。

在身份证读取方面,页面提供了四种操作模式:时间段内读取、单次读取、不拿起持续读取以及获取安全模块号(SAMID)。这些功能覆盖了不同场景下的使用需求 —— 例如酒店前台可通过 “时间段内读取” 功能在规定时间内等待旅客放置身份证,而 “不拿起读身份证” 则适用于需要连续核验的场景。

M1 卡交互功能则包含认证、读取、写入及银行卡信息获取,支持自定义块号、密码与写入值,满足对 M1 卡进行数据读写的多样化需求。无论是会员系统的卡片信息更新,还是门禁卡的权限配置,都可通过这些功能实现。

技术实现逻辑

页面采用 WebSocket 协议建立前端与后端服务的实时连接,通过ws:127.0.0.1:9001地址与本地服务通信。当用户点击 “连接服务” 按钮时,前端创建 WebSocket 实例,监听连接状态变化并同步显示在日志区域;连接建立后,所有操作指令(如读卡、写卡)通过特定格式的字符串(如03?timeout=10000)发送至后端。

后端返回的数据经 “|” 符号分割后,由前端按预设规则解析并填充至对应字段。例如身份证信息包含姓名、性别、民族等 17 项以上数据,分别对应页面中的输入框;M1 卡数据则根据操作类型(认证、读写)显示序列号、块数据等内容。此外,身份证照片通过 Base64 编码格式实时渲染至页面,实现信息可视化展示。

应用场景价值

该页面的设计充分考虑了实际使用场景的需求:超时时间设置可避免因设备响应延迟导致的操作卡顿;日志区域实时反馈操作状态,便于快速排查连接或读卡失败问题;模块化的功能分区使操作人员能迅速定位所需功能,降低学习成本。

阿雪技术观

在科技发展浪潮中,我们不妨积极投身技术共享。不满足于做受益者,更要主动担当贡献者。无论是分享代码、撰写技术博客,还是参与开源项目维护改进,每一个微小举动都可能蕴含推动技术进步的巨大能量。东方仙盟是汇聚力量的天地,我们携手在此探索硅基生命,为科技进步添砖加瓦。

Hey folks, in this wild tech - driven world, why not dive headfirst into the whole tech - sharing scene? Don't just be the one reaping all the benefits; step up and be a contributor too. Whether you're tossing out your code snippets, hammering out some tech blogs, or getting your hands dirty with maintaining and sprucing up open - source projects, every little thing you do might just end up being a massive force that pushes tech forward. And guess what? The Eastern FairyAlliance is this awesome place where we all come together. We're gonna team up and explore the whole silicon - based life thing, and in the process, we'll be fueling the growth of technology.  


网站公告

今日签到

点亮在社区的每一天
去签到