[java] Java를 사용하여 지정된 S3 버킷에 지정된 키가 있는지 확인하는 방법

Java를 사용하여 주어진 버킷에 키가 있는지 확인하고 싶습니다. API를 살펴 봤지만 유용한 방법이 없습니다. 사용하려고했지만 getObject예외가 발생했습니다.



답변

jets3t 라이브러리를 사용하십시오. AWS SDK보다 훨씬 쉽고 강력합니다. 이 라이브러리를 사용하여 s3service.getObjectDetails ()를 호출 할 수 있습니다. 이것은 개체의 내용이 아닌 개체의 세부 정보 만 확인하고 검색합니다. 객체가 없으면 404가 발생합니다. 따라서 해당 예외를 포착하고 앱에서 처리 할 수 ​​있습니다.

그러나 이것이 작동하려면 해당 버킷의 사용자에 대한 ListBucket 액세스 권한이 있어야합니다. GetObject 액세스 만 작동하지 않습니다. 그 이유는 Amazon이 ListBucket 액세스 권한이없는 경우 키가 있는지 확인하지 못하도록하기 때문입니다. 키가 있는지 여부를 아는 것만으로도 어떤 경우에는 악의적 인 사용자에게도 충분합니다. 따라서 ListBucket 액세스 권한이 없으면 그렇게 할 수 없습니다.


답변

이제 공식 Java API에 doesObjectExist 메소드가 있습니다.

즐겨!


답변

최신 정보:

그것을 확인하는 새로운 API가있는 것 같습니다. 이 페이지에서 다른 답변을 참조하십시오 : https://stackoverflow.com/a/36653034/435605

원본 게시물 :

사용하다 errorCode.equals("NoSuchKey")

try {
    AmazonS3 s3 = new AmazonS3Client(new ClasspathPropertiesFileCredentialsProvider());
    String bucketName = getBucketName();
    s3.createBucket(bucketName);
    S3Object object = s3.getObject(bucketName, getKey());
} catch (AmazonServiceException e) {
    String errorCode = e.getErrorCode();
    if (!errorCode.equals("NoSuchKey")) {
        throw e;
    }
    Logger.getLogger(getClass()).debug("No such key!!!", e);
}

예외에 대한 참고 사항 : 흐름 제어에 예외를 사용해서는 안된다는 것을 알고 있습니다. 문제는 Amazon이이 흐름을 확인하기위한 API를 제공하지 않았다는 것입니다. 예외에 대한 문서 일뿐입니다.


답변

AWS SDK를 사용하면 getObjectMetadata 메서드를 사용합니다. 이 메서드는 키가 존재하지 않으면 AmazonServiceException을 발생시킵니다.

private AmazonS3 s3;
...
public boolean exists(String path, String name) {
    try {
        s3.getObjectMetadata(bucket, getS3Path(path) + name);
    } catch(AmazonServiceException e) {
        return false;
    }
    return true;
}


답변

Amazon Java SDK 1.10 이상에서는을 사용 getStatusCode()하여 HTTP 응답의 상태 코드를 가져올 수 있습니다. 객체가 없으면 404가됩니다.

import com.amazonaws.services.s3.AmazonS3;
import com.amazonaws.services.s3.model.AmazonS3Exception;
import org.apache.http.HttpStatus;

try {
    AmazonS3 s3 = new AmazonS3Client();
    ObjectMetadata object = s3.getObjectMetadata("my-bucket", "my-client");
} catch (AmazonS3Exception e) {
    if (e.getStatusCode() == HttpStatus.SC_NOT_FOUND) {
        // bucket/key does not exist 
    } else {
        throw e;
    }
}

getObjectMetadata()더 적은 리소스를 소비하며 응답을 getObject().


이전 버전에서는 getErrorCode()적절한 문자열을 사용 하고 확인할 수 있습니다 (버전에 따라 다름).


답변

ListObjectsRequest 설정 Prefix를 키로 사용하십시오.

.NET 코드 :

 public bool Exists(string key)
    {

        using (Amazon.S3.AmazonS3Client client = (Amazon.S3.AmazonS3Client)Amazon.AWSClientFactory.CreateAmazonS3Client(m_accessKey, m_accessSecret))
        {
            ListObjectsRequest request = new ListObjectsRequest();
            request.BucketName = m_bucketName;
            request.Prefix = key;
            using (ListObjectsResponse response = client.ListObjects(request))
            {

                foreach (S3Object o in response.S3Objects)
                {
                    if( o.Key == key )
                        return true;
                }
                return false;
            }
        }
    }.


답변

PHP의 경우 (질문이 Java라는 것을 알고 있지만 Google이 여기로 가져 왔습니다) 스트림 래퍼 및 file_exists를 사용할 수 있습니다.

$bucket = "MyBucket";
$key = "MyKey";
$s3 = Aws\S3\S3Client->factory([...]);
$s3->registerStreamWrapper();
$keyExists = file_exists("s3://$bucket/$key");