一、http和https的区别与原理

介绍原理的博文太多了,这里列出一篇详细的:

IOS 使用自签名证书开发HTTPS文件传输

二、证书的类型和自制证书生成

1.什么是数字证书(Certificate)

在HTTPS的传输过程中,有一个非常关键的角色——数字证书,那什么是数字证书?又有什么作用呢?

所谓数字证书,是一种用于电脑的身份识别机制。由数字证书颁发机构(CA)对使用私钥创建的签名请求文件做的签名(盖章),表示CA结构对证书持有者的认可。数字证书拥有以下几个优点:

  1. 使用数字证书能够提高用户的可信度
  2. 数字证书中的公钥,能够与服务端的私钥配对使用,实现数据传输过程中的加密和解密
  3. 在证认使用者身份期间,使用者的敏感个人数据并不会被传输至证书持有者的网络系统上

X.509证书包含三个文件:key,csr,crt。

  • key是服务器上的私钥文件,用于对发送给客户端数据的加密,以及对从客户端接收到数据的解密
  • csr是证书签名请求文件,用于提交给证书颁发机构(CA)对证书签名
  • crt是由证书颁发机构(CA)签名后的证书,或者是开发者自签名的证书,包含证书持有人的信息,持有人的公钥,以及签署者的签名等信息

备注:在密码学中,X.509是一个标准,规范了公开秘钥认证、证书吊销列表、授权凭证、凭证路径验证算法等。

关于这三种证书的区别和原理,以及前两种证书的申请方式,网上介绍太多了,大家可以自行搜索。

2.付费商业证书

要钱。

3.免费商业证书

腾讯云和阿里云都能申请免费商业证书,好像都是一年,一年到期怎么续签不太清楚。腾讯云申请免费商业证书没试过,阿里云现在申请免费商业证书步骤比较深。

4.自制证书

工具:

OpenSSL ssl的开源实现,几乎实现了市面上所有的加密

libcrypto: 通用加密库, 任何软件要实现加密功能 链接调用这个库

libssl: TLS/SSL 加密库

openssl: 命令行工具 多功能多用途工具 实现私有证书颁发机构

子命令:

genrsa [-out filename] [-passout arg] [numbits]

generate an RSA private key

生成一个 RSA 的私钥 (公钥是从私钥中提取的,有了私钥 就有公钥)

openssl rsa -in ca.key -pubout 提取私钥

创建证书的基本流程

  • 生成自己的服务端私钥 Server Key

  • 输入基本信息并用私钥签名生成CSR 证书签名请求(csr中间文件可以不生成,直接生成crt文件)

  • 提交CSR给证书机构CA(免费或商业证书)签名生成CRT,或自己做CA签名生成CRT(自签名证书)

生成RSA服务器私钥:

openssl genrsa -out server.key 2048

输出的server.key文件就是服务器私钥,2048是密钥长度,要求不高的话用4096也可。

执行命令 生成 CSR 文件:

openssl req -new -nodes -sha256 -newkey rsa:2048 -keyout myprivate.key -out mydomain.csr

其中,

  • -new 指定生成一个新的CSR。

  • -nodes 指定私钥文件不被加密。

  • -sha256 指定摘要算法。

  • -keyout 生成私钥文件。

  • -newkey rsa:2048 指定私钥类型和长度。

因为sha1已经不安全,所以这里用了sha256,可能太旧的客户端(比如win98?)会不支持。

mydomain.csr就是生成的CSR,mydomain建议用你的网站名标识会比较方便识别。

然后按提示输入:

  • 国家

  • 公司

  • 部门

  • 通用名(即网站域名,这个必须准确,有些商业证书支持在这里用带www的域名后签发出同时支持不带www的域名)

  • email

  • 密码(可选,设置的话以后重启webserver都需要输入密码)

不生成中间csr文件的自签名证书做法(我采用的是这种方法)

非常简单,两条命令就搞定了:

1.先生成一对秘钥,把公钥做成证书 ca.key

openssl genrsa -out ca.key 2048

生成一个 2048 位的 私钥

我们可以 输出它的公钥看看:

openssl rsa -in ca.key -pubout

2. 生成证书CRT server.crt

openssl req -new -x509 -key ca.key -out server.crt -days 3650

国家 Country Name: CN

省 Stat or Province Name Shanghai

市 Locality Name Shanghai

公司 Organization Name : TX

