AWS S3란 AWS(Amazon Web Service)에서 제공하는 인터넷 스토리지 서비스로서 이미지, 파일 등의 데이터들을 저장해주는 시스템을 말합니다. 기본적으로 트래픽에 따른 시스템적인 문제가 없으며, 파일에 대한 접근 권한을 지정할 수 있어 유용하게 사용됩니다. 필자는 서비스의 이미지 관리를 위해 AWS S3를 활용하고자 하였습니다.
우선 S3 이미지 관리를 위해 버킷을 생성합니다.
default로 설정되어 있는 액세스 차단을 모두 해제합니다. 이를 통해 S3 url을 통해 접근이 가능합니다.
버킷 설정 -> 권한 -> 버킷 정책 편집 -> 정책 생성기
*은 권한을 모두에게 부여합니다.
ARN은 정책 편집란에서 복사할 수 있습니다.
ARN을 입력할 때에는 복사내용을 붙여넣기 한 후 가장 뒤에 /*를 넣어야 합니다.
정책을 Add한 후 Generate Policy를 클릭하면 위와 같은 정책 JSON 파일이 생성됩니다. 생성된 JSON 파일을 복사합니다.
복사한 JSON 파일을 버킷 정책의 정책 부분에 붙여넣기 한 후 저장합니다.
버킷 생성과 권한 설정을 진행했으니 이미지를 빌드하고 url로 접근했을 때 해당 이미지를 추출할 수 있는지 테스트를 진행합니다.
이미지 업로드 후 이미지 제목을 클릭하면 위와 같이 객체 개요로 이동됩니다.
우측 하단의 객체 URL을 통해 외부에서도 접근 가능한 이미지 URL을 확인할 수 있습니다.
현재까지 AWS S3 버킷을 통해 이미지를 직접 업로드하고, URL을 통해 외부에서 접근할 수 있는지 알아보았습니다. 이번엔 직접 이미지를 업로드하는 것이 아닌 Node를 통해 S3 이미지 업로드 API를 구현하는 방법을 알아보겠습니다.
우선 AWS S3와 연동하기 위해 access key와 secret access key가 필요합니다. 해당 정보는 env 파일로 관리할 수 있습니다.
access key는 AWS / 사용자 계정 관리에서 사용자 추가 후 key를 발급하면 얻을 수 있습니다. 이때 한 번 발급하면 다시 확인할 수 없으니 키 값을 잘 저장해야 합니다.
그리고 S3의 객체 소유권의 ACL을 활성화 해줘야 합니다.
ACL 활성화는 이미지를 직접 업로드하지 않고 코드를 통해 S3에 접근하기 위해서 필요합니다.
npm install --save aws-sdk
aws-sdk npm 모듈을 설치합니다.
import AWS from 'aws-sdk';
import multer from 'multer';
import multers3 from 'multer-s3';
import path from 'path';
import { Request} from "express";
import dotenv from 'dotenv';
dotenv.config();
AWS.config.update({ // AWS 설정
region: process.env.AWS_REGION,
accessKeyId: process.env.AWS_ACCESS_KEY_ID,
secretAccessKey: process.env.AWS_SECRET_ACCESS_KEY
});
const allowedExtensions = ['.png', '.jpg', '.JPG', '.PNG', '.jpeg', '.JPEG', '.bmp', '.BMP'];
const imageUploader = multer({ // multer 설정
storage: multers3({
s3: new AWS.S3() as any,
bucket: process.env.AWS_BUCKET_NAME as string, // 업로드할 버킷 이름
key: (req:Request, file, callback) => {
const uploadDirectory = req.query.directory ?? 'uploads';
const extension = path.extname(file.originalname);
if (!allowedExtensions.includes(extension)) {
return callback(new Error('wrong extension'));
}
callback(null, `${uploadDirectory}/${Date.now()}_${file.originalname}`); // 저장될 S3의 저장소 경로 설정
},
acl: 'public-read-write',
}),
});
export default imageUploader;
Node(TypeScript)를 통해 이미지 업로드 함수를 구현하였습니다.
앞서 설정한 accessKey, secretAccessKey를 env 파일 값으로 관리하여 AWS config를 설정합니다. 이때 이미지 파일의 형식을 png, jpg, jpeg 등 여러 형식으로 정의하였습니다. 이미지 업로드 함수는 express, multer를 이용하여 구현하였고, 이미지 업로드 시 디렉토리 명을 쿼리에 직접 입력하여 API를 호출하는 형식으로 구현하였습니다. 만약 디렉토리 명을 따로 지정하지 않는다면 default값으로 디렉토리가 생성됩니다.
해당 함수는 router, controller 구조를 통해 하나의 이미지 업로드 API로서 동작할 수 있습니다.
s3로 이미지를 업로드하는 방법이 궁금했는데 덕분에 잘 알게 됐어요. 글을 이해하기 쉽게 잘 쓰시네요!