본문 바로가기

Trouble Shooting

S3 Virtual hosting of buckets에서 bucket, key 정보 추출하기

Public한 Object인 경우, S3에서 제공해 준 링크로 접근할 수 있다. 이 링크들은 아래 구성의 주소 같이 생겼다. 이것을 Virtual hosting of buckets라고 한다.

https://s3.us-west-2.amazonaws.com/jbarr-public/puppy.jpg

 

그런데 만약 Virtual hosting of buckets에서 bucket명과 key값을 추출할 수 있는 메서드가 필요할 때에는 어떻게 해야 할까? 여기에서 bucket과 key는 각각 이렇게 매핑되어야 한다.

  • bucket: jbarr-public
  • key: puppy.jpg

 

Java AWS SDK에서 bucket과 key 값을 추출할 수 있는 유틸리티성 메서드를 지원해준다. 그런데 내가 찾지 못한 건지 Ruby에서는 없는 것 같아 직접 구현해야 한다. Virtual hosting of buckets에는 두 가지 Style이 존재하는데, 이 두 가지 스타일에 대해 알아보았다

 

Path-style requests

Deprecated 된 Style이다. s3(.||-){region-code}.amazonaws.com 의 고정된 Host를 가지고 있고, Path에는 Bucket name과 Key가 순서대로 들어가게 된다. 즉, 아래와 같은 Style을 가지게 되는 것이다.

Original Plan – Support for the path-style model ends on September 30, 2020.

Revised Plan – Support for the path-style model continues for buckets created on or before September 30, 2020. Buckets created after that date must be referenced using the virtual-hosted model.

 

Deprecated 되었지만 관련 글이 써진 블로그를 보면 알 수 있듯이 2020년 9월 30일 이전에 만들어진 Bucket의 경우에는 여전히 Path-style requests를 지원한다. 그렇기 때문에 2020년 9월 30일 이전에 만들어진 Bucket이 있고, Virtual hosting of buckets를 사용하게 된다면 Path-style requests를 고려해서 로직을 작성해야 한다.

 

공식 문서에서는 한 가지 패턴만 소개해줘서 하나의 패턴만 있는 줄 알고 로직을 잘못 작성했다… ㅠ.ㅠ s3와 Region 정보 사이에 ., - 모두 들어갈 수 있으니 이 점을 유의해야 한다.

 

Virtual-hosted–style requests

현재 사용하고 있는 Style이며, Domain name 부분에 Bucket 정보가 들어가게 된다. {bucket-name}.s3.{region-code}.amazonaws.com/{key-name} 이라는 구성의 링크가 있다면 Virtual-hosted–style requests로 링크가 구성된 것이다.

그렇기 때문에 Path-style requests, Virtual-hosted–style requests를 모두 고려해서 S3 URL로부터 Bucket name과 Key를 가져오려면 아래와 같이 정규식을 작성하면 된다.

if /^s3[\\-\\.][a-zA-Z0-9\\-]+\\.amazonaws\\.com/.match?(uri.host) # Path-style requests
  captured = path.match(%r{/(?<bucket>[^/]*)/(?<key>.*)})
  [captured[:bucket], captured[:key]]
else # Virtual-hosted–style requests
  [uri.host.split('.').first, path].delete_prefix('/')
end

 

참고