2時間でQiitaとはてブのトレンドをLINEに通知するプログラムを書いてAWSにデプロイした話
はじめに
出社して、いつものトレンドチェックの日課をしていると、
以下の記事が目に留まりました。
GitHubActionsでQiitaとSlackを繋いで、エンジニアにとっての良い習慣をつくる。
そういえば自分以外のエンジニアがトレンドチェックしているの見かけたことないぞ🤔
というわけで、毎日チェックしてもらいたい Qiita トレンド と はてなブックマークIT トレンド を毎朝LINEに通知するシステムを作りました。
LINEアカウントを追加した人に、こんな感じの通知が届きます
LINE DeveloperでMessaging APIの作成
まず、息を吸うように新規のMessaging APIを作成します。
名前やアイコンは適当でいいです。
プログラミング開始
では、組んで行きましょう。
環境構築
PHPが得意なので、Laravelプロジェクトを作成します。
$ laravel new line-it-trend-news
LINE BotをPHPで扱うためのSDKをインストールします。
$ composer require linecorp/line-bot-sdk
スクレイピングしたいので、DomCrawlerをインストールします。
$ composer require symfony/dom-crawler
AWSのLambdaにデプロイしたいので、bref をインストールします。
$ composer require bref/bref bref/laravel-bridge
$ php artisan vendor:publish --tag=serverless-config
はい、これで環境は整いました。
プログラミング
LINE Message APIで実行させるための設定ファイルを作成します
<?php
return [
'channel_access_token' => getenv('LINE_CHANNEL_ACCESS_TOKEN', null),
'channel_secret' => getenv('LINE_CHANNEL_SECRET', null),
];
LINE_CHANNEL_ACCESS_TOKEN=<Messaging APIのチャネルアクセストークンを記述>
LINE_CHANNEL_SECRET=<Messaging APIのチャネルシークレットを記述>
クーロンで実行したいので、コマンドを作成します。
$ php artisan make:command SendLineMessageCommand
中身はこんな感じ
正直、突貫で作ってるのでアンリーダブルです。
<?php
namespace App\Console\Commands;
use Illuminate\Console\Command;
use LINE\LINEBot\HTTPClient\CurlHTTPClient;
use LINE\LINEBot;
use LINE\LINEBot\MessageBuilder\TextMessageBuilder;
use Symfony\Component\DomCrawler\Crawler;
class SendLineMessageCommand extends Command
{
/**
* The name and signature of the console command.
*
* @var string
*/
protected $signature = 'cron:send_line_message';
/**
* The console command description.
*
* @var string
*/
protected $description = 'Command description';
/**
* Create a new command instance.
*
* @return void
*/
public function __construct()
{
parent::__construct();
}
/**
* Execute the console command.
*
* @return int
*/
public function handle()
{
$message = sprintf(
"【Qiitaのトレンド】\n%s\n\n【はてなのトレンド】\n%s",
$this->createQiitaTrendMessage(),
$this->createHatenaTrendMessage()
);
$httpClient = new CurlHTTPClient(config('linebot.channel_access_token'));
$bot = new LINEBot($httpClient, ['channelSecret' => config('linebot.channel_secret')]);
$textMessageBuilder = new TextMessageBuilder($message);
$bot->broadcast($textMessageBuilder);
return 0;
}
private function createQiitaTrendMessage() {
$response = \Http::get('https://qiita.com');
$crawler = new Crawler($response->getBody()->getContents());
$node = $crawler->filter('div[data-hyperapp-app="Trend"]')->eq(0);
$value = $node->attr('data-hyperapp-props');
$message = collect(json_decode($value, true))
->dotc('trend.edges', [])
->slice(0, 5)
->map(function($row) {
$data = collect($row);
$subject = $data->dot('node.title');
$uuid = $data->dot('node.uuid');
$userName = $data->dot('node.author.userName');
$url = sprintf('https://qiita.com/%s/items/%s', $userName, $uuid);
return sprintf('▼ %s%s%s', $subject, "\n", $url);
})
->join("\n\n");
return $message;
}
private function createHatenaTrendMessage() {
$response = \Http::get('https://b.hatena.ne.jp/hotentry/it');
$crawler = new Crawler($response->getBody()->getContents());
$list = collect([]);
$crawler->filter('.entrylist-contents div.entrylist-contents-main')->each(function($node) use($list) {
$title = $node->filter('h3 a')->eq(0)->attr('title') ?? null;
$url = $node->filter('h3 a')->eq(0)->attr('href') ?? null;
$list->push([$title, $url]);
});
return $list->slice(0, 5)->map(function($data) {
list($title, $url) = $data;
return sprintf('▼ %s%s%s', $title, "\n", $url);
})
->join("\n\n");
}
}
app/Console/Kernel.php
に追加して指定した時間に実行されるようにします
protected function schedule(Schedule $schedule)
{
$schedule->command('cron:send_line_message')->dailyAt('10:00');
}
serverless.yml
に app/Console/Kernel.php
を実行するコマンドを追加
events
を追加することによって、毎分 Cloudwatchが schedule:run
コマンドを叩いてくれます。
artisan:
handler: artisan
timeout: 120
layers:
- ${bref:layer.php-74}
- ${bref:layer.console}
# ここを追加
events:
- schedule:
rate: rate(1 minute)
input:
cli: schedule:run
デプロイ
ワンコマンドでデプロイできます。
プロファイラや環境などはよしなに
$ serverless deploy
ソース
こちらにそのまま公開しています。
記事書いたときと変わる可能性があります。
https://github.com/YuK1Game/line-it-trend-news
さいごに
・URLは短縮して短くしたい
・カルーセルテンプレート使って表示したい
など諸々やりたいことはありますが、
即席にしてはなかなかいい感じになったんではないでしょうか。
あとはこれを社内のエンジニアに共有しなくては…
Author And Source
この問題について(2時間でQiitaとはてブのトレンドをLINEに通知するプログラムを書いてAWSにデプロイした話), 我々は、より多くの情報をここで見つけました https://qiita.com/YuK1Game/items/c8e8c79396b6feae5dd5著者帰属:元の著者の情報は、元のURLに含まれています。著作権は原作者に属する。
Content is automatically searched and collected through network algorithms . If there is a violation . Please contact us . We will adjust (correct author information ,or delete content ) as soon as possible .