10个Java安全最佳实践

10 Java security best practices

In this cheat sheet edition, we’re going to focus on ten Java security best practices for both open source maintainers and developers. Although most developers understand that secure coding is important, security is not the first thing on a Developers mind. Using the OWASP Top 10 vulnerabilities as the initial starting point, I created this top 10. For this cheat sheet, I collaborated with Jim Manico, Java Champion and founder of Manicode Security.

So without further due I proudly present the 10 Java security best practices

1. Use query parameterization to prevent injection

在OWASP十大漏洞的2017版中,注入是当年排名第一的漏洞。 当查看Java中典型的SQL注入时,续集查询的参数会天真地连接到查询的静态部分。 以下是Java中SQL的不安全执行,攻击者可能会使用它来获取比原本打算的要多的信息。

public void selectExample(String parameter) throws SQLException {
   Connection connection = DriverManager.getConnection(DB_URL, USER, PASS);
   String query = "SELECT * FROM USERS WHERE lastname = " + parameter;
   Statement statement = connection.createStatement();
   ResultSet result = statement.executeQuery(query);

   printResult(result);
}

如果此示例中的参数类似于''OR 1 = 1,结果包含表中的每个项目。 如果数据库支持多个查询,并且参数为''; 更新用户集姓氏=''。

为了防止在Java中出现这种情况,我们应该使用准备好的语句对查询进行参数化。 这应该是创建数据库查询的唯一方法。 通过定义完整的SQL代码并在以后将参数传递给查询,代码更易于理解。 最重要的是,通过区分SQL代码和参数数据,该查询不会被恶意输入劫持。

public void prepStatmentExample(String parameter) throws SQLException {
   Connection connection = DriverManager.getConnection(DB_URL, USER, PASS);
   String query = "SELECT * FROM USERS WHERE lastname = ?";
   PreparedStatement statement = connection.prepareStatement(query);
   statement.setString(1, parameter);
   System.out.println(statement);
   ResultSet result = statement.executeQuery();

   printResult(result);
}

在上面的示例中,输入绑定到String类型,因此是查询代码的一部分。 此技术可防止参数输入干扰SQL代码。

2. Use OpenID Connect with 2FA

身份管理和访问控制很困难,而身份验证失败通常是造成数据泄露的原因。 实际上,这是OWASP十大漏洞列表中的第二名。 自己创建身份验证时,需要考虑很多事情:密码的安全存储,强大的加密,凭据的检索等。在许多情况下,使用令人兴奋的解决方案(如OpenID Connect)会更容易,更安全。 OpenID Connect(OIDC)使您可以跨网站和应用程序对用户进行身份验证。 这样就无需拥有和管理密码文件。 OpenID Connect是提供用户信息的OAuth 2.0扩展。 除了访问令牌外,它还添加了一个ID令牌,以及一个/用户信息获得更多信息的端点。 它还添加了端点发现功能和动态客户端注册。

使用像Spring Security这样的库来设置OpenID Connect是一项简单而常见的任务。 确保您的应用程序强制执行2FA(两因素身份验证)或MFA(多因素身份验证)以在系统中添加额外的安全层。

通过将oauth2-client和Spring安全性依赖项添加到您的Spring Boot应用程序中,您可以利用Google,Github和Okta等第三方客户端来处理OIDC。 创建应用程序后,只需在应用程序配置中指定它即可将其连接到您选择的特定客户端。 可能是您的GitHub或Okta client-id和client-secret,如下所示。

pom.xml

<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-oauth2-client</artifactId>
</dependency>
<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-security</artifactId>
</dependency>

application.yaml

spring:
 security:
   oauth2:
     client:
         registration:
           github:
             client-id: 796b0e5403be4729ca01
             client-secret: f379318daa27502254a05e054361074180b840a9
           okta:
             client-id: 0oa1a4wascEpYu6yk358
             client-secret: hqxj7a9lVe_TudbS2boBW7AWwxTlZiHNrJxdc_Sk
             client-name: Okta
         provider:
           okta:
             issuer-uri: https://dev-844689.okta.com/oauth2/default

