网络安全与HTTPS
一、信息安全三要素
任何完整的信息安全体系,都需要遵循CIA原则,即保密性(Confidentiality)、完整性(Integrity)、可用性(Availability)。
- 保密性:对需要保护的数据(如用户的私人信息等)进行保密操作,无论存储还是传输,都要保证用户数据及相关资源的安全。通常使用加密等手段保证数据的安全。
- 完整性: 访问的数据要是完整的,没有缺失或被篡改。可以对数据进行签名和校验(比如MD5和数字签名等)。
- 可用性:服务必须可用。可以使用访问控制、限流等手段保证服务的可用性。
二、常见的网络攻击
网络攻击大体可以分为非破坏性攻击和破坏性攻击。非破坏性攻击一般是为了扰乱系统的运行,使之暂时失去正常对外提供服务的能力,比如DDoS攻击等;破坏性攻击注意会造成两种后果:系统数据受损或信息被窃取,比如CSRF等。
DDoS
DDoS(Distributed Denial of Service,分布式拒绝服务)主要通过大量合法的请求占用大量网络资源,从而使合法用户无法得到服务的响应,是目前最强大、最难防御的攻击之一。其攻击效果:
- 占满网络带宽
- 提交大量请求,使服务器超负荷运行,响应缓慢
- 阻断某一用户访问服务器
- 阻断某服务与特定系统或个人的通讯
防范思路:
1、 请求拦截,包括:硬件防火墙、HTTP请求限流(如阿里的开源中间件sentinel)等
2、使用CDN
3、带宽扩容
4、实时监控等
SQL注入
SQL注入是由于未将代码与数据进行严格的隔离,导致在读取用户数据的时候,错误地将数据作为代码的一部分执行,从而导致的安全问题。最常见的例子是当对SQL语句进行字符串拼接操作时,直接使用未加转义的用户输入内容作为变量,从而可能出现drop、delete等意想不到的结果。
防范思路:
1、过滤用户输入参数中的特殊字符,从而降低被SQL注入的风险
2、禁止通过字符串拼接的SQL语句,严格使用参数绑定传入的SQL参数
3、合理使用数据库访问框架提供的防范注入机制。比如Mybatis提供的#{}
XSS
跨站脚本攻击(Cross-Site Scripting):为了和CSS区分开,所以简称为XSS。它是指黑客通过技术手段,向正常用户请求的HTML页面中插入恶意脚本,从而可以执行任意脚本,达到信息窃取、破坏等目的。
主要防范思路是对用户输入数据做过滤或转义,且需要前后端开发人员共同配合。比如后端开发可以使用Jsoup、Spring框架的HtmlUtils等框架工具做过滤或转义;前端使用安全的API展示数据,比如innerText而不是innerHTML等。
CSRF
跨站请求伪造(Cross-Site Request Forgery):在用户不知情的情况下,冒充用户发起请求,在当前已登录的Web应用程序中执行恶意操作,如恶意发帖、修改密码、发邮件、甚至利用网银登陆信息进行转账等。
和XSS的区别:XSS是在正常用户的HTML页面中执行黑客提供的恶意代码,问题在于没有对用户数据过滤、转移;而CSRF是黑客直接盗用用户浏览器中的登陆信息,冒充用户去执行黑客的指定操作,问题出在HTTP接口没有防范不受信任的调用。
防范思路:
1、CSRF Token验证:利用浏览器的同源机制,在HTTP接口执行前验证页面或者Cookie中设置的Token
2、人机交互:比如在调用网银转账接口时校验短信验证码
三、HTTPS
HTTP的不足:
- 通信使用明文,内容可能会被窃听
- 不验证通信方的身份,因此有可能遭遇伪装
- 无法证明报文的完整性,有可能已遭篡改
因此当前网站的主流文本传输协议都使用HTTPS了。HTTPS的全称是HTTP over SSL,即在HTTP传输上增加了SSL协议的加密能力。SSL(Secure Socket Layer)协议工作于传输层与应用层之间,为应用提供数据的加密传输。
要理解HTTPS的传输机制,需要先理解对称加密与非对称加密算法(这里就不作展开)。另一个重要概念是数字证书,是由CA(Certificate Authoriry)颁发的HTTPS证书,用于证明信息传输方的身份,防止传输过程中的公钥和密文被替换。
访问一个HTTPS网站的大致流程如下:
HTTPS请求执行流程
1、浏览器向服务器发送请求,请求中包括浏览器支持的协议,并附带一个随机数(作为客户端公钥)
2、服务器收到请求后,选择某种非对称加密算法,把数字证书签名公钥、身份信息发送给浏览器,同时也附带一个随机数(作为服务端公钥)
3、浏览器收到后:
3.1 首先验证证书的真实性,如果服务端的CA机构存在于浏览器的受信任CA机构列表中,并且服务器证书中的信息与当前正在访问的网站(域名等)一致,则认为服务端是可信的
3.2 生成客户端的公私钥、会话密钥
3.3 使用服务端公钥加密{客户端公钥,客户端会话密钥},并给服务端
4、服务器收到后:
4.1 使用服务端私钥解密{客户端公钥,客户端会话密钥}
4.2 使用之前的随机数生成服务端会话密钥
4.3 使用客户端公钥加密服务端密钥,并发送给客户端
5、后续所有的信息发送都是以对称加密方式进行