1. 加密

1.1 对称加密

对称加密是指双方持有相同的密钥进行通信,加密速度快,但是有一个安全问题,双方怎样获得相同的密钥?你总不能总是拿着U盘把密钥拷贝给对方吧。
常见的对称加密算法有DES、3DES、AES等

1.2 非对称加密

非对称加密,又称为公开密钥加密,是为了解决对称加密中的安全问题而诞生,一个称为公开密钥(public key),即公钥,另一个称为私钥(private key),即私钥。但是它的加密速度相对于对称加密来说很慢。

  • 公钥(public key)是对外开放的,私钥(private key)是自己拥有的。
  • 公钥(public key)加密的数据,只能用私钥(private key)解密。
  • 私钥(private key)加密的数据,只能用公钥(public key)解密。

2. 信息安全问题

在信息安全性问题中,我们常常要做到三点才能保证信息的安全:

  • 信息的保密性
  • 信息的完整性
  • 身份识别

2.1 信息的保密性(加密算法)

信息的保密性我们可以使用对称加密和非对称加密来完成,使用对称加密来完成,速度相对非对称加密很快,但是存在一个安全问题,密钥如何传递?由此通用的方法是使用非对称加密+对称加密来完成。客户端使用公钥对对称加密的密钥进行加密,然后传递给服务端,服务端使用私钥进行解密确认密钥,开始传输数据。

2.2 信息的完整性(数字签名)

2.2.1 hash算法

信息传输的途中,我们的信息很有可能被第三方劫持篡改,所以我们需要保证信息的完整性,通用方法是使用散列算法如SHA1,MD5将传输内容hash一次获得hash值,即摘要。客户端使用服务端的公钥对摘要和信息内容进行加密,然后传输给服务端,服务端使用私钥进行解密获得原始内容和摘要值,这时服务端使用相同的hash算法对原始内容进行hash,然后与摘要值比对,如果一致,说明信息是完整的。

2.2.2 hmac

通过哈希算法,我们可以验证一段数据是否有效,方法就是对比该数据的哈希值,例如,判断用户口令是否正确,我们用保存在数据库中的password_md5对比计算md5(password)的结果,如果一致,用户输入的口令就是正确的。

为了防止黑客通过彩虹表根据哈希值反推原始口令,在计算哈希的时候,不能仅针对原始输入计算,需要增加一个salt来使得相同的输入也能得到不同的哈希,这样,大大增加了黑客破解的难度。

如果salt是我们自己随机生成的,通常我们计算MD5时采用md5(message + salt)。但实际上,把salt看做一个“口令”,加salt的哈希就是:计算一段message的哈希时,根据不同口令计算出不同的哈希。要验证哈希值,必须同时提供正确的口令。

这实际上就是Hmac算法:Keyed-Hashing for Message Authentication。它通过一个标准算法,在计算哈希的过程中,把key混入计算过程中。

和我们自定义的加salt算法不同,Hmac算法针对所有哈希算法都通用,无论是MD5还是SHA-1。采用Hmac替代我们自己的salt算法,可以使程序算法更标准化,也更安全。

>>> import hmac
>>> message = b'Hello, world!'
>>> key = b'secret'
>>> h = hmac.new(key, message, digestmod='MD5')
>>> # 如果消息很长,可以多次调用h.update(msg)
>>> h.hexdigest()
'fa4ee7d173f2d97ee79022d1a7355bcf'

2.3 身份识别(数字证书)

在信息传输的过程中,我们通常需要验证信息的发送方的身份,这时我们转化一下思路就可以完成,把发送端的公钥发送给接收端,发送端通过把自己的内容使用私钥加密然后发送给接收端,接收端只能用发送端的公钥解密,自然就验证了发送端的身份。

2.3.1 中间人劫持