3. Scan your dependencies for known vulnerabilities

您很有可能不知道您的应用程序使用了多少直接依赖项。 您也很可能不知道您的应用程序使用了多少可传递依赖项。 尽管依赖项构成了整个应用程序的大部分,但这通常是正确的。 攻击者越来越多地将目标锁定在开源依赖项上,因为它们的重用为恶意攻击者带来了许多受害者。 确保您的应用程序整个依赖树中没有已知漏洞很重要。

Snyk测试您的应用程序构建工件,并标记那些具有已知漏洞的依赖项。 它为您提供了在应用程序中用作仪表板的软件包中存在的漏洞列表。

此外,它通过对源代码存储库的拉取请求,建议升级版本或提供修补程序来补救您的安全问题。 Snyk还通过确保自动测试(通过Webhooks)存储库上提出的任何将来的拉取请求来确保它们不会引入新的已知漏洞,从而保护您的环境。

Snyk可通过Web UI和CLI来使用,因此您可以将其与CI环境集成,并配置它以在存在严重性超过设置的阈值的漏洞时中断构建。

Use Snyk for free for open source projects or for private projects with a limited number of monthly tests.

4. Handle sensitive data with care

暴露敏感数据(例如客户的个人数据或信用卡号)可能是有害的。 但是,甚至比这更微妙的情况也同样有害。 例如,如果可以在另一个调用中使用该标识符来检索其他数据,则在系统中公开唯一标识符是有害的。

首先,您需要仔细查看应用程序的设计并确定您是否确实需要数据。 最重要的是,请确保您不公开敏感数据,例如通过日志记录,自动完成,传输数据等。

防止敏感数据出现在日志中的一种简单方法是对toString()域实体的方法。 这样,您就不会偶然打印出敏感字段。 如果您使用项目Lombok生成您的toString()方法,尝试使用@ ToString.Exclude以防止字段成为toString()输出。

另外,在将数据暴露给外界时要非常小心。 例如:如果我们在一个显示所有用户名的系统中具有一个端点,则无需显示内部唯一标识符。 此唯一标识符可用于通过使用其他端点将其他更敏感的信息连接到用户。 如果您使用Jackson将POJO序列化和反序列化为JSON,请尝试使用@JsonIgnore和@JsonIgnoreProperties以防止这些属性被序列化或反序列化。

如果您需要将敏感数据发送到其他服务,请对其进行适当的加密,并确保例如使用HTTPS保护您的连接。

5. Sanitize all input

跨站点脚本(XSS)是一个众所周知的问题,通常在JavaScript应用程序中使用。 但是,Java不能幸免。 XSS仅仅是注入可远程执行的JavaScript代码。 根据OWASP的说法,防止XSS的规则#0是“切勿在允许的位置插入非信任的数据”。基本解决方案是在使用数据之前,尽可能地防止不受信任的数据并清除所有其他内容。 OWASP Java编码库是一个很好的起点,它为您提供了很多编码器。

<dependency>
   <groupId>org.owasp.encoder</groupId>
   <artifactId>encoder</artifactId>
   <version>1.2.2</version>
</dependency>
String untrusted = "<script> alert(1); </script>";
System.out.println(Encode.forHtml(untrusted));

// output: <script> alert(1); </script>

清除用户文本输入很明显。 但是,即使是您自己的数据库,您从数据库检索的数据又如何呢? 如果您的数据库被破坏并且有人在数据库字段或文档中植入了一些恶意文本该怎么办?

另外,请注意传入的文件。 许多库中存在Zip-slip漏洞,因为未清理压缩文件的路径。 包含路径文件的压缩文件../../../../foo.xy可能会被提取并可能覆盖任意文件。 尽管这不是XSS攻击,但这是为什么必须清理所有输入的一个很好的例子。 每个输入都可能是恶意的,应进行相应的清理。


These are only the first 5 of my top 10.
Want to know more about the following 5?
Read more ...

from: https://dev.to//brianverm/10-java-security-best-practices-be8

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值