PHP 怎么电子签章

wen PHP项目 3

本文目录导读:

PHP 怎么电子签章

  1. 电子签章的本质:不是“图片盖章”,而是“数字签名”
  2. PHP 实现电子签章的核心技术栈
  3. 三种主流实现方案对比
  4. 手把手实战:基于 OpenSSL + PDF 的 PHP 签名代码示例
  5. 常见问题与合规避坑指南(含问答)
  6. 结语:技术选型建议与 SEO 延伸


PHP 怎么电子签章?从原理到实战,一文搞定合规数字签名**


目录导读

  1. 电子签章的本质:不是“图片盖章”,而是“数字签名”
  2. PHP 实现电子签章的核心技术栈(哈希、非对称加密、时间戳)
  3. 三种主流实现方案对比(第三方 API / 开源库 / 自研 PKI)
  4. 手把手实战:基于 OpenSSL + PDF 的 PHP 签名代码示例
  5. 常见问题与合规避坑指南(含问答)
  6. 技术选型建议与 SEO 关键词延伸

电子签章的本质:不是“图片盖章”,而是“数字签名”

很多 PHP 开发者最初会误解“电子签章”就是往 PDF 上贴一张红章 PNG,但真正合规的电子签章(尤其在中国《电子签名法》框架下)必须具备三个核心属性:

  • 身份可信:签名者身份经过实名认证(CA 机构颁发数字证书)。
  • 防篡改:签名后文档任何字节改动,验签都会失败。
  • 不可抵赖:签名与文档内容、签名时间强绑定,产生法律效力。

PHP 实现电子签章的本质是利用非对称加密算法(RSA/ECC)对文档摘要进行加密,并将签名值、证书信息、时间戳嵌入文档(通常是 PDF)的特定结构(如 /Sig 签名域)。


PHP 实现电子签章的核心技术栈

技术组件 作用 PHP 对应库/扩展
哈希算法 (SHA-256) 计算文档唯一指纹 hash() 原生函数
非对称加密 (RSA) 私钥签名、公钥验签 openssl_sign() / openssl_verify()
数字证书 (X.509) 绑定公钥与身份信息 openssl_x509_parse()
PDF 签名域 将签名值嵌入 PDF TCPDF / FPDI / SetaPDF(商业)
时间戳服务 (TSA) 证明签名时间合规 第三方 TSA 接口(如中国网证通)

三种主流实现方案对比

方案类型 优点 缺点 适用场景
第三方 API(如 e签宝、法大大、腾讯电子签) 合规性强、免运维、内置实名认证 按次收费、有网络依赖 小微企业、短期项目
开源库组合(OpenSSL + TCPDF) 免费、可控性高 需自建 CA 信任链,法律效力较弱 内部流程、非强合规场景
企业自研 PKI(对接 CFCA / 国密 SM2) 完全自主可控、符合国密标准 开发周期长、需申请证书资质 银行、政务、大型国企

SEO 提示:搜索量较高的长尾词包括“PHP pdf 电子签名库”“php sm2 国密签名”“laravel 电子签章”等,本文覆盖前两者。


手把手实战:基于 OpenSSL + PDF 的 PHP 签名代码示例

以下代码实现简化的“数字签名”(不嵌入 PDF 可视化章,但法律效力完整),若需可视化红章,可叠加 TCPDF 的图像叠加功能。

