Programming/Python

파이썬으로 구글 드라이브의 스프레드시트 파일에 데이터 추가하기

makeitworth 2024. 6. 28. 19:14

 

구글 공유 드라이브에 정기적으로 업데이트하는 스프리드시트 파일이 있는 경우가 많을 것이다.

파이썬으로 작업한 데이터를 이 스프레드시트 파일에 자동으로 업데이트하는 방법을 다룬다. 

기본적인 원리는 

1. 기존 파일 다운로드
2. 새 데이터 추가
3. 업데이트된 파일 다시 업로드

이다.

 

1. Google Cloud Console 설정

만약 구글 클라이드 콘솔에서 구글 드라이브 API를 설정한 적이 없다면 해야 한다.

아래 블로그를 참고하면 된다.

Python으로 특정한 파일을 Google Drive 자동 업로드하기

 

핵심은 credentials.json 파일을 내가 작업하고 있는 파일에 저장하는 것이다.

 

2. 업데이트할 파일의 file_id 얻기

폴더 id와 마찬가지로 url의 뒷부분에서 확인할 수 있다. 

단, csv 파일은 주의해야할 점이 있는데, 파일을 열 때, csv 파일을 바로 여는 것이 아닌, gsheet 파일로 변경하여 열기 때문에 스프레드시트 작업창의 주소가 내가 다운받아 업데이트하고자 하는 파일의 주소가 아니라는 점이다.

 

 

 

이렇게 csv 파일의 링크를 복사한 다음  /view?usp=drive_link  탭 앞부분의 주소가 file_id이다. 

 

3. 파이썬 코드

import pandas as pd
from google.oauth2.credentials import Credentials
from googleapiclient.discovery import build
from googleapiclient.http import MediaFileUpload, MediaIoBaseDownload
from google_auth_oauthlib.flow import InstalledAppFlow
from google.auth.transport.requests import Request
import io
import os

SCOPES = ['https://www.googleapis.com/auth/drive.file']

def get_drive_service():
    creds = None
    if os.path.exists('token.json'):
        creds = Credentials.from_authorized_user_file('token.json', SCOPES)
    if not creds or not creds.valid:
        if creds and creds.expired and creds.refresh_token:
            creds.refresh(Request())
        else:
            flow = InstalledAppFlow.from_client_secrets_file('credentials.json', SCOPES)
            creds = flow.run_local_server(port=0)
        with open('token.json', 'w') as token:
            token.write(creds.to_json())
    return build('drive', 'v3', credentials=creds)

def download_file(service, file_id, file_name):
    request = service.files().get_media(fileId=file_id)
    fh = io.BytesIO()
    downloader = MediaIoBaseDownload(fh, request)
    done = False
    while done is False:
        status, done = downloader.next_chunk()
    fh.seek(0)
    with open(file_name, 'wb') as f:
        f.write(fh.read())
    print(f"{file_name} 파일이 다운로드되었습니다.")

def update_csv(file_name, new_data):
    df = pd.read_csv(file_name)
    new_df = pd.DataFrame([new_data])
    updated_df = pd.concat([df, new_df], ignore_index=True)
    updated_df.to_csv(file_name, index=False)
    print(f"{file_name}에 새로운 데이터가 추가되었습니다.")

def upload_file(service, file_name, file_id):
    file_metadata = {'name': file_name}
    media = MediaFileUpload(file_name, resumable=True)
    file = service.files().update(fileId=file_id, body=file_metadata, media_body=media).execute()
    print(f"파일이 업데이트되었습니다. 파일 ID: {file.get('id')}")

def main():
    service = get_drive_service()
    
    # 기존 파일의 ID (Google Drive에서 확인 가능)
    file_id = '내 파일 아이디'
    file_name = '내 파일 이름'
    
    # 파일 다운로드
    download_file(service, file_id, file_name)
    
    # 새로운 데이터 추가 (예시)
    new_data = {'column1' : 'value1', 'column2' : 'value2', 'column3' : 'value3',... }
    update_csv(file_name, new_data)
    
    # 업데이트된 파일 업로드
    upload_file(service, file_name, file_id)

if __name__ == '__main__':
    main()