用于高度安全的Web应用程序的工具和技术

Cod*_*odo 6 .net java asp.net security web-applications

我们计划构建一个需要高度安全的Web应用程序,因为大量的资金和声誉都存在风险.因此,我正在寻找有助于这项工作的工具和技术.这些工具和技术应该有助于防止SQL注入,跨站点脚本漏洞,远程代码执行等问题.

我们的团队对这些漏洞有扎实的了解.但是每个开发人员都会犯错误,而一个简单的错误不应该导致安全漏洞.应该通过Web应用程序框架,应用程序服务器,编程语言,安全库,代码分析器等来防止或检测它们.

一个简单的例子:如果您将数据插入HTML,则需要对其进行转义,以便正确显示并且不会因注入脚本而被滥用.一些Web应用程序框架会给开发人员带来负担.如果他们忘记在一个地方逃跑,他们就会遇到安全问题.一个好的工具不仅可以自动进行转义,甚至可以防止开发人员强行执行.

不是在寻找有关防火墙的建议(我们有一个好的),强化操作系统(这是计划的一部分),使用加密通信(这将是唯一的选择)和安全认证(硬件令牌将使用).相反,建议应以应用程序服务器和要构建的Web应用程序软件为中心.

我们也完全理解编写安全软件不仅仅是技术:它涉及知识渊博的人,管理层的关注,时间和金钱以及软件质量流程.到目前为止,这不是问题,也不是这个问题的焦点.

我应该提一下,我们对Java和.NET有一定的偏见.

那么您可以向我们推荐哪些工具和技术或其组合?

ide*_*ide 13

背景

您提到的漏洞都源于数据与控件(或代码,如果您愿意)的混淆.它们在实践中出现,因为许多编程语言和API不能编码特定于域的语言(如SQL,HTML和系统shell)的语义.例如,几乎所有的XSS漏洞都会发生,因为程序员打印出一个未经过清理的字符串,并且编程语言或API没有足够的信息来检测该字符串是否是用户提交的,并且应该将其控制字符转义.幸运的是,有语言扩展和API将数据与控制分开,几乎可以消除所有这些攻击.

SQL注入

  • 准备好的陈述.JDBC预处理语句的Java实现是在SQL级别访问的DBMS的事实标准.您使用变量编写SQL查询,然后指定这些变量及其类型的值,有效地为DBMS提供足够的信息来转义数据,同时保留您的查询结构(控件).
  • 查询构建器.您可以以构建器模式的方式将其表示为逐步构建对象的方法调用序列,而不是将查询指定为字符串.您可能会将其视为手动构建AST,然后将其序列化为查询字符串.Robertson和Vigna 的论文阐述了Haskell中的一些例子.
  • LINQ.这是.NET特有的.查询实际上是语言的一部分,因此解析器可以区分查询关键字和数据.再次,这允许语言安全地仅转义数据.由于我缺乏LINQ的经验,我不能说更多,但可能数据值包含在随后进行转义的SqlParameter对象中.
  • ORM框架.高于SQL注入的级别,ORM框架旨在抽象出大部分DBMS细节,包括查询本身.他们可以在幕后使用预处理语句,甚至可以公开类似预备语句的API,以便更直接地访问数据库(例如,Hibernate的SQLQuery).

跨站点脚本(XSS)

许多防止XSS攻击的技术在精神上与防御SQL注入相似.只有这一次,目标是Web浏览器而不是数据库.无论哪种方式,我们都不希望将数据错误地解释为控件.

  • 模板.大多数流行的模板语言似乎都针对PHP,Python或Ruby.但是,Java.NET都有一些.模板通常包含HTML和占位符以供数据使用.然后,您将数据传递到模板引擎,它将所有数据都转义,然后呈现模板,并将占位符替换为已清理的数据.
  • DOM树构建器.与SQL查询构建器类似,您可以使用类似DOM的API构建页面以创建新元素和文本节点,最后将它们序列化为HTML字符串.遗憾的是,遗憾的是标准DOM API过于冗长,这种方法令人满意.
  • XML文字.与LINQ一样,XML文字是语言的本机部分,允许解析器区分标记和数据.虽然Java和C#都不支持XML文字,但ScalaVB9都支持XML文字.Facebook有一个名为XHP的开源PHP扩展,它也提供了一些软件工程优势,包括组件重用以及能够为自定义标签指定内容模型.
  • 启发式和检测.这不是一个肯定的防御,但有些系统检查HTML输出并猜测是否嵌入了恶意脚本.但是,正如人们在IE8中发现的那样,这可以实现攻击.
  • 仅限HTTP的cookie.不是对XSS的防御,但它可以防止相当多的攻击.当您的服务器设置cookie时,它可以将其标记为仅HTTP,这意味着支持的浏览器不会让页面上的JavaScript访问该cookie.因此,即使攻击者能够在您的网站上嵌入恶意脚本,他们也无法窃取您用户的cookie,只要他们拥有相当现代的浏览器(即使是IE6 +计数!).

远程执行代码

关于这个话题,我没有太多话要说,但尽量尽量减少system()类似的呼叫.如果您必须拨打其他二进制文件,请应用良好的安全措施,例如尽可能使用白名单,并在适当情况下使用经过严格审查的清理功能.一些API,比如Python的Popen,可以很好地确保参数不被视为shell控制字符.最后,使用Java和C#,缓冲区溢出漏洞的可能性极小.这不是一个正式的保证,但数十亿美元的公司一直在运行Java服务器.

最佳实践

最终,您应该考虑使用为手头任务设计的API或语言功能,无论是创建SQL查询还是构建HTML页面.这些语言和API不仅增加了您对安全性的信心,而且通常也有助于编程.与连接一堆字符串的老派策略相比,我们现在拥有LINQ和XML文字,可以说代码更容易编写,更易于阅读,也更容易验证.我是语言增强和API的粉丝,可以提高代码质量和程序员的工作效率!