Pythonでスプレッドシートを操作したい！


# はじめに
業務でPython(JupyterLab)を使用するために
一からインストール、設定をする必要があり
ほぼテキストだけの設定手順書を渡されて ?(゜-゜)? となったので
ひとまず最低限使える環境を作るためにやったことを
できる限り簡単にまとめてみました。

※最低限動く を目標にしているので用語の解説などは省略しています

Python始めてみたいけど・・・ とか
とりあえず自分で環境作ってみたい！ とか
そういう方の参考になれば幸いです。

# 環境
Windows 10 Pro
Python 3.9.0

## やりたいこと
・Python(JupyterLab)でスプレッドシートの編集ができる環境の構築

最終的には以下
・特定のサイトからリンクのテキストとURLを取得する
・Googleスプレッドシートの操作(主に書き込み)

# 環境構築
## Pythonのインストール
### 1.インストーラーをダウンロード
[リンク先](https://www.python.org/downloads/windows/)から、必要なバージョンのインストーラーをダウンロードしてください。
諸事情により私はバージョン3.9.0をインストールしていますが、
とくに理由がないようであれば最新のものを選べば問題ないかと思います。

### 2.インストール
インストーラーを起動し、インストールを実行してください。
![インストール.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/4e02f082-cfa9-2675-c388-d7c16249aaa2.jpeg)

インストールに伴う各種設定については、任意で変更してください。
今回は**Install launcher for all users** と **Add Python x.x to PATH**にチェックを入れ、「Install Now」からお任せインストールとしました。

「Setup was successful」が表示されたらインストールは完了です。
![インストール完了.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/850bcdbd-f5c7-f481-c75f-5b759985402e.jpeg)

## JupyterLabのインストール
### 1.JupyterLab のインストール
コマンドプロンプトを立ち上げて以下のコマンドを実行します
```
> pip install jupyterlab
```
少し時間がかかると思うので、コマンドプロンプトの画面を眺めてお待ちください。

### 2.日本語化パッケージをインストール
JupyterLabのインストールが完了したら、引き続き
コマンドプロンプトで以下のコマンドを実行します。
```
> pip install jupyterlab-language-pack-ja-JP
```
日本語化は必須ではないので、
英語で大丈夫！という方はこの手順をスキップしてください。

### 3.モジュールをインストール
前述の「やりたいこと」で必要になるモジュールのみ抜粋してインストールしていきます。
ほかに必要なものがあれば任意でインストールしてください。
今回は以下のモジュールをインストールしました。
+ gspread
スプレッドシートに対して読み取り、書き込み、書式設定などができます

+ oauth2client
Google APIsの認証周りの機能を取り扱います

+ beautifulsoup4
HTMLやXMLファイルからデータを取得することができます

こちらもコマンドプロンプトから以下のコマンドをそれぞれ実行してください。
```
> pip install gspread
> pip install oauth2client
> pip install beautifulsoup4
```
### 4.JupyterLabの起動確認
ここまででインストールは完了しているはずなので、
JupyterLabの起動確認をおこないます。
コマンドプロンプトから以下を実行してください。
```
> Jupyter lab
```
既定のブラウザで以下のような画面が表示されたら問題ありません。
![起動画面.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/998e3c9c-c52b-172a-d4ab-04f68309ea7a.jpeg)

### 5.JupyterLabの終了
JupyterLabを終了するには、画面から **File > Shut Down** の順にクリックして、JupyterLabを終了してください
![終了.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/8c57cded-4413-3166-9c59-b52a2493d46a.jpeg)

お疲れさまでした！
ここまででJupyterLabが使用できるようになりました。
スプレッドシートの操作まではいいかな・・・という方はここまでで問題ないかと思います！

ここからは、JupyterLabからスプレッドシートを操作するための設定などなどをおこなっていきますので、もうしばらくお付き合いください！

## GCP(Google Cloud Platform)の設定
GCPの利用にはアカウントが必要になるので、必要に応じてご用意ください。
以降はGCPアカウント作成済みとして進めていきます。

### 1.プロジェクトの作成
[GCPコンソール](https://console.cloud.google.com/)をひらいて、画面左上の点が三角形に並んでいるアイコンをクリックしてください。
![01_GCPプロジェクト作成_01.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/d3f2af2d-6044-ecd9-1306-1a117ac81283.jpeg)
以下のような画面が表示されるとおもうので、右上の **新しいプロジェクト** をクリックしてください。
![01_GCPプロジェクト作成_02.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/e7d5d26c-a2fa-e386-eefe-49bdd66e6dc4.jpeg)
さらに以下の画面が表示されるので **プロジェクト名** を任意で設定し **作成** をクリックしてください。
![01_GCPプロジェクト作成_03.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/006b528b-2098-5df7-a9ba-a41db853deab.jpeg)



ここまでがGCPプロジェクトの作成手順となります。
### 2.ライブラリの追加
作成したプロジェクトにライブラリを追加していきます。
画面左上の点が三角形に並んでいるアイコンから先ほど作成したプロジェクトを選択しておいてください。

左上の **≡** のメニューから **APIとサービス > ライブラリ** をクリックしてください。
![02_APIの有効化_01.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/7aff7c4a-465c-615a-db52-59e88adb048c.jpeg)
開いた画面で「drive」と検索し、検索結果から「**Google Drive API**」を選択してAPIを有効化してください。
![02_APIの有効化_02.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/6801728e-1287-9df2-9baa-4afcdfaae781.jpeg)
↓↓
![02_APIの有効化_03.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/2300ee9b-ee2b-1f56-8ce0-31667cd37d91.jpeg)
「Google Drive API」の有効化が完了したら、次は「sheet」で検索して「**Google Sheets API**」も同様に有効化してください。
![02_APIの有効化_04.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/ad2be35e-be66-c7ef-0d25-b7d01f9b829d.jpeg)

### 3.GCPサービスアカウントの作成
左上の **≡** のメニューから **APIとサービス > 認証情報** をクリックしてください。
![03_サービスアカウントの作成_01.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/a9adea72-5352-2460-53fb-d820f18b4d84.jpeg)
認証情報画面から「**+ CREATE CREDENTIALS**」をクリック後、「**サービスアカウント**」をクリックしてください。
![03_サービスアカウントの作成_02.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/8ab91ece-bb93-e3ac-84ad-549712275f88.jpeg)
サービスアカウントの詳細設定画面で任意の「**サービスアカウント名**」を入力し「**完了**」をクリックしてください。

![03_サービスアカウントの作成_03.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/ed78b665-d8b1-b86c-c3f6-e17a10d5bdea.jpeg)


サービスアカウントIDはアカウント名から自動で生成されるようです。また、サービスアカウントの説明は自由に入力して問題ないようです。

### 4.秘密鍵の作成
PythonとGoogleアカウントを紐づけるための秘密鍵を発行します。
左上の **≡** のメニューから **APIとサービス > 認証情報** をクリックして、認証情報の画面を開いておいてください

認証情報の画面から、先ほど作成したサービスアカウントのペン(編集)アイコンをクリックします。
アカウント情報の画面が表示されるので、「**キー**」タブから 「**鍵を追加**」⇒「**新しい鍵を作成**」の順にクリックしてください。
![04_秘密鍵ファイルの作成_02.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/4e002242-b96b-7c91-97db-c22d9c025879.jpeg)

秘密鍵のタイプを選択する画面が表示されるので、「**JSON**」を選択し、「**作成**」をクリックします。
![04_秘密鍵ファイルの作成_03.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1349742/6366f7d6-c1a6-a61d-4a8a-6075e7e23a86.jpeg)

JSONファイルがダウンロードされるので、紛失、流出しないよう取り扱いにはご注意ください。

## Googleスプレッドシートの設定
前項で作成したサービスアカウントでスプレッドシートを編集できるように、権限の設定を行います。
事前に操作したいスプレッドシートを作成しておいてください。

### 1.サービスアカウントのメールアドレスを取得
秘密鍵ファイルを開くと「**"client_email"**」 という項目があるので、そこに記載されているメールアドレスをコピーしてください。
`xxxxxx＠xxxxxx.iam.gserviceaccount.com`

### 2.スプレッドシートの編集権限を付与
スプレッドシートを開いて、画面右上の「**共有**」から先ほど取得したメールアドレスを追加します。

今回はPythonから編集することが目的なので「編集者」権限をつけてあげてください。

## おわりに
お疲れさまでした！
これで最低限動く環境が構築できたかと思います。
よいPythonライフをお過ごしください。

環境構築が完了してから、改めて初めに渡された手順書を見て
「あぁ 確かに手順通りだ・・・」となったんですが、作業者がすべて理解している前提でかかれていて、「この手順書で対応できるレベルなら、そもそもこの手順書いらないのでは・・・?」という気持ちになり、人に伝えるというのは難しいことなんだなぁと改めて実感しました。

## おまけ
動作確認として、Yahooニュースの各カテゴリからトピックのみ抜き出してタイトルとURLをスプレッドシートに吐き出すプログラムを書きました。
何かの参考になれば幸いです。
```python:newsList.ipynb
import json
import gspread
import datetime
from oauth2client.service_account import ServiceAccountCredentials 

import re
import requests
from bs4 import BeautifulSoup

scope = ['https://spreadsheets.google.com/feeds',
         'https://www.googleapis.com/auth/drive']

# このコードと同じ階層に秘密鍵のJSONファイルを置く
credentials = ServiceAccountCredentials.from_json_keyfile_name("秘密鍵ファイル名.json", scope)

gc = gspread.authorize(credentials)

# スプレッドシートキーを設定
# https://docs.google.com/spreadsheets/d/**************/edit#gid=0
SPREADSHEET_KEY = '**************'
workbook = gc.open_by_key(SPREADSHEET_KEY)

# 追加するシート名をYYYYMMDDHHmmとする
sheet_name = datetime.datetime.now().strftime('%Y%m%d%H%M')

# ↑↑のシート名でシートを作成
worksheet = workbook.add_worksheet(sheet_name, rows=100, cols=10)

# 見にいくURLのリスト
categories_list = [
    ["トップ","https://www.yahoo.co.jp/"],
    ["国内","https://news.yahoo.co.jp/categories/domestic"],
    ["国際","https://news.yahoo.co.jp/categories/world"],
    ["経済","https://news.yahoo.co.jp/categories/business"],
    ["エンタメ","https://news.yahoo.co.jp/categories/entertainment"],
    ["スポーツ","https://news.yahoo.co.jp/categories/sports"],
    ["IT","https://news.yahoo.co.jp/categories/it"],
    ["科学","https://news.yahoo.co.jp/categories/science"]
]

# 取得したニュースタイトルとURLを格納するリスト
news_list = []

# ニュースタイトルとURLの取得処理
for n in categories_list:
    header = [n[0], ""]
    news_list.append(header)
    URL = n[1]
    
    rest = requests.get(URL)
    soup = BeautifulSoup(rest.text, "html.parser")
    data_list = soup.find_all(href=re.compile("news.yahoo.co.jp/pickup"))
    
    for data in data_list:
        temp_list = [data.text, data.attrs["href"]]
        news_list.append(temp_list)
    
    news_list.append(["", ""])
    
# さっき追加したシートに取得したニュースの一覧を書き出す
worksheet.append_rows(news_list, table_range='A1')
```
### 参考資料
設定を進めるにあたり先達のお力をお借りしました
ありがとうございました
Qiita：[PythonでGoogleスプレッドシートを編集](https://qiita.com/akabei/items/0eac37cb852ad476c6b9)