AWS - S3

이윤택·2022년 7월 27일
0

인프라

목록 보기
2/11

Amazon S3(Amazon Simple Storage Servive) 는 인터넷용 스토리지 서비스이다.
이번 프로젝트에서는 이미지만 저장할 목적으로 S3을 이용하였다.

Amazon S3 구조

S3에는 BucketObject 라는 단위가 있다. 객체(Object)는 데이터와 메타데이터를 구성하는 저장 단위이며, 버킷(Bucket)은 이러한 객체를 저장하고 관리하는 역할이다. 버킷을 생성하면 Owner 권한을 부여 받아 버킷 단위로 여러가지 기능들을 제어할 수 있다.

S3 특징

  • 제공하는 웹 서비스 인터페이스를 사용하여 웹에서 언제 어디서나 원하는 양의 데이터를 저장하고 검색할 수 있다.
  • 개발자는 Amazon이 자체 웹 사이트의 글로벌 네트워크 운영에 사용하는 것과 같은 높은 확장성과 신뢰성을 갖춘 빠르고 경제적인 데이터 스토리지 인프라에 액세스할 수 있다.
  • 단독 스토리지로도 사용할 수 있으며 EC2, EBS, Glacier와 같은 다른 AWS 서비스와도 함께 사용할 수 있어 클라우드 어플리케이션, 컨텐츠 배포, 백업 및 아카이빙, 재해 복구 및 빅데이터 분석을 포함한 다양한 사례에 알맞다.
  • S3의 버킷은 무한대의 객체를 저장할 수 있으므로 스토리지의 요구를 미리 추정하여 관리할 필요가 없어 확장/축소에 신경쓰지 않아도 된다.
  • HTTPS 프로토콜을 사용하여 SSL로 암호화된 엔드포인트를 통해 데이터를 안전하게 업로드/다운로드 할 수 있다. 또 상주 데이터를 자동으로 암호화 하고 AWS KMS를 통해 S3에서 사용자를 위해 키를 관리하게 하는 방법과 고유한 키를 제공하는 방법 중에서 키 관리 방법을 선택할 수 있는 기능을 제공한다.
  • 사용한 스토리지 만큼 요금이 청구되며 데이터 전송부분에서는 해당 리전 내에서는 데이터 송수신은 무료(다른 AWS 리전으로는 무료가 아님)이고 S3에서 인터넷으로 데이터를 송수신 시에도 가격이 매우 저렴하다.

사용법

Amazon S3에서 버킷을 생성한 뒤

  • AWS Access Key
  • AWS Secret Access Key
  • AWS Region
  • AWS S3 Bucket Name
    을 환경변수에 저장하여 사용하였다
util/aws.ts

import AWS from 'aws-sdk';
import path from 'path';
import { v4 as uuidv4 } from 'uuid';
import { ENV } from '@config';

const {
  AWS_ACCESS_KEY,
  AWS_REGION,
  AWS_SECRET_ACCESS_KEY,
  AWS_S3_BUCKET_NAME,
} = ENV;

const BUCKET_URL = `https://${AWS_S3_BUCKET_NAME}.s3.ap-northeast-2.amazonaws.com`;

const BUCKET = new AWS.S3({
  accessKeyId: AWS_ACCESS_KEY,
  secretAccessKey: AWS_SECRET_ACCESS_KEY,
  region: AWS_REGION,
});

export const uploadImage = async (
  data: Express.Multer.File
): Promise<string | null> => {
  try {
    if (!data) {
      console.log('invalid data');
      return null;
    }

    const fileExtension = path.extname(data.originalname); //파일명
    let imageName = path.basename(data.originalname, fileExtension);
    let uuid = uuidv4();
    const fileName = `${uuid}_${imageName}${fileExtension}`;

    if (AWS_S3_BUCKET_NAME) {
      await BUCKET.putObject({
        Key: fileName,
        Bucket: AWS_S3_BUCKET_NAME,
        ContentType: 'image/*',
        Body: data.buffer,
        ACL: 'public-read',
      }).promise();
      return `${BUCKET_URL}/${fileName}`;
    } else {
      console.log('uploadImage fail, not setting AWS_S3_BUCKET_NAME');
      return null;
    }
  } catch (err: any) {
    console.error('uploadImages error : ', err.message);
    return null;
  }
};
profile
데이터 엔지니어로 전향중인 백엔드 개발자입니다

0개의 댓글