@Satoh_D no blog

大分にUターンしたので記念に。調べたこととか作ったこととか食べたこととか

PyDriveを使ってGoogle DriveにDjangoからアクセスしてみる

PyDriveを使ってGoogle Driveを操作する必要があったのでメモ
調べてみると素のPythonのコードはたくさんあるんだけどDjangoを利用してのサンプルが見つからなかったので書いてみた。
とりあえずはOAuthの認証とファイル/フォルダの一覧取得まで。

前提

手順

1. GCPコンソールで認証情報を作成する

  • プロジェクト「PyDrive-Django」を作成(プロジェクト名は何でもよい)
  • プロジェクト「PyDrive-Django」の管理画面を開く
  • 画面中央「APIの概要に移動」をクリック(APIとサービスページに移動)
  • 左側メニュー「認証情報」をクリック
  • 画面上部「認証情報を作成」をクリック
    • 「OAuthクライアントID」を選択
  • OAuthクライアントIDの作成画面にて以下入力する
  • 作成後、認証情報画面にリダイレクトされる
    • OAuth2.0クライアントIDの一覧に先程追加した認証情報が表示される
  • 先程作成した認証情報をダウンロードする(画面右端の矢印ボタン)
    • 認証情報はclient_secrets.jsonとリネームしておく

2. Djangoの実装をしていく

デモ用のアプリをDjangoにて作成する

$ python manage.py startapp gdrive

作成したアプリをsettings.pyで有効化する

# <project-app>/settings.py
INSTALLED_APPS = [
    ...,
    # My Applications
    'gdrive.apps.Gdriveconfig',
    ....
]

gdriveアプリ内に認証情報を入れるディレクトリを作成し、client_secrets.jsonを入れておく

$ cd gdrive
$ mkdir certs
$ cd certs
$ mv /path/to/client_secrets.json .

認証方式の設定ファイルsettings.yamlを作成しclient_secrets.jsonと同じ場所に入れておく
詳細な項目は OAuth made easy — PyDrive 1.3.0 documentation を参照

# <project-root>/gdrive/settings.yaml
# 認証情報をどこから読み込むか(settings or file: default)
client_config_backend: file
# client_config_backend: fileの場合に指定するファイルのパス
client_config_file: /path/to/<project-root>/gdrive/certs/client_secrets.json

# 認証情報をファイルに保存するか
save_credentials: True
# 認証情報をどの形式で保存するか(file固定)
save_credentials_backend: file
# 認証情報の保存先ファイルパス(ファイルが存在しない場合は作成される / 2回目以降は更新)
save_credentials_file: /path/to/<project-root>/gdrive/certs/saved_credentials.json

# 認証情報を自動で更新するか?
get_refresh_token: True

Viewを作成する
とりあえずはQuickstart — PyDrive 1.3.0 documentationに記載されているコードを参考に作成する

import os
from django.shortcuts import render, redirect
from django.http import HttpResponse

from pydrive.auth import GoogleAuth
from pydrive.drive import GoogleDrive

def index(request):
    current_dir_path = os.path.dirname(os.path.abspath(__file__))
    settings_file_path = os.path.join(current_dir_path,'certs/settings.yaml')
    # settings.yamlを元にGoogleAuthを生成する
    gauth = GoogleAuth(settings_file=settings_file_path)
    auth_url = gauth.GetAuthUrl()

    # OAuthの認証がない場合はauth_url(認証用URL)に遷移する
    # 認証済みの場合はfile一覧に遷移する
    if 'code' in request.GET:
        code = request.GET.get('code')
        gauth.Auth(code)
        gauth.SaveCredentials('file')
        return redirect('files')
    else:
        return redirect(auth_url)

def files(request):
    current_dir_path = os.path.dirname(os.path.abspath(__file__))
    settings_file_path = os.path.join(current_dir_path,'certs/settings.yaml')
    gauth = GoogleAuth(settings_file=settings_file_path)

    # Google Driveのroot直下のファイル, フォルダ一覧を取得
    drive = GoogleDrive(gauth)
    file_list = drive.ListFile({'q': "'root' in parents and trashed=false"}).GetList()
    files = []
    for file_item in file_list:
        file = {}
        file['id'] = file_item['id']
        file['title'] = file_item['title']
        file['mimeType'] = file_item['mimeType']
        files.append(file.copy())

    return render(request, 'gdrive/files.html', {
        'files': files
    })

Viewに対応するルーティングを設定する

$ touch <project-root>/gdrive/urls.py
# <project-root>/gdrive/urls.py
from django.urls import path

from . import views

urlpatterns = [
    path('', views.index, name='index'),
    path('files/', views.files, name='files'),
]

# <project-root>/<project-app>/urls.py
from django.contrib import admin
from django.urls import path, include

urlpatterns = [
    ...
    path('gdrive/', include('gdrive.urls'))
]

ビルトインサーバを起動しブラウザでhttp://localhost:8000/gdriveにアクセスする
OAuthの認証ページが表示され、許可をするとファイル一覧が表示されればOK 認証さえできればあとはファイル操作はdocumentみればなんとかなりそう。

参考サイト