Project/[Python] 도서 정보 입력 프로그램

[도서 입력 프로그램] 5. Pillow GIF → JPG 변환 (feat. ChatGPT코딩)

CodeNook; 2024. 6. 4. 10:36

[도서 정보 자동 입력 프로그램] 5. Pillow GIF → JPG 변환

 

산 넘어 산이랬던가.. 자동화의 길은 멀고도 멀다.

사람이 했을때 '이럴 때는 이렇게 해야지'하는 예외 사항들이 자동화를 위한 코딩 과정에서는 굉장히 복잡한 변수가 되어버린다.

 

Pillow가 필요하게 된 계기도 그렇다.

 

Yes24가 골때리는 점이 이미지 파일은 오로지 JPG 또는 PNG만 업로드할 수 있다. GIF를 올릴 때는 오류가 뜬다.

 

근데 문제는 우리가 원본 소스로 크롤링하는 알라딘에서는 gif파일이 업로드 가능하다는 것.

 

극히 드문 예외사항이긴 하지만, 만약 ISBN이 없는 신규도서를 알라딘에서 크롤링해서 Yes24로 등록하고자 할때, 만약 등록된 알라딘 이미지가 GIF라면 주소를 그대로 복사해와도 Yes24에 올리려면 다시 다운받은 GIF를 JPG나 PNG로 변환해야하는 번거로움이 있다.

 

문제가 있다면 되게 하라.

 

방법을 찾아보자. 그런데 이번엔 한번 전적으로 ChatGPT에 의존해보도록 하자.

 

먼저 그냥 맨땅에 헤딩으로 바로 ChatGPT에 물어보자. 

 

나: 인터넷 이미지파일의 주소를 입력하면 gif를 jpg로 변환해서 저장한 뒤 저장위치를 출력하는 함수 만들어줘

 

그러자 ChatGPT가 아래와 같은 코드를 답변해주었다.

 

import os
import requests
from PIL import Image

def convert_gif_to_jpg(url, save_path):
    # 이미지 다운로드
    response = requests.get(url)
    if response.status_code == 200:
        # GIF 이미지를 열고 JPG로 변환
        with Image.open(BytesIO(response.content)) as img:
            # JPG로 변환하여 저장
            img = img.convert("RGB")
            img.save(save_path, "JPEG")
            return save_path
    else:
        print("이미지를 다운로드하는 중 오류가 발생했습니다.")
        return None

# 테스트를 위한 이미지 URL
image_url = "https://example.com/image.gif"
# 저장할 파일 경로
save_path = "converted_image.jpg"

# 함수 호출하여 이미지 다운로드 및 변환
result = convert_gif_to_jpg(image_url, save_path)
if result:
    print("변환된 이미지가 저장된 경로:", result)
else:
    print("이미지 변환에 실패했습니다.")

 

여기서 사용하는 주된 라이브러리가 Pillow(PIL)이다. 파이썬에는 워낙 다양한 라이브러리가 많으니 라이브러리를 직접 배우기 보단 주요 라이브러리 이외엔 이렇게 ChatGPT나 검색을 통해 코드를 베끼는것이 더 편하다.

 

아무튼 그래서 위 코드를 실행해보니 에러가 뜬다...😅

NameError: name 'BytesIO' is not defined. Did you mean: 'bytes'?

 

저때는 내가 쓴 GPT가 무료버전인 GPT3.5라 무언가 가끔씩 어설픈 점이 있다. 코드를 보면 with문 안에 BytesIO라는 라이브러리를 사용했는데 import하지 않았다... 이럴땐 그냥 에러메시지를 그대로 ChatGPT에 보여주면 수정된 코드를 보여준다. 위 코드에서 import부분에 from io import BytesIO를 추가해서 에러를 해결했다.

계속해서 GPT에 물어보면서 불필요한 if문을 빼는 등 일부 수정을 했다.

 

import requests
from PIL import Image
from io import BytesIO

def convert_gif_to_jpg(url, save_path): 
    # GIF 이미지를 다운로드하여 이미지 객체로 변환
    response = requests.get(url)
    img = Image.open(BytesIO(response.content))
    # JPG로 변환하여 저장
    img = img.convert("RGB")
    img.save(save_path, "JPEG")
    return save_path

# 테스트를 위한 이미지 URL
image_url = "https://example.com/image.gif"
# 저장할 파일 경로
save_path = "converted_image.jpg"

# 함수 호출하여 이미지 다운로드 및 변환
result = convert_gif_to_jpg(image_url, save_path)
if result:
    print("변환된 이미지가 저장된 경로:", result)
else:
    print("이미지 변환에 실패했습니다.")

 

이제 conver_gif_to_jpg함수는 이미지(gif)주소와 파일 이름을 받아 jpg로 저장해서 저장경로를 return하는 함수가 되었다.

 

