はじめに
こんにちは!24卒の新米社内SEです。大手ECサイトの保守・運用をメインの会社で社内SEとして勤務しています。最近はbrSEとして中規模ECサイトの案件で中国側とやり取りする業務も担当しています。そんな私ですが、仕事の合間や帰宅後の時間を使って、ちょっとしたサービスを作ってみました。
サービス概要
「漫画発売日検索サービス」
URL: https://manga-service.web.app/
漫画の最新刊がいつ発売されるのか、いちいち調べるのがめんどくさい!そんな「めんどくさい」を解決するために作りました。
技術スタック
フロントエンド: React
バックエンド: Firebase (Firestore)
データ収集: Python (Selenium for web scraping)
ホスティング: Firebase Hosting
データフロー
1.PythonスクリプトでSeleniumを使用し、週刊少年ジャンプの公式サイトから最新の漫画情報をスクレイピング(集英社は個人運営であれば問題ないみたいです)
2.Seleniumを使用することで、動的に生成されるコンテンツも取得可能
3.ヘッドレスモードで実行し、バックグラウンドでデータ収集を行う
4.収集したデータをFirestoreに保存
5.ReactアプリがFirestoreからデータを取得して表示
6.ユーザーが検索すると、Firestoreでクエリを実行
7.検索結果を表示し、各漫画タイトルにAmazonの検索リンクを付与
苦労したポイント
- Seleniumを使ったスクレイピング
動的に生成されるコンテンツを取得するために、Seleniumを使用しました。以下は簡略化したコードの一部です:
pythonCopyfrom selenium import webdriver
from selenium.webdriver.chrome.service import Service
from selenium.webdriver.common.by import By
from webdriver_manager.chrome import ChromeDriverManager
# Seleniumの設定
options = webdriver.ChromeOptions()
options.add_argument('--headless')
driver = webdriver.Chrome(service=Service(ChromeDriverManager().install()), options=options)
# スクレイピングするURL
url = "https://www.shueisha.co.jp/books/newreleases/?gid=5"
driver.get(url)
# 必要な情報を抽出
comics = driver.find_elements(By.CLASS_NAME, 'book-item')
for comic in comics:
title = comic.find_element(By.CLASS_NAME, 'book-title').text
author = comic.find_element(By.CLASS_NAME, 'book-author').text
release_date = comic.find_element(By.CLASS_NAME, 'book-release-date').text
# ここでFirestoreにデータを保存する処理を行う
driver.quit()
2.Amazonリンクの生成
漫画のタイトルを使ってAmazonの検索リンクを生成するのが意外と難しかったです。最初は「めんどくさい」の精神に反して頑張りすぎてしまい、Amazon Product Advertising APIとにらめっこしていました。結局、シンプルに検索URLを生成する方法に落ち着きました。
javascriptCopyconst generateAmazonLink = (title) => {
const encodedTitle = encodeURIComponent(title);
return `https://www.amazon.co.jp/s?k=${encodedTitle}&tag=myassociateid-22`;
};
3.データベースの肥大化対策
「めんどくさい」のは使う側だけでなく、管理する側も同じ。データベースが肥大化するのを防ぐため、6ヶ月以上前に登録された漫画のデータを自動で削除するPythonスクリプトも作成しました。
pythonCopyimport firebase_admin
from firebase_admin import credentials, firestore
from datetime import datetime, timedelta
# Firebaseの初期化
cred = credentials.Certificate("path/to/serviceAccount.json")
firebase_admin.initialize_app(cred)
db = firestore.client()
# 6ヶ月前の日付を計算
six_months_ago = datetime.now() - timedelta(days=180)
# 古いデータを削除
comics_ref = db.collection('comics')
old_comics = comics_ref.where('release_date', '<', six_months_ago).get()
for comic in old_comics:
comic.reference.delete()
print(f"{len(old_comics)} comics deleted.")
まとめ
このサービスを通じて、フロントエンドからバックエンド、データ収集まで一通りの流れを経験できました。また、Amazonのアフィリエイトリンクも設置してみました(買ってくれたら紹介料入るんですかね?わからないけど)。
「めんどくさい」を解決するサービスを作るのは、意外と「めんどくさい」作業の連続でした。でも、自分で使ってみると「あ、これ便利かも」と思えるものができて満足しています。
追記
今までは集英社のみ対応していましたが
講談社も対応できるようにしました(結構てこずりました)
試し読みがある漫画にはそちらのリンクも追加しました