ACC 해커톤에서 S3에서 파일을 가져오는 조회 API와, 바로 로컬에 다운로드되는 다운로드 API를 구현했다.
프론트엔드가 없기 때문에 다운로드 응답에서 링크를 누르면 바로 로컬에 다운로드가 되게 했어야 했는데, Content-Disposition 헤더를 사용해 똑같이 presignedUrl을 반환하는 것만으로 구현할 수 있었다!
https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Disposition
Content-Disposition 헤더는 HTTP 응답 헤더 중 하나이다.
content를 브라우저에 띄울지, 로컬에 저장할지를 옵션으로 지정해줄 수 있다.
Content-Disposition: inline
Content-Disposition: attachment
Content-Disposition: attachment; filename="filename.jpg"
- inline(default) : 웹페이지 안에서 띄워진다.
- attachment : 다운로드가 된다.
save as(다른 이름으로 저장)하려면 attachment 뒤에 filename을 붙여주면 된다.
브라우저가 웹페이지 안에서 볼 수 없는 형식이거나, 꼭 다운로드 해야 한다면 Content-Disposition 헤더를 꼭 붙여주어야 한다고 한다.
따라서, 하나의 s3 presignedUrl을 쓰면서 조회는 inline으로, 다운로드는 attachment로 구현하면 되는 것이다.
나는 조회 할 때는 그냥 presignedUrl만 넘겨주면 됐기 때문에 따로 헤더 설정을 하지는 않았고, 다운로드 시에만 헤더를 추가해줬다.
//다운로드 요청일 때는 Content-Disposition 헤더 추가
if (forDownload) {
// 한글 파일명 처리할 수 있도록 파일명을 UTF-8로 인코딩
String encodedFileName = URLEncoder.encode(filePath, StandardCharsets.UTF_8.toString()).replaceAll("\\+", "%20");
generatePresignedUrlRequest.addRequestParameter("response-content-disposition",
"attachment; filename=\"" + encodedFileName + "\"");
}
이런 식으로 뜨게 된다.
728x90
'study > Server' 카테고리의 다른 글
[Gradle] 스프링부트 빌드 시 plain.jar vs .jar 차이점 (0) | 2024.09.24 |
---|---|
Caddy로 도메인 없이 https 설정하기 (1) | 2024.09.07 |
[error] Node.js Error <SyntaxError: Cannot use import statement outside a module> (0) | 2023.11.20 |