見出し画像

Webスクレイピングを使ってチェックシートを自動作成してみた

序章

こんにちは!インフラストラクチャ事業部の平山です!

早速ですが、皆さんは日々の業務で毎日同じ様な資料を作成してはいませんでしょうか?私が勤めている現場では以下の作業を毎日行っていました。

①チェックシート(yyyy年mm月)を開き、テンプレートから今日分のシートをコピー
②コピーしたシートを今日の日付にリネーム
③当日のチェック項目をリネームしたシートに入力

毎日毎日同じ作業の繰り返し。。。
「実はこの作業って自動化出来るのではないか…?」と思ったので独学でPythonを学び、自動化プログラムを作成しました。
まだ学び始めたばかりで至らぬところがあるかと思いますが、社内で『作ったものを公開してみないか?』と機会を頂いたのでシェアしてみます!宜しくお願いします!


当コードで実行出来る内容

私が今回紹介するコードでは以下の事を実現しております。
参考になる部分がありましたら、各々の環境に合わせて改変して頂ければと思います!

・チェックシート内のテンプレートをコピー
・チェックシートに年月日を入力
・Webスクレイピングで当日のチェック項目を取得

以降は実際に作成したコードと、それについて簡単に解説をさせて頂きたいと思います!


実際に作成したコード

import openpyxl
import datetime
import subprocess
import time
from selenium import webdriver
from selenium.webdriver.common.by import By

driver_path = "driver/chromedriver.exe"
driver = webdriver.Chrome(executable_path=driver_path)
driver.get("取得するデータがあるWebサイトのURL")
links = driver.find_elements(By.CSS_SELECTOR, "要素の指定")
time.sleep(5)

course_class = []
for link in links:
	link_text = link.text
	link_class = link.get_attribute("class")
	course_class.append([link_text, link_class])

today_data = datetime.datetime.now()
today_year = today_data.year
today_month = today_data.month
today_day = today_data.day

def check_create_func():

       day = []
       night = []
       for s in course_class:
               if 'courseName  night' in s:
                       night.append(s[0])
               else:
                       day.append(s[0])

       today_slash=(str(today_year)+"/"+str(today_month)+"/"+str(today_day))

       wb_check=openpyxl.load_workbook(r"ホームディレクトリからExcel格納先ディレクトリまでを記載\チェックシート("+str(today_year)+"年"+ str(today_month)+"月).xlsx")
       ws_check = wb_check.copy_worksheet(wb_check['テンプレート'])

       if len(str(today_month)) == 1:
               if len(str(today_day)) == 1:
                       ws_check.title = '0' + str(today_month) + '0' + str(today_day)
                       sheet_today = wb_check['0' + str(today_month) + '0' + str(today_day)]
               else:
                       ws_check.title='0'+str(today_month)+str(today_day)
                       sheet_today = wb_check['0' + str(today_month) + str(today_day)]
       else:
               if len(str(today_day)) == 1:
                       ws_check.title=str(today_month)+'0'+str(today_day)
                       sheet_today = wb_check[str(today_month) + '0' + str(today_day)]
               else:
                       ws_check.title=str(today_month) + str(today_day)
                       sheet_today=wb_check[str(today_month)+str(today_day)]

       wb_check.move_sheet(sheet_today, offset = -1)

       sheet_today['C3'] = today_slash

       start_column = 3
       for d in day:
               ws_check.cell(5, start_column).value = d
               start_column += 1

       start_column = 3
       for n in night:
               ws_check.cell(6, start_column).value = n
               start_column += 1

       wb_check.save(r"ホームディレクトリからExcel格納先ディレクトリまでを記載\チェックシート(" + str(today_year) + "年" + str(today_month) + "月).xlsx")
       subprocess.Popen(['start', r"ホームディレクトリからExcel格納先ディレクトリまでを記載\チェックシート(" + str(today_year) + "年" + str(today_month) + "月).xlsx"], shell = True)

check_create_func()

driver.quit()


1.ライブラリモジュールのインポート

import openpyxl
import datetime
import subprocess
import time
from selenium import webdriver
from selenium.webdriver.common.by import By

