• 聊聊加密那些事儿


    (本文阅读预计10分钟)

    前言:

    最近公司在对接第四方采宝服务商,用于聚合门店支付。之前对接微信支付宝都有sdk下载,直接调用服务即可,很多加密中间知识有盲区。

    确实,任何时候都得注重基础。

    想起了Swoole作者韩天峰曾提及:

    不重视基础。就好比练武功,只求速成,不修炼内功和心法,只练各种招式,这样能高到哪里去?”

    https://blog.csdn.net/ty_hf/article/details/74942935

    这回就把知识的不扎实,翻出来再晒晒理理吧,是学习,也是潜下心来,故有此文。

    目录

    一.RSA与RSA2有什么区别

    二. 加密类型与用途

    三. 本次碰到的问题

    四. 注意事项


    一.RSA与RSA2有什么区别

    1.说这个之前,需要再了解下密码学基本知识

    知其所以然,很好的一篇图文文章,传送门:数字签名是什么?

    2.为啥叫RSA

    让人瞌睡的什么原理算法这里就不提了

    百度百科粘贴的一段话:

    RSA是1977年由罗纳德·李维斯特(Ron Rivest)、阿迪·萨莫尔(Adi Shamir)和伦纳德·阿德曼(Leonard Adleman)一起提出的。

    当时他们三人都在麻省理工学院工作。RSA就是他们三人姓氏开头字母拼在一起组成的。

    3.再说说RSA2

    来源:蚂蚁金服在原来RSA的SHA1WithRSA签名算法的基础上,新增了支持SHA256WithRSA的签名算法。便产生的RSA2

    优点:该算法在摘要算法上比SHA1WithRSA有更强的安全能力。

    换句话说,RSA2这个名词来自于蚂蚁金服,并没有出现新的技术,它只是RSA的升级版,更安全。

    (忽然想起以前有种md6加密算法,本质是md5了两次)

    开放平台签名算法名称

    标准签名算法名称

    备注

    RSA2

    SHA256WithRSA

    强制要求RSA密钥的长度至少为2048

    RSA

    SHA1WithRSA

    对RSA密钥的长度不限制,推荐使用2048位以上

    4.php如何使用RSA

    在php官方扩展代码openssl.php中,截取片段如下:

    我们在使用rsa加密时,通过openssl_sign实现

    if ("RSA2" == $signType) {
    	openssl_sign($data, $sign, $res, OPENSSL_ALGO_SHA256);//RSA2加密
    } else {
    	openssl_sign($data, $sign, $res,OPENSSL_ALGO_SHA1);//RSA加密
    }

    不难看出,RSA与RSA2的切换时通过第4个参数实现

    /**
     * Used as default algorithm by <b>openssl_sign</b> and
     * <b>openssl_verify</b>.
     * @link https://php.net/manual/en/openssl.constants.php
     */
    define ('OPENSSL_ALGO_SHA1', 1);
    define ('OPENSSL_ALGO_MD5', 2);
    define ('OPENSSL_ALGO_MD4', 3);
    define ('OPENSSL_ALGO_MD2', 4);
    define ('OPENSSL_ALGO_DSS1', 5);
    define ('OPENSSL_ALGO_SHA224', 6);
    define ('OPENSSL_ALGO_SHA256', 7);
    define ('OPENSSL_ALGO_SHA384', 8);
    define ('OPENSSL_ALGO_SHA512', 9);
    define ('OPENSSL_ALGO_RMD160', 10);

    二 加密类型与用途

    加密类型有三种:对称加密,非对称加密和其他

    1.对称加密

    a.定义:加密密钥和解密密钥是相同的

    b.问题:泄漏密钥就意味着任何人都可以对他们发送或接收的消息解密,所以密钥的保密性对通信的安全性至关重要。

    c.举例:DES,AES等

    2.非对称加密

    a.定义:有两种密钥,一种是公共密钥(正如其名,这是一个可以公开的密钥值),一种是私人密钥(对外保密只有自己知道)

    (两种密钥可以互相加解密,公钥加密的信息,只有我们的唯一的私钥可以解密,反之亦如此)

    b.场景:

    1).公钥加密信息,私钥解开;//常规数据加密,比如微信支付宝传输过程中

    2).私钥加密信息,公钥解开;//常用于数据验签,

    3).双方公钥加密,在特定排序下的数据加密后做结果对比;//同样用于验签作用,【这也是我们方案中采用的方法】

    c.举例:RSA、DSA等

    3.其他

    有些同学可能会问,常用的md5、hash算法(sha1、sha256、sha512、sha1024等)怎么没被提及,

    其实准确的说,md5和hash算法不能算是加密算法,它们都属于信息摘要算法,可以为不同的信息生成独一无二的信息摘要,而它们都属于不可逆算法,

    三. 本次碰到的问题

    1.php报错,公钥不可用

    key parameter is not a valid public key error in openssl_public_encrypt()

    原因是因为证书格式不正确,RSA单独签名方法未做字符串处理

    需要把密钥由一串变成每行64位,

    解决:

    $public_key = "-----BEGIN PUBLIC KEY-----
    " .
        wordwrap($public_key_content, 64, "
    ", true) .
        "
    -----END PUBLIC KEY-----";

    2. 获取加密值时,openssl_pkey_get_public返回false

    解决:在rsa加密时,被加密的明文长度最大为公钥长度-11,比如数据长度300,那么公钥长度必须大于311,否则失败返回false

    3.rsa2的使用函数

      // 4. 获取rsa2的密钥
      $public_key_c = Env::get('root_path') . DIRECTORY_SEPARATOR . 'config' . DIRECTORY_SEPARATOR . 'caibao_pem' . DIRECTORY_SEPARATOR . 'rsa_public_key.pem';
    
      $public_key_content = file_get_contents($public_key_c);
    
      $public_key = "-----BEGIN PUBLIC KEY-----
    " .
          wordwrap($public_key_content, 64, "
    ", true) .
          "
    -----END PUBLIC KEY-----";
    
      $res = openssl_get_publickey($public_key);
    
      //对比两种签名,相同返回返回true ,不同返回false
      $result = (openssl_verify($str, base64_decode($sign), $res, OPENSSL_ALGO_SHA256)===1);
    
      openssl_free_key($res);

    四. 注意事项

    1.密码加密最好md5加盐salt,

    2.尽量减少md5等摘要唯一不可逆加密算法,容易被攻破,愿不愿意的问题

    五.参考文章

    支付宝:https://docs.open.alipay.com/291/105974

    现代 PHP 中的密码安全性:https://www.ibm.com/developerworks/cn/web/wa-php-renewed_2/

    加密算法比较:SHA1,SHA256,MD5 :https://blog.csdn.net/WuLex/article/details/81477097

    author: hann

  • 相关阅读:
    每日日报
    Java学习
    Java学习
    Java学习
    Java学习
    Java学习
    Java学习
    Java学习
    Java学习
    JAVA日报
  • 原文地址:https://www.cnblogs.com/widgetbox/p/12035720.html
Copyright © 2020-2023  润新知