You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

咨询Java环境下无需调用外部程序获取AWS S3凭证的实现方法

咨询Java环境下无需调用外部程序获取AWS S3凭证的实现方法

嘿,我来帮你搞定这个问题!你之前用aws_signing_helper外部程序获取凭证,现在想纯Java实现完全没问题——结合你手里的证书、私钥以及各类ARN信息,这明显是AWS IAM Roles Anywhere的场景,我给你两种靠谱的方案:

方案一:使用官方IAM Roles Anywhere凭证提供者(推荐)

AWS SDK for Java v2专门提供了RolesAnywhereCredentialsProvider,可以直接通过你的证书、私钥和ARN信息生成凭证,不用依赖外部程序,还自动处理了凭证缓存、过期刷新等逻辑,非常省心。

步骤1:添加依赖(Maven为例)

首先确保项目引入Roles Anywhere的SDK依赖,以及解析PEM私钥所需的BouncyCastle库:

<dependency>
    <groupId>software.amazon.awssdk</groupId>
    <artifactId>rolesanywhere</artifactId>
    <version>2.20.0</version> <!-- 替换成最新的SDK版本 -->
</dependency>
<dependency>
    <groupId>org.bouncycastle</groupId>
    <artifactId>bcpkix-jdk15on</artifactId>
    <version>1.70</version>
</dependency>

步骤2:编写代码实现

下面是完整的示例代码,包含证书、私钥加载,以及S3Client的创建和文件上传操作:

import software.amazon.awssdk.auth.credentials.RolesAnywhereCredentialsProvider;
import software.amazon.awssdk.regions.Region;
import software.amazon.awssdk.services.s3.S3Client;
import org.bouncycastle.jce.provider.BouncyCastleProvider;
import org.bouncycastle.openssl.PEMParser;
import org.bouncycastle.openssl.jcajce.JcaPEMKeyConverter;

import java.io.FileReader;
import java.nio.file.Paths;
import java.security.PrivateKey;
import java.security.Security;
import java.security.cert.CertificateFactory;
import java.security.cert.X509Certificate;
import java.io.FileInputStream;

public class S3RolesAnywhereDemo {
    public static void main(String[] args) throws Exception {
        // 初始化BouncyCastle提供者,用于解析PEM格式的私钥
        Security.addProvider(new BouncyCastleProvider());

        // 加载X.509证书
        CertificateFactory certFactory = CertificateFactory.getInstance("X.509");
        X509Certificate certificate = (X509Certificate) certFactory.generateCertificate(
                new FileInputStream("/path/to/your/certificate.pem"));

        // 加载PEM格式的私钥
        PrivateKey privateKey = loadPrivateKey("/path/to/your/private-key.pem");

        // 创建RolesAnywhere凭证提供者
        RolesAnywhereCredentialsProvider credentialsProvider = RolesAnywhereCredentialsProvider.builder()
                .region(Region.US_EAST_1) // 替换成你的AWS区域
                .trustAnchorArn("your-trust-anchor-arn")
                .profileArn("your-profile-arn")
                .roleArn("your-role-arn")
                .certificate(certificate)
                .privateKey(privateKey)
                .build();

        // 创建S3客户端并执行上传操作
        try (S3Client s3Client = S3Client.builder()
                .region(Region.US_EAST_1)
                .credentialsProvider(credentialsProvider)
                .build()) {
            s3Client.putObject(req -> req.bucket("your-bucket-name").key("test-file.txt"),
                    Paths.get("/path/to/local/file.txt"));
            System.out.println("文件上传成功!");
        }
    }

    // 辅助方法:加载PEM格式的私钥
    private static PrivateKey loadPrivateKey(String filePath) throws Exception {
        PEMParser parser = new PEMParser(new FileReader(filePath));
        Object obj = parser.readObject();
        parser.close();

        JcaPEMKeyConverter converter = new JcaPEMKeyConverter().setProvider("BC");
        if (obj instanceof org.bouncycastle.openssl.PEMKeyPair) {
            return converter.getPrivateKey(((org.bouncycastle.openssl.PEMKeyPair) obj).getPrivateKeyInfo());
        } else if (obj instanceof org.bouncycastle.asn1.pkcs.PrivateKeyInfo) {
            return converter.getPrivateKey((org.bouncycastle.asn1.pkcs.PrivateKeyInfo) obj);
        }
        throw new IllegalArgumentException("无效的私钥文件格式");
    }
}

方案二:手动调用STS AssumeRoleWithCertificate API

如果你需要更定制化的逻辑(比如自定义凭证缓存策略、调整请求参数),可以直接调用STS的AssumeRoleWithCertificate接口获取会话凭证,再用这个凭证创建S3Client。

示例代码

import software.amazon.awssdk.auth.credentials.AwsSessionCredentials;
import software.amazon.awssdk.auth.credentials.StaticCredentialsProvider;
import software.amazon.awssdk.regions.Region;
import software.amazon.awssdk.services.sts.StsClient;
import software.amazon.awssdk.services.sts.model.AssumeRoleWithCertificateRequest;
import software.amazon.awssdk.services.sts.model.AssumeRoleWithCertificateResponse;
import software.amazon.awssdk.services.s3.S3Client;

// 证书和私钥加载代码和方案一一致,此处省略

public class ManualStsDemo {
    public static void main(String[] args) throws Exception {
        X509Certificate certificate = ...; // 加载你的证书
        PrivateKey privateKey = ...; // 加载你的私钥

        // 创建STS客户端
        StsClient stsClient = StsClient.builder()
                .region(Region.US_EAST_1)
                .build();

        // 构造AssumeRoleWithCertificate请求
        AssumeRoleWithCertificateRequest request = AssumeRoleWithCertificateRequest.builder()
                .trustAnchorArn("your-trust-anchor-arn")
                .profileArn("your-profile-arn")
                .roleArn("your-role-arn")
                .certificate(certificate)
                .privateKey(privateKey)
                .durationSeconds(3600) // 凭证有效期,最大支持43200秒
                .build();

        // 获取会话凭证
        AssumeRoleWithCertificateResponse response = stsClient.assumeRoleWithCertificate(request);
        AwsSessionCredentials sessionCredentials = AwsSessionCredentials.create(
                response.credentials().accessKeyId(),
                response.credentials().secretAccessKey(),
                response.credentials().sessionToken()
        );

        // 创建S3客户端并执行操作
        try (S3Client s3Client = S3Client.builder()
                .region(Region.US_EAST_1)
                .credentialsProvider(StaticCredentialsProvider.create(sessionCredentials))
                .build()) {
            // 这里可以执行你的S3操作,比如上传、下载等
        }
    }
}

注意事项

  • 确保你的IAM角色拥有sts:AssumeRoleWithCertificate权限,同时具备S3操作所需的权限(比如s3:PutObject)
  • 证书和私钥要妥善保管,避免泄露
  • 优先选择方案一,官方的凭证提供者已经帮你处理了很多细节,不用自己维护凭证的刷新逻辑

备注:内容来源于stack exchange,提问作者Gord

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.15 10:54:53