Google Cloud Function に ターミナルからデプロイ
【1】概要
◆背景
・以下の様にコードと共に認証用のファイルが入ったフォルダをアップロードしたいが通常通りの関数作成ではこのようにできない。
・ターミナルからならできるようなので実際にやってみる

◆やりたいこと
・ターミナルから複数ファイル(コードと共に認証用のファイルが入ったフォルダ)をGCFにデプロイする
【2】内容
◆コード全文
cd {対象のファイルが入っているフォルダまで移動}
gcloud functions deploy {デプロイしたい関数名} --runtime python39 --trigger-http --allow-unauthenticated --timeout=540
【3】補足
◆複数のプロジェクトを所持していてデプロイ先のプロジェクトを変更したい時
現在のプロジェクトがデプロイ先のプロジェクトとして設定されているか確認する
$ gcloud config list [core] account = *****@***** disable_usage_reporting = True project = [プロジェクト名]
もし意図したプロジェクトと違っていたら以下のコマンドで変更。
$ gcloud config set project [プロジェクト名]
◆2023/11/15追記
久々に実施したら以下のようなエラーが発生した。
(gcloud.functions.deploy) There was a problem refreshing your current auth tokens: ('invalid_grant: Token has been expired or revoked.', {'error': 'invalid_grant', 'error_description': 'Token has been expired or revoked.'})
以下のコマンドでログインしたら解決した。
gcloud auth login
【Python】SeleniumでログインしCSVダウンロード&そのCSVをPandasで加工してBigQueryに転送
【1】概要
◆背景
・毎日決まったところからCSVを落とし、BigQueryに転送する処理をしたい。
【2】内容
◆コード全文
import time
from selenium import webdriver
from selenium.webdriver.common.by import By
import pandas as pd
from datetime import datetime as dt, timedelta
import datetime
from webdriver_manager.chrome import ChromeDriverManager
import os
from google.cloud import bigquery
os.getcwd()
#フォルダ指定
default_folder_name = "{ファルダパス}"
os.chdir(default_folder_name)
#日付指定
tdatetime = dt.now()
date_nonhyphen = tdatetime.strftime('%Y%m%d')
date_hyphen = tdatetime.strftime('%Y-%m-%d')
time_str = tdatetime.strftime('%Y-%m-%d %H:%M:%S')
#Seleniumを使うための設定とログインしたい画面への遷移
URL = "{ログインしたいサイトのURL}"
driver_path = "./chromedriver"
driver = webdriver.Chrome(ChromeDriverManager().install())
#driver = webdriver.Chrome()
driver.maximize_window()
time.sleep(2.5)
driver.get(URL)
time.sleep(2.5)
# emailをクリックする(ここの指定はサイトによって変わる)
email_btn = driver.find_element(By.NAME,'email')
email_btn.click()
# 1秒待機
time.sleep(1)
# emailを入力
email_btn.send_keys("{ログインに必要なemail}")
# 1秒待機
time.sleep(1)
# パスワードをクリック(ここの指定はサイトによって変わる)
password_btn = driver.find_element(By.NAME,'password')
password_btn.click()
# パスワードを入力
password_btn.send_keys("{ログインに必要なPassword}")
# 1秒待機
time.sleep(1)
# サブミットをクリックしログイン、これでログインできる
login_btn = driver.find_element(By.NAME,'submit')
login_btn.click()
#ファイルをdownload
posts_download_url = "{ダウンロードURL}"
driver.get(posts_download_url)
#30秒待機
time.sleep(30)
# ブラウザを終了する。
driver.close()
#ファイル名指定
file_name = "{ダウンロードされるファイルのCSV名}"
#ダウンロードフォルダ指定
key="HOME"
folder = os.getenv(key)
print(folder)
folder_name = folder+"/Downloads"
os.getcwd()
os.chdir(folder_name)
#CSVをダウンロード
df = pd.read_csv(file_name)
#日時列を追加
df["uploaded_at"] = time_str
#最初のフォルダに戻る
os.chdir(default_folder_name)
#GCPの設定
GCP_PROJECT_NAME = "{GCPのプロジェクト名}"
os.environ['OAUTHLIB_INSECURE_TRANSPORT'] = '1'
os.environ['GOOGLE_APPLICATION_CREDENTIALS'] = '{GCPの認証ファイルの場所}'
# bigQueryクライアント認証
client = bigquery.Client(project=GCP_PROJECT_NAME)
#BQにアップロード
df.to_gbq("{テーブル名}"+date_nonhyphen,if_exists="replace")
【3】補足
◆コード補足
●chromedriverの更新が必要
通常だと更新が必要だが、ChromeDriverManagerのモジュールを使用することで更新不要になる。
driver = webdriver.Chrome() #更新必要 driver = webdriver.Chrome(ChromeDriverManager().install()) #更新不要
【Python】SeleniumでGoogleの検索結果をリストとして抽出
【2】内容
◆コード全文
import time
from selenium import webdriver
from selenium.webdriver.common.by import By
from webdriver_manager.chrome import ChromeDriverManager
#from selenium.webdriver.common.keys import Keys
import pandas as pd
import tqdm
import datetime
#Seleniumを使うための設定とgoogleの画面への遷移
MIN_INTERVAL = 0.5
INTERVAL = 2.5
MINUTE_INTERVAL = 60.0
URL = "https://www.google.com/"
driver_path = "./chromedriver"
driver = webdriver.Chrome(ChromeDriverManager().install())
driver.maximize_window()
time.sleep(INTERVAL)
driver.get(URL)
time.sleep(INTERVAL)
#googleで検索する文字をリスト化
search_string = ['味噌 スープ','しいたけ キャベツ']
#results = None
concat_df = None
result_df = None
for query_string in tqdm.tqdm(search_string):
## フォームに入っている情報を削除
driver.find_element(By.NAME,'q').clear()
## 検索ワードを送信する
driver.find_element(By.NAME,'q').send_keys(query_string)
# 検索を実行
driver.find_element(By.NAME,'q').submit()
# 待機
time.sleep(INTERVAL)
#検索結果の一覧を取得する
results = []
flag = False
while True:
#g_aryは検索結果のタイトルとURLが入った要素をリストで保持
g_ary = driver.find_elements(By.CLASS_NAME,'g')
#print(g_ary)
#title = driver.title
#url = driver.get(url)
for g in g_ary:
result = {}
#YOUTUBEのときだけ場合わけ、それ以外はスキップ(Wiki等)
try:
result['url'] = g.find_element(By.CLASS_NAME,'yuRUbf').find_element(By.TAG_NAME,'a').get_attribute('href')
except: #YOUTUBE
try:
result['url'] = g.find_element(By.CLASS_NAME,'ct3b9e').find_element(By.TAG_NAME,'a').get_attribute('href')
except: #Wiki等
break
result['title'] = g.find_element(By.TAG_NAME,'h3').text
results.append(result)
if len(results) >= 20:#抽出する件数を指定
flag = True
break
if flag:
break
#次のページへ
driver.find_element(By.ID,'pnnext').click()
#time.sleep(INTERVAL)
#pandasでデータフレーム化
result_df = pd.DataFrame(results)
result_df.reset_index(inplace=True)
result_df = result_df.rename(columns={'index': 'rownum'})
result_df['rownum'] = result_df['rownum'] + 1
result_df['query'] = query_string
concat_df = pd.concat([result_df,concat_df], axis=0)
time.sleep(MINUTE_INTERVAL)
concat_df['domain'] = concat_df['url'].str.extract('://([^/]+).*', expand=True)
#今日の日付でCSV保存
now = datetime.datetime.today()
date = str(now.strftime("%y%m%d"))
concat_df.to_csv("keyword_rank_list_"+ date +".csv", encoding="utf-8")
◆アウトプットイメージ
【3】補足
◆コード補足
●find_element_by_nameが使えない
昔はfind_element_by_xxxでできたが現在そのコードのままだと
'WebDriver' object has no attribute 'find_element_by_name'というエラーが表示される。
driver.find_element_by_name('q').send_keys(query_string) #今まで
driver.find_element(By.NAME,'q').send_keys(query_string) #今回
●chromedriverの更新が必要
通常だと更新が必要だが、ChromeDriverManagerのモジュールを使用することで更新不要になる。
driver = webdriver.Chrome() #更新必要 driver = webdriver.Chrome(ChromeDriverManager().install()) #更新不要