在传输的过程中,客户端如何获得服务器端的公钥呢?当时是服务器分发给客户端,如果一开始服务端发送的公钥到客户端的过程中有可能被第三方劫持,然后第三方自己伪造一对密钥,将公钥发送给客户端,当服务器发送数据给客户端的时候,中间人将信息进行劫持,用一开始劫持的公钥进行解密后,然后使用自己的私钥将数据加密发送给客户端,而客户端收到后使用公钥解密,反过来亦是如此,整个过程中间人是透明的,但信息泄露却不得而知。

为了防止这种情况,数字证书就出现了,它其实就是基于上上面所说的私钥加密数据,公钥解密来验证其身份。

2.3.2 CA颁发数字证书

数字证书是由权威的CA(Certificate Authority)机构给服务端进行颁发,CA机构通过服务端提供的相关信息生成证书,证书内容包含了持有人的相关信息,服务器的公钥,签署者签名信息(数字签名)等,最重要的是公钥在数字证书中。
数字证书是如何保证公钥来自请求的服务器呢?数字证书上由持有人的相关信息,通过这点可以确定其不是一个中间人;但是证书也是可以伪造的,如何保证证书为真呢?

一个证书中含有三个部分:“证书内容,散列算法,加密密文”,证书内容会被散列算法hash计算出hash值,然后使用CA机构提供的私钥进行RSA加密。

2.3.3 数字证书验证和解密

当客户端发起请求时,服务器将该数字证书发送给客户端,客户端通过CA机构提供的公钥对加密密文进行解密获得散列值(数字签名),同时将证书内容使用相同的散列算法进行Hash得到另一个散列值,比对两个散列值,如果两者相等则说明证书没问题。

2.3.4 常见的证书文件类型

  • X.509#DER 二进制格式证书,常用后缀.cer .crt
  • X.509#PEM 文本格式证书,常用后缀.pem
  • 有的证书内容是只包含公钥(服务器的公钥),如.crt、.cer、.pem
  • 有的证书既包含公钥又包含私钥(服务器的私钥),如.pfx、.p12

3. HTTPS,TLS/SSL

Hyper Text Transfer Protocol over Secure Socket Layer,安全的超文本传输协议,网景公式设计了SSL(Secure Sockets Layer)协议用于对Http协议传输的数据进行加密,保证会话过程中的安全性。

3.1 单向认证

单向认证流程中,服务器端保存着公钥证书和私钥两个文件,整个握手过程如下:

3.2 双向认证

4. HTTP API 认证授权

4.1 AK/SK+HMAC

App ID(或者叫做Access Key Id)(AK)跟验证没有关系,只是用来区分,是谁来调用API的,就像我们每个人的身份证一样,只是用来标注不同的人,不是用来做身份认证的。

Secret Access Key(SK)是客户端用于加密认证字符串和服务端用来验证认证字符串的密钥,SK必须保密。

我们需要用App ID 来映射一个用于加密的密钥,这样一来,我们就可以在服务器端进行相关的管理,我们可以生成若干个密钥对AK/SK(AppID, AppSecret)。

HMAC 在作为网络通信的认证设计中作为凭证生成算法使用,避免了口令等敏感信息在网络中传输。基本过程如下:

  1. 客户端需要在认证服务器中预先设置 access key(AK 或叫 app ID) 和 secure key(SK)
  2. 在调用 API 时,客户端需要对参数和 access key 进行自然排序后并使用 secure key 进行签名生成一个额外的参数 digest
  3. 服务器根据预先设置的 secure key 进行同样的摘要计算,并要求结果完全一致,注意 secure key 不能在网络中传输,以及在不受信任的位置存放(浏览器等)

AK/SK认证的方式好处在于,AppID和AppSecretKey,是由服务器的系统开出的,所以,是可以被管理的,其管理了用户、权限和其对应的AppID和AppSecretKey。但是不好的地方在于,这个东西没有标准 ,所以,各家的实现很不一致。

4.2 JWT – JSON Web Tokens

JWT是一个比较标准的认证解决方案,这个技术在Java圈里应该用的是非常普遍的。JWT签名也是一种MAC(Message Authentication Code)的方法。