部门 Organizational Unit Tech

主机名 Common Name www.xxxxxxx.com

邮件 Email Address 123456789@qq.com

我们可以查看证书内容 openssl x509 -text -in server.crt

最后如果可以的话 ,可以配置一个服务器签署(这个没试,不需要也可以)

openssl req -new -out server.csr -key server.key -config /etc/pki/tls/openssl.cnf

三、Nginx https配置

给nginx配置SSL证书之后,https可以正常访问,http访问显示400错误,nginx的配置如下:

server {
listen 80 default backlog=2048;
listen 443;
server_name lvtao.net;
root /var/www/html;
ssl on;
ssl_certificate /usr/local/ca/mydomain.crt;
ssl_certificate_key /usr/local/ca/mydomain.key;
}

http访问的时候,报错如下:

400 Bad Request
The plain HTTP requset was sent to HTTPS port. Sorry for the inconvenience.
Please report this message and include the following information to us.
Thank you very much!

原因是http的请求被发送到https的端口上去了,所以才会出现这样的问题。

把ssl on;这行去掉,ssl写在443端口后面。这样http和https的链接都可以用,完美解决,修改后的配置如下:

server {
listen 80 default backlog=2048;
listen 443 ssl;
server_name lvtao.net;
root /var/www/html;
ssl_certificate /usr/local/ca/mydomain.crt;
ssl_certificate_key /usr/local/ca/mydomain.key;
}

配置好之后重启Nginx,注意检查服务器443端口要打开!

四、XCode和AFNetworking支持https

1.iOS实现单向与双向验证的区别与实现,下面这篇博文讲得非常详细:

ios https 单项认证 双向认证 以及服务端配置

2.生成客户端用的der(cer)文件

  客户端最终需要的格式是.der(AF3.0以上)或者.cer(AF3.0以下),直接用服务器端的crt证书,如下方法转为客户端证书:

  crt转.der方法,打开终端,执行下面命令即可:

  openssl x509 -in /Users/mac/Desktop/ca.crt -out /Users/mac/Desktop/ca.der -outform DER

  或者 crt转.cer方法,打开终端,执行下面命令即可:

  openssl x509 -in /Users/mac/Desktop/ca.crt -out /Users/mac/Desktop/ca.cer -outform DER

3.将证书导入XCode

将我们的mydomain.der拖到我们的工程Supporting Files中,把 Copy Items if needed 的勾选上。然后把您的Add to targets 选上,点击确定。就完成了证书的导入工作。非常简单。

4.AFNetworking支持https

  AFNetworking中的AFSecurityPolicy是主要的类,我们可以这样来使用它(AFNetworking 2.6.0之前):

    AFHTTPRequestOperationManager *manager = [AFHTTPRequestOperationManager manager];NSString *cerPath                = [[NSBundle mainBundle] pathForResource:@"mytestdomain" ofType:@"der"];NSData *certData                 = [NSData dataWithContentsOfFile:cerPath];AFSecurityPolicy *securityPolicy = [[AFSecurityPolicy alloc] init];[securityPolicy setAllowInvalidCertificates:NO];[securityPolicy setPinnedCertificates:@[certData]];[securityPolicy setSSLPinningMode:AFSSLPinningModeCertificate];[securityPolicy setValidatesDomainName:YES];[securityPolicy setValidatesCertificateChain:NO];manager.securityPolicy = securityPolicy;

解析:
1)新建一个manager, 地球人都知道
2)在mainBundle中寻找我们刚才拖进项目中的https.cer, 并且将相关的数据读取出来
3)新建一个AFSecurityPolicy,并进行相应的配置
4)将这个AFSecurityPolicy 实例赋值给manager

也可以这样来使用:

AFHTTPRequestOperationManager *manager = [AFHTTPRequestOperationManager manager]; AFSecurityPolicy *securityPolicy = [[AFSecurityPolicy alloc] init];
[securityPolicy setAllowInvalidCertificates:NO];
[securityPolicy setSSLPinningMode:AFSSLPinningModeCertificate];
[securityPolicy setValidatesDomainName:YES];
[securityPolicy setValidatesCertificateChain:NO]; manager.securityPolicy = securityPolicy;

这种方式比前面那种方式要更加简便一些,主要原因在于AFNetworking会自动去搜索mainBundle下的所有der结尾的文件并放进内存中;再一一对比。因此在代码中可以省略不写。

