勉強したことのメモ

Webエンジニア / プログラマが勉強したことのメモ。

GASで「カクヨム」の更新状況をスクレイピングで取得する

  Google Apps Script Google

Google Apps Scriptの勉強として「カクヨム」の指定した小説が更新された際に何らかの方法で通知を送りたい。以前に「小説家になろう」サイトにてAPIを用いて同じようなスクリプトを作成したが、今回はAPIが用意されていない為、スクレイピングを行う必要がある。以下に対応方法のメモ。

 

やりたいこと

スプレッドシートにNコードを入力しておくと定期的に「カクヨム」にリクエストし話数に変更があった場合、LINEやメールでその旨通知させたい。Nコードは「https://kakuyomu.jp/works/xxxxx/」の「xxxxx」部分にあたる。

尚、通知部分に関しては以下過去記事で取り扱ったので、今回は省略する。

GASとGmailを連携させて受信メール検索及びメール送信

GASとLINEを連携させて通知メッセージを送る方法のメモ

スプレッドシートの作成

後で見たときにわかりやすいようA1~D1セルにカラム名を入力しておく。以下のような形。

シート名は「kakuyomu」とする。

 

ライブラリの追加

HTMLのソースコードから特定のデータを抽出する際にParserというライブラリが便利らしい。

スクリプトエディタページの左側にある「ライブラリ」をクリックするとダイアログが表示されるので、「1Mc8BthYthXx6CoIz90-JiSzSafVnT6U3t0z_W3hLTAX5ek4w0G_EIrNw」にて検索し、Parserライブラリを追加する。

 

スクリプトの作成

//カクヨム
function getKakuyomu(){

	//スプレッドシートの読み込み
	const sheet = SpreadsheetApp.getActiveSpreadsheet();

	//シートを指定
	const kakuyomuSheet = sheet.getSheetByName('kakuyomu');

	//シートのデータ取得
	const kakuyomuSheetVal = kakuyomuSheet.getDataRange().getValues();

	//結果用配列
	let resultVal = kakuyomuSheetVal;

	//戻り値用変数
	let returnMessage = '';

	//ループ処理
	for( let i = 1; i < kakuyomuSheetVal.length; i++ ){

		//パース用オブジェクト
		const parseData = new Object();

		//通知用フラグ
		let notifyFlg = false;

		//行からデータ取得
		const row = kakuyomuSheetVal[i];
		const ncode = row[0];
		const cnt = row[1];
		const novelUpdate = row[2];
		const sheetUpdate = row[3];

		//URL指定
		const novelUrl = 'https://kakuyomu.jp/works/' + ncode;

		//HTMLデータ取得する
		const html = UrlFetchApp.fetch(novelUrl).getContentText('UTF-8');

		//小説の更新日時
		parseData['novelUpdate'] = Parser.data(html).from('<p class="widget-toc-date"><time datetime="').to('Z"><span>').iterate();
		parseData['novelUpdate'] = parseData['novelUpdate'][0].replace('T', ' ');

		//全掲載部分数
		parseData['general_all_no'] = Parser.data(html).from('<span class="js-vertical-composition-item">全').to('話</span>').iterate();
		parseData['general_all_no'] = parseData['general_all_no'][0];

		//小説の更新日時が変更されている場合
		if( !novelUpdate || novelUpdate < parseData['novelUpdate'] ){
			resultVal[i][2] = parseData['novelUpdate'];
		}

		//全掲載部分数が変更されている場合
		if( !cnt || cnt < parseData['general_all_no'] ){
			resultVal[i][1] = parseData['general_all_no'];
			notifyFlg = true;
		}

		//チェック日時
		const now = new Date();
		const date = Utilities.formatDate(now, 'Asia/Tokyo', 'yyyy-MM-dd HH:mm:ss');
		resultVal[i][3] = date;

		//全掲載部分数が変更されている場合
		if( notifyFlg ){
			returnMessage += "カクヨム更新通知\nhttps://kakuyomu.jp/works/" + ncode + "\n\n";
		}

	}

	//シートにまとめて書き込み
	kakuyomuSheet.getRange(1, 1, kakuyomuSheetVal.length,kakuyomuSheetVal[0].length).setValues(resultVal);

	return returnMessage;
}

 

参考サイト

https://auto-worker.com/blog/?p=2460

 - Google Apps Script Google

  関連記事

GASでNintendo Storeをチェックし指定したソフトが〇円以下の際に通知する方法

Google Apps Scriptを利用してNintendo Storeをスク ...

GASを使ってみて感じたメリットとデメリット

Google Apps Scriptを色々勉強した中で感じたメリットとデメリット ...

GASで特定サイトにログインした後にスクレイピングを行う方法

Google Apps Scriptの勉強として特定サイトにログインし、その後に ...

GASとAdSense Management APIを使って前日分の売り上げをメール通知する方法

Googleアドセンスの売り上げをチェックする際、いつもはアドセンスの管理画面に ...

GASでGoogleカレンダーと連携してイベントの取得・追加・削除

Google Apps Scriptの勉強としてGoogleカレンダーと連携させ ...