学编程,来源栈;先学习,再交钱
当前系列: 原理架构 修改

安全:黑客/病毒/木马/漏洞/后门

互联网是开放的,所以也是不安全的。

随着互联网的蓬勃发展,网络安全逐渐形成一个专门的学科/职业/岗位。作为开发人员,也应对有所了解:

黑客

这就是给自己脸上贴金了,^_^

最初曾指热心于计算机技术、水平高超的电脑高手,尤其是程序设计人员,……hacker客观的解释:

a person who secretly finds a way of looking at and/or changing information on sb else's computer system without permission和计算机技术水平没关系,而且一般都不是程序员!程序员不会干这种事。(别问我密码忘了怎么办?)

黑客世界也是金字塔结构的,遵循80/20原则,一大批的“工具”人,做什么“灰产”……

病毒

在计算机程序中插入的破坏计算机功能或者破坏数据,影响计算机正常使用并且能够自我复制的一组计算机指令或程序代码
  • 外部侵入:区别于漏洞、后门
  • 破坏性:区别于木马
  • 传染性:哦豁~,最大的特点,区别于特定的黑客攻击

木马

名称来源:特洛伊木马。

也可以把它也归入病毒,但是木马通常更隐蔽,没有明显的破坏性,其目的:
  • 窃取数据
  • 远程控制

黑话:“肉鸡”、“种马”。病毒越来越少,木马越来越隐蔽……

漏洞

在硬件、软件、协议的具体实现或系统安全策略上存在的缺陷,从而可以使攻击者能够在未授权的情况下访问或破坏系统。

可以简单的理解为安全性方面的bug。我们开发人员,应该极力避免我们的代码中有这样的漏洞,燃鹅……

几乎所有攻击(病毒/木马/黑客)都是因为系统本身的漏洞!

发现漏洞之后发布的修复程序,一般被称之为补丁

后门

开发人员故意留下的、能够以非常规手段,隐秘的访问、监听、控制项目或系统的手段。比如:

  • 键入XXXXXX,自动掉落XXXXX装备……一般是为了测试
  • 用某种特定的手段,就可以打开用户手机的摄像头、监听用户的语音

如何让一个系统更安全?

和普通人的直觉相反,开源,而不是闭源,会让系统更安全!

@想一想@:为什么?


HTTPS