这样一个网络请求的https的安全策略就配置好了,接下来再说明一下几个AFSecurityPolicy相关的配置
1. SSLPinningMode
SSLPinningMode 定义了https连接时,如何去校验服务器端给予的证书。

typedef NS_ENUM(NSUInteger, AFSSLPinningMode) {AFSSLPinningModeNone,AFSSLPinningModePublicKey,AFSSLPinningModeCertificate,
};

AFSSLPinningModeNone: 代表客户端无条件地信任服务器端返回的证书。
AFSSLPinningModePublicKey: 代表客户端会将服务器端返回的证书与本地保存的证书中,PublicKey的部分进行校验;如果正确,才继续进行。
AFSSLPinningModeCertificate: 代表客户端会将服务器端返回的证书和本地保存的证书中的所有内容,包括PublicKey和证书部分,全部进行校验;如果正确,才继续进行。

2. allowInvalidCertificates
  allowInvalidCertificates 定义了客户端是否信任非法证书。一般来说,每个版本的iOS设备中,都会包含一些既有的CA根证书。如果接收到的证书是iOS信任的CA根证书签名的,那么则为合法证书;否则则为“非法”证书。
  allowInvalidCertificates 就是用来确认是否信任这样的证书的。当然,我们也可以给iOS加入新的信任的CA证书。iOS已有的CA根证书,可以在这里了解到:https://support.apple.com/en-us/HT204132

3. pinnedCertificates
  pinnedCertificates 就是用来校验服务器返回证书的证书。通常都保存在mainBundle 下。通常默认情况下,AFNetworking会自动寻找在mainBundle的根目录下所有的.cer文件并保存在pinnedCertificates数组里,以校验服务器返回的证书。

4. validatesDomainName
  validatesDomainName 是指是否校验在证书中的domain这一个字段。每个证书都会包含一个DomainName, 它可以是一个IP地址,一个域名或者一端带有通配符的域名。如*.google.com, www.google.com都可以成为这个证书的DomainName。设置validatesDomainName=YES将严格地保证其安全性。

5. validatesCertificateChain
  validatesCertificateChain 指的是是否校验其证书链。
  通常来讲,一个CA证书颁发机构有很多个子机构,用来签发不同用途的子证书,然后这些子证书又再用来签发相应的证书。只有证书链上的证书都正确,CertificateChain才算验证完成。

五、一些常见问题

1.在创建manager时没有设定BaseURL则会报错

reason: 'A security policy configured with `AFSSLPinningModeCertificate` can only be applied on a manager with a secure base URL (i.e. https)'

碰到以上问题,在创建manager时指定BaseURL即可,如下:

AFHTTPSessionManager *manager = [[AFHTTPSessionManager manager] initWithBaseURL:[NSURL URLWithString:urlString]];

2.证书配置错误。如使用了一个过期或是错误的证书

运行时报错   Error Domain=NSURLErrorDomain Code=-999

同时还回返回"canceled"字样,表示任务已经放弃。

3.Serializer未配置

get要配置responseSerializer,post要配置requestSerializer,可以同时配置两个,但如果没有配置则会在调用时出错。

manager.responseSerializer = [AFHTTPResponseSerializer serializer];

manager.requestSerializer = [AFJSONRequestSerializer serializer];

4.如果测试打不开页面,请检查服务器443端口是否打开

六、参考资料:

IOS 使用自签名证书开发HTTPS文件传输

Nginx 配置 HTTPS自签名证书

iOS适配HTTPS,创建一个自签名的SSL证书(x509)具体步骤

nginx配置http和https可同时访问方法

ios https 单项认证 双向认证 以及服务端配置

AFNetworking配置https请求(这篇文章简明清晰,可以对着直接操作)

nginx 之 https 证书配置

AFNetworking之于https认证(这篇文章还讲了AFNetworking的https代理实现原理)

IOS HTTPS AFNETWORKING验证