openpyxl
Excelを操作するためのライブラリ。セルに自動入力したり、シートやブックの新規作成なども出来る。
・datetime
時刻を使うためのモジュール。現在の時刻(年月日時分秒)を取得できる。
・subprocess
Pythonで他のアプリを起動したりするモジュール。本コードではExcelを自動で開くために使用。
・time
処理時間等を扱うことが出来るモジュール。本コードではsleep関数を使用した。
・selenium webdriver
ブラウザを自動で操作するためのライブラリ。Webスクレイピングに利用。
・selenium.webdriver.common.by By
取得したHTMLから属性や要素を抽出するモジュール。必要なデータを取得するため使用した。


2.目的のサイトから必要なデータを取得

driver_path = "driver/chromedriver.exe"
driver = webdriver.Chrome(executable_path=driver_path)
driver.get("目的サイトのURL")
links = driver.find_elements(By.CSS_SELECTOR, "要素の指定")
time.sleep(5)

course_class = []
for link in links:
	link_text = link.text
	link_class = link.get_attribute("class")
	course_class.append([link_text, link_class])

1~2行目でWebスクレイピングに使用するWebブラウザのドライバを指定します。(※1)
3行目でWebスクレイピングを実行するWebサイトを指定。
4行目でHTMLから取得したい要素を指定して取得。今回はlinksという配列に要素が合致したデータを格納しています。(※2)6行目以降では4行目で取得したデータを1つずつ取り出して追加処理を実施。別の配列を用意し追加処理したデータを格納しています。

※1:今回のコードでは、このコードが格納されているフォルダにdriverフォルダを作成し、その中にChromedriverを格納しています。
※2:今回の要素指定はあくまで参考となります。Webスクレイピングを実施したいHTMLファイルの要素を解析し、各々コードを変えてください。
私は以下の書籍を参考にしました。非常にわかりやすくおすすめです!
https://www.amazon.co.jp/dp/4815606390


3.コード実行時の年月日を分けて取得

today_data = datetime.datetime.now()
today_year = today_data.year
today_month = today_data.month
today_day = today_data.day

1行目でコードを実行した日付を取得し、2,3,4行目で年/月/日をそれぞれ分けて変数に格納しています。


4.チェックシートを作成する関数を定義

def check_create_func():
        day = []
       night = []
       for s in course_class:
               if 'courseName  night' in s:
                       night.append(s[0])
               else:
                       day.append(s[0])

まず、check_create_funcという名前の関数を定義しております。
2行目以降は条件によってデータを格納する変数を変えています。
条件に合致した場合はnight変数に、合致しなかった場合はday変数に格納しています。


today_slash= (str(today_year)+"/"+str(today_month)+"/"+str(today_day))
wb_check = openpyxl.load_workbook("●\●\●\チェックシート(" + str(today_year) + "年" + str(today_month) + "月).xlsx")
ws_check = wb_check.copy_worksheet(wb_check['テンプレート'])

today_slash変数にコードを実行した年月日を「yyyy/mm/dd」という文字列に整形して格納。この変数内の文字列はEXCELのセルに入力する際に使用します。(例:2021/10/26)
wb_check変数はチェックシートを作成するEXCELシートを指定するためのEXCELファイル名を格納する変数になります。(例:2021年10月.xlsx)
ws_check変数はwb_check変数に格納しているEXCELファイルを呼び出して、そのEXCELファイルに内に事前に作成してある【テンプレート】シートを複製し、複製先を格納しています。


       if len(str(today_month)) == 1:
               if len(str(today_day)) == 1:
                       ws_check.title = '0' + str(today_month) + '0' + str(today_day)
                       sheet_today = wb_check['0' + str(today_month) + '0' + str(today_day)]
               else:
                       ws_check.title='0'+str(today_month)+str(today_day)
                       sheet_today = wb_check['0' + str(today_month) + str(today_day)]
       else:
               if len(str(today_day)) == 1:
                       ws_check.title=str(today_month)+'0'+str(today_day)
                       sheet_today = wb_check[str(today_month) + '0' + str(today_day)]
               else:
                       ws_check.title=str(today_month) + str(today_day)
                       sheet_today=wb_check[str(today_month)+str(today_day)]