추가적으로 수정하고 싶은 부분은, 저장경로 설정이다. 파이썬 실행파일이 있는 곳에 이미지 파일을 두면 폴더가 복잡해지니 따로 image라는 하위 폴더를 만들어서 거기에 저장한뒤 그 저장경로를 불러오도록 코드를 수정해보자. GPT의 도움을 받아서

나: save_path 경로를 현재 py파일이 있는 곳 기준에서 image폴더 안으로 결정하려면 어케해?

 

아래는 수정된 코드

import os
import requests
from PIL import Image
from io import BytesIO

def convert_gif_to_jpg(url, file_name):
    # 이미지를 다운로드하여 이미지 객체로 변환
    response = requests.get(url)
    img = Image.open(BytesIO(response.content))
    
    # 저장할 디렉토리 생성
    save_dir = os.path.join(os.path.dirname(__file__), 'image')
    os.makedirs(save_dir, exist_ok=True)
    
    # 이미지를 JPG로 변환하여 저장
    save_path = os.path.join(save_dir, file_name)
    img = img.convert("RGB")
    img.save(save_path, "JPEG")
    
    return save_path

# 테스트를 위한 이미지 URL
image_url = "https://example.com/image.gif"
# 저장할 파일 이름
file_name = "converted_image.jpg"

# 함수 호출하여 이미지 다운로드 및 변환
result = convert_gif_to_jpg(image_url, file_name)
if result:
    print("변환된 이미지가 저장된 경로:", result)
else:
    print("이미지 변환에 실패했습니다.")

 

이렇게 되어 내 코드에 갖다붙히면 99.5% 완성이다. 나머지 0.5%는?

 

위 코드에 사실 에러가 하나 있다.save_dir 변수 부분에 'image'로만 되어있는데 이렇게 되면 저장경로 주소가 'C:\\ .... \image'로만 끝나버린다. 뒤에 jpg파일 이름이 붙으면 폴더 구분 없이 '...\image파일이름.jpg'로 되어 에러가 발생한다.image 뒤에 백슬래시(\)를 붙혀야하는데 파이썬에서 백슬래시 하나를 입력하려면 \\(앞의 \는 구분기호)로 입력해야 하므로'imge\\'이 되어야 한다.

 

그리하여 최종적으로 완성된 코드 (라이브러리 임포트 코드 등은 생략)

 

def convert_gif_to_jpg(url, file_name): #gif -> jpg 변환
    response=requests.get(url)
    with Image.open(BytesIO(response.content)) as img:
        # 저장할 디렉토리 생성
        save_dir = os.path.join(os.path.dirname(__file__), 'image\\')
        os.makedirs(save_dir, exist_ok=True)
    
        # 이미지를 JPG로 변환하여 저장
        save_path = os.path.join(save_dir, file_name)
        # JPG로 변환하여 저장
        img = img.convert("RGB")
        img.save(save_path, "JPEG")
        return save_path

 

이제 위 함수를 실행하면 자동으로 gif를 jpg로 변환해 image폴더 아래 저장하고 그 저장경로를 반환한다.

위 함수를 실행하기 전에 미리 크롤링한 이미지 주소의 확장자가 gif인지 확인하고(if) 함수를 실행해서 저장경로를 전환하도록 코딩하면 완성!

 

이번 내용을 포함한 ChatGPT 대화 내용을 보고싶다면 아래 링크를 클릭!

https://chatgpt.com/share/a0d6caab-5c05-458b-adea-49d21642798e

 

ChatGPT

A conversational AI system that listens, learns, and challenges

chat.openai.com

 

 

이번 포스팅은 여기까지 😎

 

또 역시 뭔가가 남았다. 다음엔 Pandas를 활용해서 엑셀파일을 읽어와서 기존 데이터와 매칭하는 법을 알아보자.

 

이전글: [도서 입력 프로그램] 4. Autoit 업로드창 제어

 

[도서 입력 프로그램] 4. Autoit 업로드창 제어

[도서 정보 자동 입력 프로그램] 4. Autoit 업로드창 제어 길고긴 Selenium과의 사투가 끝났다. 이제는 프로그램 인터페이스만 신경쓰면 되겠다고 생각을 했는데...이게 웬일.문제는 항상 예상치 못

codenook.site

 

다음글: [도서 입력 프로그램] 6. Pandas 데이터 처리

 

[도서 입력 프로그램] 6. Pandas 데이터 처리

[도서 정보 자동 입력 프로그램] 6. Pandas 데이터 처리 세상은 넓고 예외는 많다.이제 좀 다 끝내고 GUI로 넘어가나 싶었는데 한가지 아쉬운점이 남았다. 바로 란이다. 이 부분은 도서주문이 들어

codenook.site