HTTP协议是明文传递的,而互联网上的信息传递会经过很多网络节点(复习:路由,每一个节点都可能存在安全隐患,所以,更安全的做法需要对信息进行加密(复习)。于是现在主流推荐的是采用HTTPS协议。其中的S,代表SSL(Secure Sockets Layer),安全套接字层。

很多浏览器(比如chrome和火狐),访问非HTTPS协议的网址,会给予警告:

要用户手动操作确认允许访问才行,而且会一直用图标标注:不安全。

是否使用HTTPS协议,和我们开发没关系,使用HTTPS协议也只需要简单部署,但其底层原理可能是#高等级面试题#。

互联网中加密

但在互联网中使用加密,有更具体的问题:一台服务器要响应无数的不确定用户的访问,如何和他们“约定”加密?算法可以公开,秘钥呢?不用说用户A可能无法妥善保管秘钥,就是给秘钥这个过程,都可能是不安全的呀!

所以必然引入不对称加密(复习):

  • 公钥:公开的,任何人都可以获得
  • 私钥:只有服务器端持有

从客户端到服务器

用户使用公钥将敏感信息加密,发送给服务器。

于是,只有服务器能获取其正确信息,因为服务器才有私钥。

这就是:防泄漏,客户的信息不会被泄露。

通常,这些信息都不大,加密和解密都不费劲。

从服务器端到客户端

服务器用私钥将信息加密,发送给用户。

@想一想@:为什么?能不能防泄漏?不能。因为哪怕是用私钥加密,但公钥是公开的,所以任何人都可以解密。

但是,可以:防篡改

哪怕信息被劫持被解密然后修改,因为没有私钥,它无法正确加密。被错误加密的信息,用正确的公钥无法解开。

数字签名

服务器发送给客户端的信息通常比较大,全部加密的话可能有性能压力。(这就是很多项目不愿意HTTPS的原因!)

但是,既然服务器端加密的目的只是“防篡改”,我们就有了一个好主意:

  1. 用Hash函数,在整个信息的基础上,生成一段“摘要(abstract)”
  2. 用私钥加密这段“摘要”,形成一个“数字签名(digit signature)”,和信息一起发送给客户端
  3. 客户端收到信息后,用公钥解密“数字签名”,得到“解密的摘要”
  4. 然后,对整个信息使用同样的Hash函数,获得“生成的摘要”,和我的“解密的摘要”相对比
  5. 如果两份摘要一致,表明数据未经篡改;否则,……

认证证书

@想一想@:还有没有问题?有的,客户端怎么拿到公钥?

一种是直接由服务器给,这种方式不够“权威”。因为服务器可能已经被“劫持”了,用户拿到的可能是一个“假”的公钥。浏览器还是会报警告:“未认证的SSL证书”云云。

所以更常见的是从使用一个权威的第三方(认证机构,CA)获取,具体的流程包括:

  1. 服务器向认证机构申请为某域名认证
  2. 认证机构给服务器一个私钥(一长串字符),服务器上配置访问该域名时告诉用户到哪里获取公钥
  3. 用户使用浏览器访问该网站,浏览器会根据服务器指示向认证机构申请公钥



脚本注入

病从口入:小心用户输入!

Web2.0开始,大量未认证的用户可以通过网站“操纵”数据库,这就给了恶意用户可乘之机:

SQL注入

详见数据库章节

Script注入

又被称之为XSS(Cross Site Scripting,为了避免和样式的CSS混淆,改为XSS)攻击。

其实就是在发布内容中输入一段恶意的(Java)Script代码,比如:
<script>
  location = "http://17bang.ren"
</script>

这样当程序将这段代码当做文章内容发布的时候,@想一想@:会发生什么?

所以后台需要对用户输入进行处理:

一种方式是转义,把用户输入中的尖括号变成&lt;和&gt;(复习:HTML)。

但是,很多时候我们是要允许用户输入的HTML标签生效的(演示:富文本编辑器),这就需要过滤:去掉有潜在危害的,只保留允许使用的标签和属性(JavaScript也可以通过属性的方式存在)。

过滤又两种策略:

  • 黑名单:过滤掉黑名单中出现的标签和属性;
  • 白名单:只允许使用白名单中的标签和属性,其他一律过滤掉,推荐!
如何过滤呢?使用正则表达式(复习)匹配


跨域请求欺骗

漏洞

无论从哪个页面访问目标网站(比如:http://17bang.ren/),浏览器都会自动将其存放的该网站cookie发送过去;

而这cookie当中,存储了用户身份验证信息……

演示:百度搜素“一起帮”,点击我们网站连接,自动登录

@想一想@:于是你能干什么坏事?^_^

CSRF

Cross-Site Request Forgery:CSRF,或者XSRF:

  1. 攻击方(黑客)可以做一个“陷阱网站”,里面放上诸如:妹妹好寂寞,阿泰快来之类的链接,诱使其他用户点击。这个链接可以通过url参数或JavaScript代码给目标网站指令,比如点赞/转账/发布评论等等
  2. 如果该用户之前曾经访问/登录过目标网站,且该网站使用cookie存放用户授权信息,浏览器就会把自动的cookie也传递到被攻击网站
  3. 被攻击网站无法辨别用户是:真正的想进行链接指示的操作,还是受欺骗后由陷阱网站生成的指令(#再次体会:HTTP无状态)

解决方案

让服务器确保该HTTP请求确实由“我”自己生成的HTML页面/链接……所产生的。

怎么确定?八仙过海各显神通,但ASP.NET(core)和SpringWeb都提供了几乎是现成的方案:

  1. 在生成表单时在其中插入一个hidden input,里面存储一个服务器生成的token做签名,
  2. 表单提交时会自动附上该签名
  3. 服务器在表单提交后对其中的签名进行验证……


其他

DDoS

Distributed Denial of Service Attack,分布式拒绝服务攻击。

DoS攻击是(通过程序)不断的向网站发起请求,使网络或系统不胜负荷以至于瘫痪而停止提供正常的网络服务。与DoS攻击由单台主机发起攻击相比,分布式拒绝服务攻击是借助无数台被(木马)入侵后安装了攻击进程的电脑同时发起的,所以规模更大、欺骗性更强、防御难度更大……最管用的解决办法就是:提高自身服务器的吞吐能力,来多少我干多少!^_^

防盗链

简单的说,就是在别人使用了由你的服务器/网站提供的资源(比如:图片)

演示:<img src="https://pic2.zhimg.com/v2-1d934807c57b0bbdc08fd40ea0f503d5_720w.jpg?source=c8b7c179" />

如果你不想当这种“活雷锋”,就可以使用一些技术禁止掉这种情况。一种简单的办法就是在响应这种请求之前,检查其referrer是否是本站网址!

演示:

反爬虫/机器人

爬虫其实也是一种机器人,对付他们最好的办法就是:图像验证。

专业的说法:captcha,Completely Automated Public Turing Test to Tell Computers and Humans Apart ,全自动区分计算机和人类的图灵测试),顾名思义,利用电脑和人脑的差异,用一张人类轻松识别的图片,考一考电脑:嗨,兄弟,这是啥?如果电脑/程序能够通过这个测试,他/她就通过了图灵测试,是强人工智能了!

服务器管理

权限:不是任何人都可以直接登录服务器的!

白名单:端口、服务、驱动……要用才开,不用就关。

备份/回滚:……


最后的啰嗦

HTTP本身是一个不安全的协议,

前端没有任何安全性可言,

后端永远不要相信前端!

Web开发 安全
觉得很 ,不要忘记分享哟!

任何问题,都可以直接加 QQ群:273534701

在当前系列 原理架构 中继续学习:

我们的 特色

  • 先学习,后付费
  • 线上/线下,自由组合

更多了解

QQ群:273534701

答疑解惑,远程debug……

B站 源栈-小九 的直播间

写代码要保持微笑 (๑•̀ㅂ•́)و✧