4.2.1 HMAC-SHA256

JWT的签名流程一般是下面这个样子:

  1. 用户使用用户名和口令到认证服务器上请求认证。
  2. 认证服务器验证用户名和口令后,以服务器端生成JWT Token,这个token的生成过程如下:
    2.1 认证服务器还会生成一个 Secret Key(密钥)
    2.2 对JWT Header和 JWT Payload分别求Base64。在Payload可能包括了用户的抽象ID和的过期时间。
    2.3 用密钥对JWT签名 HMAC-SHA256(SecertKey, Base64UrlEncode(JWT-Header)+‘.’+Base64UrlEncode(JWT-Payload));
  3. 然后把 base64(header).base64(payload).signature 作为 JWT token返回客户端。
  4. 客户端使用JWT Token向应用服务器发送相关的请求。这个JWT Token就像一个临时用户权证一样。

当应用服务器收到请求后:

  1. 应用服务会检查 JWT Token,确认签名是正确的。
  2. 然而,因为只有认证服务器有这个用户的Secret Key(密钥),所以,应用服务器得把JWT Token传给认证服务器。
  3. 认证服务器通过JWT Payload 解出用户的抽象ID,然后通过抽象ID查到登录时生成的Secret Key,然后再来检查一下签名。
  4. 认证服务器检查通过后,应用服务就可以认为这是合法请求了。

上面的这个过程,是在认证服务器上为用户动态生成 Secret Key的,应用服务在验签的时候,需要到认证服务器上去签,这个过程增加了一些网络调用。

4.2.2. JWT+非对称加密

JWT除了支持HMAC-SHA256的算法外,还支持RSA的非对称加密的算法。

使用RSA非对称算法,在认证服务器这边放一个私钥,在应用服务器那边放一个公钥,认证服务器使用私钥加密,应用服务器使用公钥解密,这样一来,就不需要应用服务器向认证服务器请求了。

但是,RSA是一个很慢的算法,所以,虽然你省了网络调用,但是却费了CPU,尤其是Header和Payload比较长的时候。

所以,一种比较好的玩法是,如果我们把header 和 payload简单地做SHA256,这会很快,然后,我们用RSA加密这个SHA256出来的字符串,这样一来,RSA算法就比较快了,而我们也做到了使用RSA签名的目的。

最后,我们只需要使用一个机制在认证服务器和应用服务器之间定期地换一下公钥私钥对就好了。

4.2.3 JWT vs https

JWT 和 HTTPS 实现不同的目标。

安全系统的三个主要组成部分:

  • C - 机密性 - 外人是否能读取数据?
  • I - 完整性 - 数据不会被外界篡改吗?
  • A - 真实性 - 是从适当的人发送的数据

HTTPS 确保机密性和完整性,JWT 有助于提高真实性。

4.3 OAuth 1.0

OAuth 的出现,目的是为了,用户为了想使用一个第三方的网络打印服务来打印他在某网站上的照片,但是,用户不想把自己的用户名和口令交给那个第三方的网络打印服务,但又想让那个第三方的网络打印服务来访问自己的照片。

OAuth 1.0区分了两个事,一个是第三方的Client,一个是真正的用户,其先拿Request Token,再换Access Token的方法主要是为了把第三方应用和用户区分开来。