<?php
// 1. 读取待签名PDF文件内容(二进制)
$docContent = file_get_contents('contract.pdf');
// 2. 计算哈希摘要(防篡改)
$docHash = hash('sha256', $docContent, true);
// 3. 加载企业私钥(.pem格式,需密码保护)
$privateKey = openssl_pkey_get_private('file://mykey.pem', 'your_passphrase');
// 4. 执行签名(使用SHA256withRSA)
openssl_sign($docHash, $signature, $privateKey, OPENSSL_ALGO_SHA256);
// 5. 获取公钥及证书信息(用于验签方)
$certData = openssl_x509_parse(file_get_contents('mycert.pem'));
$serialNumber = $certData['serialNumberHex'];
// 6. 将签名值、签名算法、证书序列号、时间戳写入一个JSON(或PDF元数据)
$signInfo = [
    'signature' => base64_encode($signature),
    'algo' => 'RSA-SHA256',
    'cert_sn' => $serialNumber,
    'signed_at' => date('c', time()),
    'digest' => base64_encode($docHash)
];
file_put_contents('signature_data.json', json_encode($signInfo));
// 7. 验签流程(供对方验证)
$publicKey = openssl_pkey_get_public(file_get_contents('mycert.pem'));
$verifyResult = openssl_verify($docHash, $signature, $publicKey, OPENSSL_ALGO_SHA256);
echo $verifyResult === 1 ? '✅ 签名有效,文档未被篡改' : '❌ 签名无效';
?>

关键说明

  • 真实生产环境需要将 signature_data.json 嵌入 PDF 的 /Annots 或 XMP 元数据中(可使用 SetaPDF-Signer 库,但收费约 $99)。
  • 若需符合《电子签名法》的“可靠电子签名”,必须接入第三方时间戳服务,否则法院可能不采信签名时间。

常见问题与合规避坑指南(含问答)

Q1:PHP 电子签章用 RSA 和 SM2(国密)有什么区别?
A:RSA 是国际通用算法,易与海外系统对接;SM2 是中国国密标准(GM/T 0003),银行/政务强制要求,PHP 实现 SM2 可使用扩展 openssl(PHP 7.4+ 支持 SM2 签名)或 bignum 库,若面向国内司法诉讼,建议优先选 SM2。

Q2:上传到服务器上的“白底红章”图片直接盖在 PDF 上算有效吗?
A:无效,图片可复制、可PS,无法防篡改,真正的电子签章必须包含数字签名值,且签名值绑定文档内容哈希,如果仅做内部预览,可以贴图;但法律纠纷时法院会委托鉴定机构校验数字签名。

Q3:PHP 使用 TCPDF 生成 PDF 时如何添加可视化签章域?
A:TCPDF 本身不支持数字签名(只支持图片水印),推荐方案:

  • 先用 FPDI 导入现有 PDF 页面;
  • 在指定坐标插入印章 PNG(->ImageSVG());
  • 再调用 TCPDF->setSignature()(但该函数只是嵌入证书,不执行标准 PAdES)。
    真正合规可试用开源库 KraftHaus/Hydra 或商业 SetaPDF-Signer

Q4:验证签名的 PHP 代码需要给客户哪些“零件”?
A:通常提供三样:

  1. 原始 PDF 文件(带签名数据)
  2. 签名方公钥证书(.cer)
  3. 验签 PHP 脚本(或在线验签页面)

关键:私钥绝不能泄露;证书过期前需重新签名。


技术选型建议与 SEO 延伸

综合来看,如果你的项目面向企业外部合同,强烈建议直接购买第三方电子签 API(如 e签宝、法大大),因为它们已做了人脸识别、短信验证、时间戳、司法存证全链路,PHP 只需调用 curl 接口即可,开发成本低于自研的 1/10。

若仅用于内部流程(如审批单、报销单),用本文的 OpenSSL 方案即可,但需自己维护证书生命周期。

SEO 延伸阅读(其他用户也在搜):

  • “php 防止文件篡改”
  • “pdf 数字化签名 php library”
  • “electron signature php codeigniter”
  • “国密 SM2 php openssl 不支持怎么办”(答案:安装 openssl 1.1.1+ 并启用 sm2 参数,或使用 sodium 扩展)

希望这篇 PHP 电子签章全解析能帮到你,动手前先小范围测试,尤其是 证书链验证PDF 兼容性(某些 PDF 阅读器会拒绝无法识别的签名域)。

抱歉,评论功能暂时关闭!