AWS S3 연동시켜버리기

leverest96·2022년 12월 11일
0

AWS

목록 보기
1/1
post-thumbnail

AWS S3 연동을 하기 위해 구글링을 했지만 대부분의 경우 AwsS3Config / AwsS3Service / AwsS3Controller / application-aws.yml 네 가지 파일로 나뉘어 있었다.

하지만 설계를 하면서 2가지의 이유로 구조를 조금 바꾸었다.

우선, 초기 AWS S3를 연동하고자 했던 목적은 프로필 사진 업로드를 위한 것이었지만 이후 게시물에 대한 사진 또한 올리게 될 경우 즉 확장성을 고려하여 따로 utility 패키지로 빼서 관리하기 위함이었다.

두번째이자 마지막은 설계에 있어서의 통일성을 가지고자 패키지 구조를 조금 바꾸어야 했다.

그래서 선택한 구조는 AwsS3Manager / AwsProperties / AwsS3Properties / AppConfig / aws.yml / application.yml이었다.

기존 설계는 구글링을 하면 많이 나오기 때문에 내가 새로 만들게 된 녀석만 올릴거야요.

0. build.gradle (dependency)

implementation 'io.awspring.cloud:spring-cloud-starter-aws:2.4.0'

1. resources

  1. application.yml

    spring:
      config:
        import:
          - classpath:properties/aws.yml
          
      # 기본 multipart file의 크기는 1MB로 더 큰 용량을 사용하기 위해 설정
      servlet:
        multipart:
          max-file-size: 5MB
          max-request-size: 5MB
  2. aws.yml : 물론, 환경변수 등록은 필요하다.

    • 싫으면 secret manager에 등록하든동!
    aws:
      access-key: ${AWS_ACCESS_KEY:aws-access-key}
      secret-key: ${AWS_SECRET_KEY:aws-secret-key}
    
      s3:
        region: ap-northeast-2
        bucket: ${AWS_S3_BUCKET:aws-s3-bucket}

2. main / java

  1. AppConfig

    @Configuration
    public class AppConfig {
        @Bean
        public AmazonS3 amazonS3(final AwsProperties awsProperties, final AwsS3Properties awsS3Properties) {
            final AWSCredentials credentials = new BasicAWSCredentials(awsProperties.getAccessKey(), awsProperties.getSecretKey());
    
            return AmazonS3ClientBuilder.standard()
                    .withCredentials(new AWSStaticCredentialsProvider(credentials))
                    .withRegion(awsS3Properties.getRegion())
                    .build();
        }
    
        # 기존과는 다르게 AwsS3Manager를 Service로 두지 않았기 때문에 AppConfig에서 AwsS3Manager를 bean으로 등록시켜준다.
        @Bean
        public AwsS3Manager awsS3Manager(final AmazonS3 amazonS3, final AwsS3Properties awsS3Properties) {
            return new AwsS3Manager(amazonS3, awsS3Properties.getBucket());
        }
    }
  2. AwsProperties : AWS에 대한 properties

    @ConfigurationProperties(prefix = "aws")
    @ConstructorBinding
    @RequiredArgsConstructor
    @Getter
    public class AwsProperties {
        private final String accessKey;
    
        private final String secretKey;
    }
  3. AwsS3Properties : AWS 중 S3에 대한 properties

    @ConfigurationProperties(prefix = "aws.s3")
    @ConstructorBinding
    @RequiredArgsConstructor
    @Getter
    public class AwsS3Properties {
        private final String region;
    
        private final String bucket;
    }
  4. AwsS3Manager

    @RequiredArgsConstructor
    public class AwsS3Manager {
        private final AmazonS3 amazonS3;
    
        private final String bucket;
    
        public List<String> uploadFiles(final Function<String, String> titleGenerator, final List<MultipartFile> multipartFile) {
            final List<String> fileNameList = new ArrayList<>();
    
            multipartFile.forEach(file -> {
                final String originalFileName = file.getOriginalFilename();
                final String fileName = titleGenerator.apply(originalFileName);
    
                final ObjectMetadata objectMetadata = new ObjectMetadata();
                objectMetadata.setContentLength(file.getSize());
                objectMetadata.setContentType(file.getContentType());
    
                try (final InputStream inputStream = file.getInputStream()) {
                    amazonS3.putObject(new PutObjectRequest(bucket, fileName, inputStream, objectMetadata)
                            .withCannedAcl(CannedAccessControlList.PublicRead));
                } catch (final IOException e) {
                    throw new IllegalArgumentException();
                }
    
                fileNameList.add(fileName);
            });
    
            return fileNameList;
        }
    }

https://jane514.tistory.com/10

profile
응애 난 애기 개발자

0개의 댓글