在 Azure 应用服务中配置 Tomcat、JBoss 或 Java SE 应用的安全性

本文介绍如何在应用服务中配置特定于 Java 的安全设置。 在应用服务中运行的 Java 应用程序与其他应用程序具有相同 的安全最佳做法 集。

Azure 应用服务在完全托管服务上以两种类型运行Java Web 应用程序:

  • Java Standard Edition (SE)。 Java SE 可以运行部署为 Java 存档(JAR)包的应用,其中包含嵌入式服务器,例如 Spring Boot、Quarkus、Dropwizard 或具有嵌入式 Tomcat 或 Jetty 服务器的应用。
  • Tomcat。 内置的 Tomcat 服务器可以运行部署为 Web 应用程序存档 (WAR) 包的应用。

对用户进行身份验证(简易身份验证)

在 Azure 门户中使用“身份验证和授权”选项设置应用身份验证。 在此处,可以使用 Microsoft Entra ID 或社交登录(如 GitHub)启用身份验证。 仅当配置单个身份验证提供程序时,Azure 门户配置才起作用。 有关详细信息,请参阅 配置应用服务应用以使用 Microsoft Entra 登录 和其他标识提供者的相关文章。

Spring Boot 开发人员可以使用 Microsoft Entra Spring Boot 启动器,通过熟悉的 Spring Security 注解和 API 来保护应用程序。 务必增加 application.properties 文件中的最大标头大小。 我们建议值为 16384

Tomcat 应用程序可通过将 Principal 对象强制转换为 Map 对象这种方式,直接从 Servlet 访问用户的声明。 Map 对象会将每个声明类型映射到该类型的声明集合。 在下面的代码示例中,requestHttpServletRequest 的一个实例。

Map<String, Collection<String>> map = (Map<String, Collection<String>>) request.getUserPrincipal();

现在,你可以检查 Map 对象是否有任何特定的声明。 例如,以下代码片段循环访问所有声明类型,并输出各集合的内容。

for (Object key : map.keySet()) {
        Object value = map.get(key);
        if (value != null && value instanceof Collection {
            Collection claims = (Collection) value;
            for (Object claim : claims) {
                System.out.println(claims);
            }
        }
    }

若要将用户注销,请使用 /.auth/ext/logout 路径。 还有有关 Tomcat HttpServletRequest 接口 及其方法的官方文档。 以下 Servlet 方法是基于你的应用服务配置填充的:

public boolean isSecure()
public String getRemoteAddr()
public String getRemoteHost()
public String getScheme()
public int getServerPort()

要禁用此功能,请创建一个名为 WEBSITE_AUTH_SKIP_PRINCIPAL 的应用程序设置,其值为 1。 若要禁用应用服务添加的所有 servlet 筛选器,请创建名为 WEBSITE_SKIP_FILTERS、值为 1 的设置。

配置 TLS

若要上传现有的 TLS 证书并将其绑定到应用程序的域名,请参阅 在 Azure 应用服务中为自定义域启用 HTTPS。 还可以将应用配置为强制实施 TLS。

使用 Azure 密钥保管库 引用

Azure 密钥保管库 通过访问策略和审核历史记录提供集中式机密管理。 可以在密钥保管库中存储机密,例如密码或连接字符串。 可以通过环境变量访问应用程序中的这些机密。

首先, 向应用授予对密钥保管库的访问权限 ,并在 应用程序设置中对机密进行 密钥保管库 引用。 你可以通过输出环境变量来验证引用是否在远程访问应用服务控制台时解析为密钥。

有关 Spring 配置文件,请参阅 外部化配置

若要在 Spring 配置文件中注入这些机密,请使用环境变量注入语法(即 ${MY_ENV_VAR})。

若要在 Tomcat 配置文件中注入这些机密,请使用环境变量注入语法(即 ${MY_ENV_VAR})。

在 Linux 中使用 Java 密钥存储

默认情况下,在容器启动时, 上传到应用服务 Linux 的任何公共或专用证书将加载到相应的 Java 密钥存储中。 上传证书后,需要重启应用服务,以便将其加载到 Java 密钥存储中。 公共证书被加载到密钥存储中,位于 $JRE_HOME/lib/security/cacerts。 专用证书存储在 $JRE_HOME/lib/security/client.jks.

对于使用 Java 密钥存储中的证书来加密您的 JDBC 连接,可能需要进行更多配置:

初始化 Linux 中的 Java 密钥存储

要初始化 import java.security.KeyStore 对象,请使用密码加载密钥存储文件。 这两个密钥存储的默认密码均为 changeit

KeyStore keyStore = KeyStore.getInstance("jks");
keyStore.load(
    new FileInputStream(System.getenv("JRE_HOME")+"/lib/security/cacerts"),
    "changeit".toCharArray());

KeyStore keyStore = KeyStore.getInstance("pkcs12");
keyStore.load(
    new FileInputStream(System.getenv("JRE_HOME")+"/lib/security/client.jks"),
    "changeit".toCharArray());

手动加载 Linux 中的密钥存储

可以手动向密钥存储加载证书。 若要禁用应用服务自动将证书加载到密钥存储中,请创建一个应用设置 SKIP_JAVA_KEYSTORE_LOAD,其值为 1。 使用 Azure 门户上传到应用服务的所有公共证书都存储在以下。/var/ssl/certs/ 专用证书则存储在 /var/ssl/private/ 下。

若要交互或调试 Java 密钥工具,请打开与应用服务的 SSH 连接 并运行命令 keytool。 有关命令列表,请参阅 密钥工具文档 。 有关 KeyStore API 的详细信息,请参阅 类 KeyStore

请访问 Azure for Java 开发人员 中心,查找 Azure 快速入门、教程和 Java 参考文档。