0. 들어가기
-. 앞 포스팅의 S3 기본 이용법에서 발전해서, 이미지를 변환 후 로컬에 저장하지 않고 메모리에서 바로 S3로 업로드 할 계획.
-. 현재 내가 가지고 있는 파일 (원본)은 *.png 형태이고, 이를 용량 감소를 위해 *.jpg로 변환해서 S3에 업로드 하려고 한다. 왜냐면... PNG 대비 JPG는 약 20% (quality에 따라 달라짐)의 용량을 가지기 때문에 이미지 호스팅에 훨씬 유리하기 때문이다.
1. PNG to JPG 변환
-. python 패키지인 pillow를 이용해서 아주 쉽게 변환 가능하다.
from PIL import Image
im = Image.open("testimage.png")
rgb_im = im.convert('RGB')
rgb_im.save('testimage_100.jpg', quality=100)
rgb_im.save('testimage_95.jpg', quality=95)
rgb_im.save('testimage_90.jpg', quality=90)
-. quality는 jpg의 화질 관련된 숫자..인거같은데, 내가 보기에 90까지는 별 차이가 없어서 90으로 변환했다. 위 방식으로 변환한 이미지를 배열해봤는데, 뭐가 다른지 사실 잘 모르겠다. (세세한 색 연속성 등에서 차이가 있다고 함)
2. 변환 이미지를 메모리에 저장
-. 위 파이썬 코드에선 .save를 이용해 파일로 저장했는데, 이번엔 S3로 바로 업로드를 할 것이다. 로컬에 임시파일을 만들고, 그 파일을 업로드 해도 결과물은 같지만, 하드에 파일을 한번 쓰는 작업이 불필요하게 소요된다.
-. 앞 포스팅에서 upload_file 함수를 사용했는데, 이번엔 upload_fileobj라는 비슷한 함수를 사용한다.
import io
from PIL import Image
im = Image.open("testimage.png")
rgb_im = im.convert('RGB')
TEMP = io.BytesIO()
rgb_im.save(TEMP, format="jpeg", quality=90)
TEMP.seek(0)
client.upload_fileobj(TEMP, Bucket="movics", Key='testimage.jpeg', ExtraArgs={'ContentType': 'image/jpeg'})
-. 요 간단한 코드 짜는 것에 한시간 정도 소요했는데, 내가 시간을 많이 뺏긴 부분이 TEMP.seek(0) 요 한줄을 몰라서였다. 이미지가 자꾸 0B로 올라가더라...
-. 다행히 stack overflow의 한 문답글에서 답을 찾았는데, PIL.Image.save() 함수로 BytesIO 객체에 할당된 메모리에 이미지 데이터를 저장하면 커서가 해당 데이터의 가장 마지막에서 멈춘다. 이후, 다시 TEMP를 호출하게 되면 가장 마지막 자리만 출력, 즉 0B의 이미지가 올라가게 된다. 아래 예시처럼 seek(0) 을 한 경우와 하지 않은 경우를 비교해 봤다.
TEMP1 = copy.copy(TEMP)
client.upload_fileobj(TEMP1, Bucket="movics", Key='testimage_noseek(0).jpeg', ExtraArgs={'ContentType': 'image/jpeg'})
TEMP.seek(0)
client.upload_fileobj(TEMP, Bucket="movics", Key='testimage.jpeg', ExtraArgs={'ContentType': 'image/jpeg'})
-. 아무튼 클리어.
'서버만들기 > aws' 카테고리의 다른 글
python sdk로 dynamodb table 생성 및 읽기/쓰기 용량 관리 (0) | 2023.06.11 |
---|---|
[python/S3] S3에 이미지 업로드 (0) | 2022.11.13 |
[aws] S3 권한 설정 (0) | 2022.10.05 |
[AWS] Elastic Beanstalk CLI (0) | 2021.07.04 |
[aws] Elastic Beanstalk 설정 (콘솔) (0) | 2021.07.03 |
최근댓글