上記の条件式では本コード実行時の日付から以下のどれに当てはまるかを確認し、先程複製した【テンプレート】というシートをopenpyxlの.titleでリネームしています。(例:【テンプレート】シート→【1026】シート)

①月が一桁(1月~9月)であり、日が一桁(1日~9日)である。
②月が一桁(1月~9月)であり、日が二桁(10日~31日)である。
③月が二桁(10月~12月)であり、日が一桁(1日~9日)である。
④月が二桁(10月~12月)であり、日が二桁(10日~31日)である。

そのあと、リネームしたシートを指定してsheet_today変数に格納しています。この変数は後程使用します。

ここまでで、以下の様に指定したEXCELシート上にコード実行日付のチェックシートのコピーが作成されました。

ca-ページ15.drawio


       wb_check.move_sheet(sheet_today, offset = -1)

       sheet_today['C3'] = today_slash

上記は、リネームした当日日付のシートを1つ前に移動しています。
そして移動した当日日付のシートのC3セルにtoday_slash変数に格納したyyyy/mm/dd形式の文字列を記載しています。
以下のスクショを見て頂くと、シートが移動していることとC3に日付が入力されていることが分かると思います。

図2


       start_column = 3
       for d in day:
               ws_check.cell(5, start_column).value = d
               start_column += 1

       start_column = 3
       for n in night:
               ws_check.cell(6, start_column).value = n
               start_column += 1

start_column変数を定義し、そこに数値の3を格納しています。
その後day変数に格納されているデータを1つずつ呼び出し、【当日日付】シートの(行,列)=(5,3)の部分に呼び出したデータを記載。その後start_column変数上に存在する3に1を足して4にして(5,,4)のセルに次のデータを記載~を繰り返しています。
EXCEL上では以下の部分にWebスクレイピングで取得したデータが入っていくイメージになります!


wb_check.save(r"●\●\●\チェックシート(" + str(today_year) + "年" + str(today_month) + "月).xlsx")
subprocess.Popen(['start', r"●\●\●\チェックシート(" + str(today_year) + "年" + str(today_month) + "月).xlsx"], shell = True)

ここまで自動生成したら、この状態を一旦保存します。
そして作成した当日シートは、作成した当日に使うので自動で開くように処理を嚙ましています。


今回の作成で学んだ事・苦労した事・次に生かしたい事

タグや要素を理解するのには苦労しました…。
また、毎日5分程度の簡単な作業ではありましたが、自動化したことにより、他の作業にすぐに着手することが出来、業務の効率化も図ることが出来ました!
この経験を活かし、次は趣味の範囲として当日の最新ニュースの取得だったり、他に自動化出来そうな定例業務をPythonで自働化出来ればと思います。


まとめ

今回はPythonを用いたWebスクレイピングとExcelの自動作成を紹介しました。私自身Pythonって何それ?の状態から勉強した身ですので、意欲さえあれば誰でも簡単に出来るかなと思います。
それだけPythonはプログラマーではない人に優しいプログラミング言語でした。

皆さんの業務の中にも毎日同じことを繰り返し行っている作業があるかと思います。もし少しでも自動化出来るのかな…と思ったなら、ぜひ!Pythonを使って作業の効率化を行ってみてはいかがでしょうか。こういった小さな気づきが自身のスキルアップに繋がると私は考えています。


画像4

◾️クラスアクトについて

”世代を超えて永続する一流の組織であること”
”ここで働く人が自分らしい幸せを感じられること”

これこそが、クラスアクトが目指す会社のあり方です。
SDGsの達成目標にもある通り、働きがいも経済成長もある社会の実現に
貢献していきたい。
社員のみなさんが、出産や育児などのライフイベントを楽しみながら、一流のエンジニアを目指せる環境を用意していきたい。
そのように心身ともに健康に過ごせる環境で、技術力を高めてお客様により高度なサービスを提供することが、お客様に選ばれる最高のエンジニアを多く輩出すること、ひいては日本のITインフラを支える企業になることにつながると信じています。

そんなクラスアクトでは、エンジニアを募集中です。
現エンジニアの方はもちろん、未経験の方もエンジニアとして活躍していける制度を整えています。
まずはホームページや弊社のWantedlyを覗いてみてください。


この記事が気に入ったらサポートをしてみませんか?