深入理解密码学基本概念和应用相关推荐

  1. c# 添加中文描述 给enum_理解C# 核心概念 – C# 程序集本地化

    在之前几讲中,老白给大家介绍了C#中module和Assembly的生成和使用.在这一篇中,老白将更加深入的介绍下Assembly其中的一个知识点--本地化(Localization). 什么是本地化 ...

  2. 理解 Keystone 核心概念 - 每天5分钟玩转 OpenStack(18)

    作为 OpenStack 的基础支持服务,Keystone 做下面这几件事情: 管理用户及其权限 维护 OpenStack Services 的 Endpoint Authentication(认证) ...

  3. 十分钟带你理解Kubernetes核心概念

    原文地址:http://www.dockone.io/article/932 十分钟带你理解Kubernetes核心概念 本文将会简单介绍Kubernetes的核心概念.因为这些定义可以在Kubern ...

  4. 从构建区块链理解区块链概念

    从构建区块链理解区块链概念 import hashlib import json from datetime import time from urllib.parse import urlparse ...

  5. 通过插画理解kubernetes基本概念

    ========== 第一篇 ========== 转自:https://www.cnblogs.com/kouryoushine/articles/8007648.html 插画版Kubernete ...

  6. 一张图理解AOP关键概念

    一张图理解AOP关键概念 Aspect(切面) Joint Point(连接点) Advice(通知) Pointcut(切入点) Weaving(织入) 这里以跟踪方法调用为例,Calculate为 ...

  7. 深入理解CRM的概念

    深入理解CRM的概念 什么是CRM CRM(Customer Relationship Management),即客户关系管理.CRM概念最初由美国Gartner Group集团于1980年提出,而在 ...

  8. 用工厂流水线的方式来理解RxJava的概念

    现在有很多的 RxJava 入门教程,但是大多数都是示例代码,并不能让人很快理解 RxJava 的原理和方法,这篇文章就用流水线来比喻 RxJava 的开发方式,看完这篇文章后你就能理解 RxJava ...

  9. [原创]理解泛函的概念和能量…

    原文地址:[原创]理解泛函的概念和能量泛函的梯度下降流 作者:小腹黑zju 对本篇文章进行转载需说明出处: 1. 泛函的概念             函数y=f(x)是一个变量x∈R到y∈R的一个映射 ...

最新文章

  1. vb.net中的部分代码
  2. 10.6 捕获处理异常
  3. 选择问题(求第k个最小元素)
  4. leetcode236 二叉树的最近公共祖先
  5. 论文浅尝 | 使用循环神经网络的联合事件抽取
  6. Docker 官方公共仓库 Docker Hub 遭攻击,恐19 万用户信息泄露;Intel 10核心新品要现身了?...
  7. 在日常生活中,经常会遇到某些需求对文件名称进行修改,借助刚学过的文件操作,编写一个可以批量修改文件名的小程序。
  8. PHP current() 函数
  9. Android:随笔—— ConstraintLayout 效率爆表的技巧
  10. 属于自己的MES(二)必备的主数据
  11. ubuntu正确安装显卡驱动的姿势
  12. GAN生成手写字体识别
  13. 万里汇WorldFirst支持从PayPal提现美元(实战教程)
  14. java调用dll实例_如何用java调用dll,详细图解
  15. Ceph rgw中的元数据组织形式及存储结构分析
  16. SD卡简单介绍(个人笔记)杜绝垃圾堆里刨食
  17. 中国电信物联网建设全面提速 投入三亿元补贴物联网模块
  18. 靖江最正宗过年习俗 只有3%的人完全继承下来了
  19. 【9种优化算法比较】CGO、SCA、GWO、CSA、SSA、HHO、WOA、PSO、TSO智能优化算法比较(Matlab代码实现)
  20. 一起白piao网页学知识吧

热门文章

  1. 点击高德地图标注没法弹窗_如何在地图上标注我的店铺
  2. 网页设计工资一般多少_初级会计师就业前景怎么样?工资一般多少?
  3. java sftp 公开键设定_如何使用JSch SFTP库解析Java UnknownHostKey?
  4. HTML之图片标签、音视频标签
  5. SpringMVC之@RequestMapping注解及其衍生注解详解
  6. 3-18pytorch与矩阵分解PCA
  7. windows下的工具链 树莓派_Windows下交叉编译Qt 5.14.2至树莓派平台 QEMU模拟树莓派...
  8. jsp iframe嵌入php,jsp中的iframe什么意思
  9. Linux安装mysql(解决E: Package ‘mysql-server‘ has no installation candidate与ERROR 1698 (28000))
  10. OpenCV检验物体尺寸