AWS S3 버킷생성후 node js와 연동하기

2025. 2. 21. 11:04개발 스토리

반응형

기존 개발된 파일업로드 기능이 순전히 프로젝트 안에 files이라는 디렉토리에 저장되는 형태였다.

EC2자체가 스토리지 역할이 주가 아니기 때문에 서버의 파일 리소스는 S3를 통하여 관리하기로 했다.

 

일단 AWS S3탭에서 버킷을 생성한다.

옵션들은 기본으로 설정되어 있는 그대로 적용하고 버킷명만 지정해주었다.

 

 

 

 

이후 파일을 업로드해보고 외부에서 리소스 경로url에 접속이 되는지 확인해봤다.

초기 설정 그대로 모든 퍼블릭 액세스 차단으로 적용했기 때문에 외부에서 접속은 안되는 상태였다. 

 

 

내가 적용하고 싶은 방법은 외부에서 리소스를 다운로드 가능하며, 현재 운행하고 있는 서비스의 WAS나, 웹사이트에서만 리소스를 업로드할수 있도록 하고 싶었다.

 

 

 

 

IAM S3 전용 사용자 생성

 

1. iam > 사용자 > 사용자 생성 화면 진입 후 사용자 이름을 지정

2. 다음 화면진입후 그룹에 사용자 추가 선택,

3. 그룹생성 클릭, 사용자 그룹 이름을 추가하고 권한정책에서 AmazonS3FullAccess권한을 선택한다

4. 다음버튼을 클릭하여 s3용 사용자 생성 완료

 

 

 

 

 

IAM 사용자 액세스키 생성

1. 사용자 목록에서 액세스키를 생성할 계정을 선택

2. 보안자격증명 탭 클릭 스크롤 내려보면 액세스 카테고리에서 액세스키 만들기 버튼 클릭

3. 로컬코드 선택 이후 다음 버튼을 눌러 생성완료

 

 

 

 

 

S3 정책 설정

 

S3 권한 탭에서 퍼블릭 액세스 차단을 비활성화 하고 정책에 아래와 같이 내용을 추가한다.

이후에 다시 사진의 경로를 접속하면 정상적으로 사진이 보여진다.

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "Statement1",
            "Effect": "Allow",
            "Principal": "*",
            "Action": "s3:GetObject",
            "Resource": "arn:aws:s3:::klaus-krpt/*"
        },
        {
            "Sid": "Statement2",
            "Effect": "Allow",
            "Principal": {
                "AWS": "arn:aws:iam::590184131293:user/klaus-krpt-s3"
            },
            "Action": "s3:PutObject",
            "Resource": "arn:aws:s3:::klaus-krpt/*"
        }
    ]
}

 

 

 

 

적용코드

# aws sdk 패키지 설치
npm install --save @aws-sdk/client-s3

 

const {
  S3Client,
  PutObjectCommand,
  GetObjectCommand,
  DeleteObjectCommand,
} = require("@aws-sdk/client-s3");

require("dotenv").config();

// AWS S3 관련 환경 변수 세팅 정보
const AWS_S3_REGION = process.env.AWS_S3_REGION;
const AWS_S3_ACCESS_KEY_ID = process.env.AWS_S3_ACCESS_KEY_ID;
const AWS_S3_SECRET_ACCESS_KEY = process.env.AWS_S3_SECRET_ACCESS_KEY;
const AWS_S3_BUCKET = process.env.AWS_S3_BUCKET;

// S3 서비스 생성 함수
const createS3Service = () => {
  const s3 = new S3Client({
    region: AWS_S3_REGION, // 리전 설정
    credentials: {
      accessKeyId: AWS_S3_ACCESS_KEY_ID,
      secretAccessKey: AWS_S3_SECRET_ACCESS_KEY,
    },
  });

  return s3;
};

// 파일 업로드 함수
const uploadFile = async (s3, file, s3Key) => {
  const uploadParams = {
    Bucket: AWS_S3_BUCKET, // S3 버킷 이름
    Key: s3Key, // S3 내 파일의 경로 및 파일명
    Body: file, // 파일 내용
  };

  try {
    const command = new PutObjectCommand(uploadParams);
    const data = await s3.send(command);
    console.log("File uploaded successfully:", data);

    return s3Key;
  } catch (err) {
    console.error("Error uploading file:", err);
    throw err;
  }
};

const getFile = async (s3, s3Key) => {
  const downloadParams = {
    Bucket: AWS_S3_BUCKET,
    Key: s3Key,
  };

  try {
    const command = new GetObjectCommand(downloadParams);
    const data = await s3.send(command);
    return await data.Body.transformToByteArray();
  } catch (err) {
    console.error("Error downloading file:", err);
    throw err;
  }
};

const deleteFile = async (s3, s3Key) => {
  const deleteParams = {
    Bucket: AWS_S3_BUCKET,
    Key: s3Key,
  };

  try {
    const command = new DeleteObjectCommand(deleteParams);
    const data = await s3.send(command);
    console.log("File deleted successfully:", data);
    return data;
  } catch (err) {
    console.error("Error deleting file:", err);
    throw err;
  }
};

module.exports = {
  createS3Service,
  uploadFile,
  getFile,
  deleteFile,
};

 

반응형