iOS https 自制证书 单向 双向 验证,以及服务器(Nginx)配置相关推荐

  1. 云服务器 nginx配置SSL证书

    阿里云的服务器 证书已经买好了,如果不会买,可以看阿里云的帮助文档 证书准备好后,点击下载 根据你web服务器的类型,下载相应证书 我的是nginx 所以下载的是nginx的证书 在nginx安装目录 ...

  2. 【SSL】Tomcat8.5 SSL/HTTPS 安装证书 单向认证

    准备 1.为localhost生成证书库.生成证书参考这里 证书库名称:localhost.jks 证书库格式:JKS 证书库密码:localhost 证书别名:localhost 2.tomcat ...

  3. nginx配置https双向验证(ca机构证书+自签证书)

    nginx配置https双向验证 服务端验证(ca机构证书) 客户端验证(服务器自签证书) 本文用的阿里云签发的免费证书实验,下载nginx安装ssl,文件夹有两个文件 这两个文件用于做服务器http ...

  4. Java nginx 双向ssl_使用Nginx实现HTTPS双向验证的方法

    https单向验证应用广泛想必大家都很熟悉,我已经在一篇博文中分享过,这次来看看Nginx如何实现双向验证. 单向验证与双向验证的区别: 单向验证: 指客户端验证服务器端证书,服务器并不需要验证客户端 ...

  5. ios https 单项认证 双向认证 以及服务端配置

    单项认证:客户端APP包里保存一份证书 用于校验服务端证书是否合法 双向认证:单项认证以外,   客户端(不是app,这里指系统)要拥有一份证书 用于传给服务端用于校验客户端证书是否合法 分两方面讲解 ...

  6. Debain8 Tomcat8 JDK8 实现SSL双向验证

    先说说环境: 系统:Debain8.Tomcat8.JDK8 实现目标:使用JDK自带的keytool实现SSL双向加密 1.为服务器生成证书 keytool -genkey -v -alias to ...

  7. LINUX服务器最简洁的HTTPS免费证书配置方法

    注意:该方法已在多台服务器配置了免费的https证书,无论是更新还是第一次配置都运行成功:由于是免费版,每个证书都只有三个月的有效期,也无法保证安全和稳定性,所以只建议做测试用,客户的项目需要时,请让 ...

  8. 啊。啊。啊。https免费证书又到期了怎么办。。。。

    这两天在"互联网大厂"批量申请的免费证书又到期了,每次都要重新批量申请->上传->导入配置,已经忘记这是第几次了,身心疲惫.... 有没有一个一劳永逸的办法呢? Let ...

  9. Nginx配置单项SSL以及双向SSL

    Https安全协议的由来? 在实现 HTTPS协议前,我们需要了解 SSL 协议,但其实我们现在使用的更多的是 TLS 加密通讯协议. 那么TLS是怎么保证明文消息被加密的呢?在OSI七层模型中,应用 ...

最新文章

  1. 漫话:如何给女朋友解释什么是缓存穿透、缓存击穿、缓存雪崩?
  2. 五分钟了解操作系统内核
  3. python os模块安装方法_基于python中pygame模块的Linux下安装过程(详解)
  4. STL常见算法transform以及二分查找,以及lambda表达式
  5. Git 提交错了不用慌,这三招帮你修改记录
  6. 任意文件夹下打开cmd窗口
  7. 红帽学习笔记[RHCSA] 第六课[进程、服务相关]
  8. 禅道和JIRA大对比
  9. 题库APP源码 在线题库源码 题库系统源码
  10. 《一次失败沟通后的自我觉察》
  11. 第三阶段应用层——1.7 数码相册—电子书(1)—实现
  12. 宇视摄像机媒体流达到上限
  13. Zabbix企业微信告警最新版
  14. 界面原型设计工具 Balsamiq Mockups
  15. 6大论坛,30+技术干货议题,2022首届阿里巴巴开源开放周来了!
  16. 乔布斯在斯坦福大学的演讲(三)[转载]
  17. mysql中如何查看表结构
  18. 计算机电缆传输频率,传输频率
  19. 基于solidity的Dapp图书管理系统
  20. 使用UltraISO制作Windows 10启动U盘

热门文章

  1. Android Studio课堂总结05
  2. win7右键菜单管理_电脑右键新建不见了怎么办 电脑右键新建不见了解决方法【详解】...
  3. VC/MFC 使用jsoncpp解析json格式内容
  4. 5G系统——5G-GUTI、5G-TMSI、5G-S-TMSI
  5. 阿里IOT云平台(二)---10分钟物联网设备接入阿里云IoT平台
  6. plc无法跟计算机通信,无法与PLC通信
  7. 初级算法_数组 --- 有效的数独
  8. 史上好电影集合--百度云
  9. java 泰文的编码_Unicode字符编码表(转)
  10. 布尔逻辑_了解Go中的布尔逻辑