ThinkPHP实现的rsa非对称加密类示例


Posted in PHP onMay 29, 2018

本文实例讲述了ThinkPHP实现的rsa非对称加密类。分享给大家供大家参考,具体如下:

公钥加密后的字符串是一直变化的,但是用私钥解密后的内容仍然是相同的,这是为了加密数据使用的。

私钥加密的字符串是不会变化的,即使暴露在外网上别人截取时如果没有公钥也是看不出来内容的,仅允许给予公钥的第三方来解密并看到内容,实际作用相当于签名功能,如果能拿到未加密的内容,说明一定是信任方的数据,因为有他的签名啊。

其实这种非对称加密技术可以用于单点登录中去,安全级别高,能解密获取到内容应该就是信任方的数据。

<?php
namespace Common\Org;
class RsaCrypt {
 const CERPATH ='../Application/Runtime/Data/server.cer'; //生成证书路径
 const PFXPATH = '../Application/Runtime/Data/server.pfx'; //秘钥文件路径
 const FILEDIR = '../Application/Runtime/Data/';
  /**
  * 生成公钥私钥
  */
  public static function generateCertKey()
  {
  $dn = array('countryName'=>'CN', 'stateOrProvinceName'=>'beijing', 'localityName'=>'beijing','organizationName'=>'clcw',
    'organizationalUnitName'=>'clcw', 'commonName'=>'clcw', 'emailAddress'=>'service@clcw.com.cn');
  $privkeypass = 'secret';  //私钥密码
  $numberOfDays = 365;   //有效时长,单位为天
  //生成证书
  $privkey = openssl_pkey_new();
  $csr = openssl_csr_new($dn, $privkey);
  $sscert = openssl_csr_sign($csr, null, $privkey, $numberOfDays);
  openssl_x509_export_to_file($sscert, self::CERPATH);
  openssl_pkcs12_export_to_file($sscert, self::PFXPATH, $privkey, $privkeypass);
  (file_exists(self::CERPATH)) or die('公钥的文件路径错误');
  (file_exists(self::PFXPATH)) or die('密钥的文件路径错误');
  }
  public static function verifyData($originData, $decryptData)
  {
  $cer_key = file_get_contents(self::$cerpath);
  $cer = openssl_x509_read($cer_key);
  $res = openssl_verify($originData, $decryptData, $cer);
  var_dump($res);
  }
  /**
  * 生成公钥私钥文件
  * @param $appName string 应用名称
  */
  public static function generateKey($appName='')
  {
  $result = ['status'=>0, 'msg'=>''];
  if (!extension_loaded('openssl') ) {
   $result['msg'] = 'php需要openssl支持';
  }
  //创建公钥
  $res = openssl_pkey_new();//array('private_key_bits'=>512) 这一串参数不加,否则只能加密54个长度的字符串
  //提取私钥
  openssl_pkey_export($res, $privatekey);
  //生成公钥
  $public_key = openssl_pkey_get_details($res);
  $publickey = $public_key['key'];
  // $path = self::FILEDIR.$appName;
  try{
   // file_put_contents($path.'_public.pem', $publickey);
   // file_put_contents($path.'_private.pem', $privatekey);
   $result['status'] = 1;
   $result['publickey'] = $publickey;
   $result['privatekey'] = $privatekey;
  }catch(\Exception $e) {
   // throw new \Exception($e->getMessage());
   $result['msg'] = $e->getMessage();
  }
  return $result;
  }
  /**
  * 用私钥加密数据
  * @param $data string 需要加密的字符串(最好不要超过200个字符)
  * @param $appName string 应用名称
  */
  public static function privateEncrypt($data, $appName)
  {
  $result = ['status'=>0, 'msg'=>''];
  $privatekey = C($appName.'.PRIVATE_KEY');
  $myinfo = 'In '.__METHOD__.',privatekey:'.$privatekey."\n";
  file_put_contents('/tmp/shiyf.log', $myinfo, FILE_APPEND);
  //生成resource类型的密钥,如果密钥文件内容被破坏,openssl_pkey_get_private函数返回false
  $privatekey = openssl_pkey_get_private($privatekey);
  if (empty($privatekey)) {
   $result['msg'] = '密钥不可用';
  }
  $encryptData = '';
  //用私钥加密
  if (openssl_private_encrypt($data, $encryptData, $privatekey)) {
   $result['msg'] = base64_encode($encryptData);
   $result['status'] = 1;
  } else {
   $result['msg'] = '加密失败!';
  }
  return $result;
  }
  /**
  * 用公钥解密数据
  * @param $data string 需要解密的字符串(最好不要超过200个字符)
  * @param $appName string 应用名称
  */
  public static function publicDecrypt($data, $appName)
  {
  $result = ['status'=>0, 'msg'=>''];
  $data = base64_decode($data);
  $publickey = C($appName.'.PUBLIC_KEY');
  //生成resource类型的公钥,如果公钥文件内容被破坏,openssl_pkey_get_public函数返回false
  $publickey = openssl_pkey_get_public($publickey);
  if (empty($publickey)) {
   $result['msg'] = '公钥不可用';
  }
  //解密数据
  $decryptData = '';
  if (openssl_public_decrypt($data, $decryptData, $publickey)) {
   $result['msg'] = $decryptData;
   $result['status'] = 1;
  } else {
   $result['msg'] = '解密失败';
  }
  return $result;
  }
  /**
  * 用公钥加密数据
  * @param $data string 需要加密的字符串(最好不要超过200个字符)
  * @param $appName string 应用名称
  */
  public static function publicEncrypt($data, $publickey)
  {
  $result = ['status'=>0, 'msg'=>''];
  //生成resource类型的公钥,如果公钥文件内容被破坏,openssl_pkey_get_private函数返回false
  $publickey = openssl_pkey_get_public($publickey);
  if (empty($publickey)) {
   $result['msg'] = '公钥不可用';
  }
  $encryptData = '';
  //用私钥加密
  if (openssl_public_encrypt($data, $encryptData, $publickey)) {
   $result['msg'] = base64_encode($encryptData);
   $result['status'] = 1;
  } else {
   $result['msg'] = '加密失败!';
  }
  return $result;
  }
  /**
  * 用私钥加密数据
  * @param $data string 需要解密的字符串(最好不要超过200个字符)
  * @param $appName string 应用名称
  */
  public static function privateDecrypt($data, $appName)
  {
  $result = ['status'=>0, 'msg'=>''];
  $data = base64_decode($data);
  $privatekey = C($appName.'.PRIVATE_KEY');
  //生成resource类型的私钥,如果私钥文件内容被破坏,openssl_pkey_get_public函数返回false
  $privatekey = openssl_pkey_get_private($privatekey);
  if (empty($privatekey)) {
   $result['msg'] = '私钥不可用';
  }
  //解密数据
  $decryptData = '';
  if (openssl_private_decrypt($data, $decryptData, $privatekey)) {
   $result['msg'] = $decryptData;
   $result['status'] = 1;
  } else {
   $result['msg'] = '解密失败';
  }
  return $result;
  }
}
PHP 相关文章推荐
一个简单的PHP投票程序源码
Mar 11 PHP
五个PHP程序员工具
May 26 PHP
PHP中实现生成静态文件的方法缓解服务器压力
Jan 07 PHP
将php数组输出html表格的方法
Feb 24 PHP
PHP实现自动登入google play下载app report的方法
Sep 23 PHP
ThinkPHP独立分组使用的注意事项
Nov 25 PHP
PHP关联数组实现根据元素值删除元素的方法
Jun 26 PHP
Linux系统递归生成目录中文件的md5的方法
Jun 29 PHP
修复ShopNC使用QQ 互联时提示100010 错误
Nov 08 PHP
php利用云片网实现短信验证码功能的示例代码
Nov 18 PHP
分享5个非常有用的Laravel Blade指令
May 30 PHP
Laravel 微信小程序后端搭建步骤详解
Nov 26 PHP
PHP中实现中文字串截取无乱码的解决方法
May 29 #PHP
php实现表单提交上传文件功能
May 28 #PHP
PHP封装的非对称加密RSA算法示例
May 28 #PHP
thinkPHP3.2.3结合Laypage实现的分页功能示例
May 28 #PHP
Windows下wamp php单元测试工具PHPUnit安装及生成日志文件配置方法
May 28 #PHP
PHP测试框架PHPUnit组织测试操作示例
May 28 #PHP
php empty 函数判断结果为空但实际值却为非空的原因解析
May 28 #PHP
You might like
谈谈PHP语法(4)
2006/10/09 PHP
php 页面执行时间计算代码
2008/12/04 PHP
浅析iis7.5安装配置php环境
2015/05/10 PHP
Yii2 hasOne(), hasMany() 实现三表关联的方法(两种)
2017/02/15 PHP
thinkPHP5.0框架URL访问方法详解
2017/03/18 PHP
jWiard 基于JQuery的强大的向导控件介绍
2011/10/28 Javascript
jquery跟js初始化加载的多种方法及区别介绍
2014/04/02 Javascript
基于javascript实现图片懒加载
2016/01/05 Javascript
JavaScript实现设计模式中的单例模式的一些技巧总结
2016/05/17 Javascript
knockoutjs动态加载外部的file作为component中的template数据源的实现方法
2016/09/01 Javascript
用jquery的attr方法实现图片切换效果
2017/02/05 Javascript
JS验证字符串功能
2017/02/22 Javascript
Vue之Watcher源码解析(2)
2017/07/19 Javascript
js实现拖拽上传图片功能
2017/08/01 Javascript
浅析为什么a=&quot;abc&quot; 不等于 a=new String(&quot;abc&quot;)
2017/10/25 Javascript
vue+webpack实现异步加载三种用法示例详解
2018/04/24 Javascript
vue动画效果实现方法示例
2019/03/18 Javascript
JS实现贪吃蛇游戏
2019/11/15 Javascript
python网络编程学习笔记(一)
2014/06/09 Python
python使用response.read()接收json数据的实例
2018/12/19 Python
Python语言检测模块langid和langdetect的使用实例
2019/02/19 Python
python图像处理入门(一)
2019/04/04 Python
基于spring boot 日志(logback)报错的解决方式
2020/02/20 Python
python 删除系统中的文件(按时间,大小,扩展名)
2020/11/19 Python
matplotlib常见函数之plt.rcParams、matshow的使用(坐标轴设置)
2021/01/05 Python
css3实现圆锥渐变conic-gradient效果
2020/02/12 HTML / CSS
Chain Reaction Cycles俄罗斯:世界上最大的在线自行车商店
2019/08/27 全球购物
NET程序员上机面试题
2015/05/23 面试题
计算机网络专业个人的自我评价
2013/10/17 职场文书
党的群众路线批评与自我批评发言稿
2014/10/16 职场文书
外贸业务员岗位职责
2015/02/13 职场文书
2015年科室工作总结
2015/04/10 职场文书
有关朝花夕拾的读书笔记
2015/06/29 职场文书
关于办理居住证的介绍信模板
2019/11/27 职场文书
css布局巧妙技巧之css三角示例的运用
2022/03/16 HTML / CSS
Golang数据类型和相互转换
2022/04/12 Golang