Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/amazon-web-services/14.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 从s3获取预签名,即使输入了错误的访问密钥或密钥_Java_Amazon Web Services_Amazon S3_Aws Sdk_Pre Signed Url - Fatal编程技术网

Java 从s3获取预签名,即使输入了错误的访问密钥或密钥

Java 从s3获取预签名,即使输入了错误的访问密钥或密钥,java,amazon-web-services,amazon-s3,aws-sdk,pre-signed-url,Java,Amazon Web Services,Amazon S3,Aws Sdk,Pre Signed Url,我正在生成一个预签名url,然后通过该url上传文件。 问题是,即使我输入了错误的访问密钥或密钥,我也会得到预签名,尽管如果我尝试使用该url上传,我会得到400个错误 <?xml version="1.0" encoding="UTF-8"?> <Error> <Code>AuthorizationQueryParametersError</Code> <M

我正在生成一个预签名url,然后通过该url上传文件。 问题是,即使我输入了错误的访问密钥或密钥,我也会得到预签名,尽管如果我尝试使用该url上传,我会得到400个错误

  <?xml version="1.0" encoding="UTF-8"?>
    <Error>
        <Code>AuthorizationQueryParametersError</Code>
        <Message>Query-string authentication version 4 requires the X-Amz-Algorithm, X-Amz-Credential, X-Amz-Signature, X-Amz-Date, X-Amz-SignedHeaders, and X-Amz-Expires parameters.</Message>
        <RequestId>{requestId}</RequestId>
        <HostId>{hostId}</HostId>
    </Error>
在生成预签名文件时,是否有某种方法会导致错误,这样我就不必尝试上传文件

    AmazonS3 s3Client = AmazonS3ClientBuilder.standard()
                    .withCredentials(new AWSStaticCredentialsProvider(new BasicAWSCredentials("accessKey", "secretKey")))
                    .withRegion(clientRegion)
                    .build();
    
    GeneratePresignedUrlRequest generatePresignedUrlRequest = new GeneratePresignedUrlRequest(bucketName, objectKey)
     .withMethod(HttpMethod.PUT)
     .withExpiration(expiration);

    URL url = s3Client.generatePresignedUrl(generatePresignedUrlRequest);

生成预签名URL不需要API调用;它可以由框架使用指定的访问密钥和密码生成

当接收到请求时,生成的URL将由S3验证,并且显然只有在使用有效凭据生成URL时才会被接受

底线:为了验证您的凭证,您需要发出一个API请求,该请求实际执行对AWS的调用。这几乎可以是S3客户端上的任何其他方法。

让我们从以下内容开始:

.withCredentials(new AWSStaticCredentialsProvider(new BasicAWSCredentials("accessKey", "secretKey")))
静态凭证与此相反。相反,依赖通过环境变量或执行角色提供的凭据(在EC2、ECS或Lambda上运行时)

验证凭据是否有效的唯一方法是尝试它们。您可以编写一个小的虚拟文件,但是由于S3上的最终一致性,这可能会导致任何应该读取该文件的内容出现问题

还有一个问题是,您给URL的过期时间可能与凭据的生存期不一致

所有这些问题的最佳解决方案是创建一个角色,该角色有权将文件放在S3上,并且持续时间与您的URL过期时间一致(请注意,最长为12小时),然后显式假定该角色以构造请求:

final String assumedRoleArn = "arn:aws:iam::123456789012:role/Example";
final String sessionName = "example";
final String bucketName = "com-example-mybucket";
final String objectKey = "myfile.txt";

final int expirationSeconds = 12 * 3600;
final Date expiresAt = new Date(System.currentTimeMillis() + expirationSeconds * 1000);

AWSSecurityTokenService stsClient = AWSSecurityTokenServiceClientBuilder.defaultClient();

AWSCredentialsProvider credentialsProvider = new STSAssumeRoleSessionCredentialsProvider.Builder(assumedRoleArn, sessionName)
                                             .withStsClient(stsClient)
                                             .withRoleSessionDurationSeconds(expirationSeconds)
                                             .build();

AmazonS3 s3Client = AmazonS3ClientBuilder.standard().withCredentials(credentialsProvider).build();

URL presignedUrl = s3Client.generatePresignedUrl(bucketName, objectKey, expiresAt, HttpMethod.PUT);