AWS S3
로컬 저장소의 한계
- 업로드된 이미지가 서버의 uploads 폴더에 저장되므로, 다른 서버에 접속한 사용자들은 이미지를 볼 수 없다
- 여러 대의 서버가 동작하는 환경에서는 이미지 접근에 제약이 생긴다
- EC2는 24시간 요금을 지불해야 하며, 항상 서버를 실행 상태로 유지해야 한다.
AWS S3 사용
S3 버킷 생성
- AWS Management Console에 로그인 후 S3 서비스를 선택
- 버킷 만들기 버튼을 클릭하고, 고유한 버킷 이름과 리전을 설정
- 퍼블릭 액세스 차단 설정은 필요한 경우 해제하고, 정책 설정
{
"Version":"2012-10-17",
"Statement": [
{
"Sid":"AddPerm",
"Effect": "Allow",
"Principal": "*",
"Action": [
"s3:GetObject",
"s3:PutObject"
],
"Resource": "arn:aws:s3:::버킷이름/*"
}
]
}
- multer-s3 @aws-sdk/client-s3 설치
npm i multer-s3 @aws-sdk/client-s3
- .env 추가
COOKIE_SECRET=
KAKAO_ID=
MYSQL_USERNAME=
MYSQL_PASSWORD=
MYSQL_DATABASE=
MYSQL_HOST=
REDIS_PASSWORD=
REDIS_HOST=
REDIS_PORT=
S3_ACCESS_KEY_ID=
S3_SECRET_ACCESS_KEY=
- s3 연결
const { S3Client } = require("@aws-sdk/client-s3");
const multerS3 = require("multer-s3");
try {
fs.readdirSync("uploads");
} catch (error) {
fs.mkdirSync("uploads");
}
const s3 = new S3Client({
credentials: {
accessKeyId: process.env.S3_ACCESS_KEY_ID,
secretAccessKey: process.env.S3_SECRET_ACCESS_KEY,
},
region: "ap-northeast-2",
});
const upload = multer({
storage: multerS3({
s3,
bucket: "nodebird-lecture-tmp",
key(req, file, cb) {
cb(null, `original/${Date.now()}_${file.originalname}`);
},
}),
limits: { fileSize: 20 * 1024 * 1024 },
});
AWS 람다
- 이미지를 축소시키는 일은 많은 CPU 리소스를 사용함
- 사용한 만큼 요금을 내는 람다를 사용해 리사이징 작업 수행
람다 사용
- 새로운 폴더에 sharp와 @aws-sdk/client-s3설치
- 람다 리사이징 코드 작성
const sharp = require("sharp");
const {
S3Client,
GetObjectCommand,
PutObjectCommand,
} = require("@aws-sdk/client-s3");
const s3 = new S3Client();
exports.handler = async (event, context, callback) => {
const Bucket = event.Records[0].s3.bucket.name;
const Key = decodeURIComponent(event.Records[0].s3.object.key);
const filename = Key.split("/").at(-1);
const ext = Key.split(".").at(-1).toLowerCase();
const requiredFormat = ext === "jpg" ? "jpeg" : ext;
console.log("name", filename, "ext", ext);
try {
const getObject = await s3.send(new GetObjectCommand({ Bucket, Key }));
const buffers = [];
for await (const data of getObject.Body) {
buffers.push(data);
}
const imageBuffer = Buffer.concat(buffers);
console.log("get", imageBuffer.length);
const resizedImage = await sharp(imageBuffer)
.resize(200, 200, { fit: sharp.fit.inside })
.toFormat(requiredFormat)
.toBuffer();
await s3.send(
new PutObjectCommand({
Bucket,
Key: `thumb/${filename}`,
Body: resizedImage,
})
);
console.log("put", resizedImage.length);
return callback(null, `thumb/${filename}`);
} catch (error) {
console.error(error);
return callback(error);
}
};
- 람다 함수 생성하고 파일 업로드
- 트리거 생성으로 S3에 업로드되면 리사이징 되게 설정
참고
Node.js 교과서 : 네이버 도서
네이버 도서 상세정보를 제공합니다.
search.shopping.naver.com
[개정3판] Node.js 교과서 - 기본부터 프로젝트 실습까지 강의 | 제로초(조현영) - 인프런
제로초(조현영) | 노드가 무엇인지부터, 자바스크립트 최신 문법, 노드의 API, npm, 모듈 시스템, 데이터베이스, 테스팅 등을 배우고 5가지 실전 예제로 프로젝트를 만들어 나갑니다. 클라우드에 서
www.inflearn.com
'Node.js' 카테고리의 다른 글
[Node.js 교과서]섹션 15 - AWS에 배포해보기 (0) | 2025.01.07 |
---|---|
[Node.js 교과서] 섹션 14- CLI 프로그램 만들기 (1) | 2024.12.15 |
[Node.js 교과서] 섹션 13- 실시간 경매 시스템 만들기 (0) | 2024.12.13 |
[Node.js 교과서] 섹션 12 - 웹 소켓으로 실시간 데이터 전송하기 (0) | 2024.12.08 |
[Node.js 교과서] 섹션 11 - 노드 서비스 테스트 하기 (3) | 2024.12.05 |