Pythonを使ってYahooニュースをスクレイピングしLINEに定時配信してニュースを見る習慣を作ろっと

## 背景
スクレイピングを行い、身の回りの生活を少しでも変化させてみようと思ってしまいました。
コミュニケーションツールとしてLINEを使うので、毎日朝に通知でニュースが来る環境を構築すると嫌でも日々のニュースに目を通すことになるので、一例として実装することにしました。

## 環境

PC: Macbook Pro
OS: Linux
言語: python

## ゴール
Pythonを使ってYahooニュースをスクレイピングしてタイトル、日付、ニュースURLをLINEで毎朝９時に定時配信する。

## 流れ
1. LINE Notifyを使ってLINEとPythonを繋げる 
2. PythonでYahooニュースを取得する
3. 出力結果をLINEにて出力
4. Crontab(Linuxのみ)を使って、毎朝9時にその日のニュースをLINEで配信するための定時実行環境を構築

### 1. LINE Notifyを使ってLINEとPythonを繋げる 

https://notify-bot.line.me/ja/

上記のURLからご自身のLINEアカウント等を使ってログインを行い、【トークンを発行する】にてトークンを発行してください。
５分くらいあれば、登録は完了すると思います。

登録したら「マイページ」→「トークンを発行する」でトークン発行
*トークンはAPIを叩く際に使用するので保管しておいてください

![スクリーンショット 2023-12-19 21.35.01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/586805/b43eb5f9-619d-2ecc-8a1e-9bdd4dbe6f8c.png)


### 2. PythonでYahooニュースを取得する

1.Python拡張子(.py)のファイルを作成

```py
# -*- coding: utf-8 -*-
```
Macの方はエンコードを指定しておく事をお勧めしておきます。稀にエラーやアラートを吐かれます。

2.使用するライブラリ 
```py
import requests
from bs4 import BeautifulSoup
import datetime
```
今回使うモジュール・ライブラリはrequests, BeautifulSoup4, datetimeの３つです。

requests...Webサイトの情報取得や画像の収集などを簡単に行うことが可能
BeautifulSoup4...HTMLからデータを抽出するために使用
datetime...今回は日付等を取得する際に使用

3.Yahooニュース情報をrequests, BeautifulSoupを使って取得。 
```py
    html = requests.get('https://news.yahoo.co.jp')
    soup = BeautifulSoup(html.content, "html.parser")
```

4.ニュースを通知する際の文言生成
LINE Notifyは制約として一回のメッセージに1,000文字までしか入力できないので区切って送信する。
```py
    d_today = datetime.date.today()
    matome = "↓↓↓ 本日" + str(d_today) + "のニュース↓↓↓" + '\r\n'
    matome2 = "ニュースの続き【" + str(d_today) + "】" + '\r\n'
    matome3 = "ニュースの続き【" + str(d_today) + "】" + '\r\n'
```

5.スクレイピングでニュースのタイトル、URLを取得して、５個ずつ送信する準備（最大１５個）
```py
    # soup.selectの部分でニュースのタイトル、URLを取得
    for i, (title , url)  in enumerate(zip(soup.select(".sc-eKYRIR.llyViG"), soup.select(".sc-fXazdy.UjHkE a"))):
        if i > 15: break

        if i < 5:
            matome += '{} ({})'.format(title.getText(), url.get('href')) + '\r\n'
        elif i < 10:
            matome2 += '{} ({})'.format(title.getText(), url.get('href')) + '\r\n'
        else:
            matome3 += '{} ({})'.format(title.getText(), url.get('href')) + '\r\n'
```

```py
    matome4 = 'その他のニュースもチェック！' + '\r\n'
    matome4 += '【Google news】'+ '(https://news.google.com/topstories?gl=JP&hl=ja&ceid=JP:ja)' + '\r\n'
    matome4 += '【Yahoo news】' + '(https://news.yahoo.co.jp)' + '\r\n'
    matome4 += '【SmartNews】' + '(https://www.smartnews.com/ja)' + '\r\n'
    matome4 += '【goo】' + '(https://news.goo.ne.jp/)' + '\r\n'
    matome4 += '【Bloomberg】' + '(https://www.bloomberg.co.jp/news/overseas)'
```
一応、他のニュース媒体URLも自分のために添えとく☺ 

### 3. 出力結果をLINEに投げる
'YOUR_TOKEN'の所にLINE Notifyで取得したトークンを入力してください。
(ローカルのみで実践する場合は直打ちでもかまいせんし、envファイルで管理してもどちらでもいいと思います。)
```py
    """
    LINEに通知する
    """
    for message in notification_message: # notification_messagesに上記のmatomeの配列が格納されていーる
        line_notify_token = os.environ.get('YOUR_TOKEN') # .envファイルにLINE notify-botのトークンを設定
        line_notify_api = 'https://notify-api.line.me/api/notify'
        headers = {'Authorization': f'Bearer {line_notify_token}'}
        data = {'message': f'message: {message}'}
        requests.post(line_notify_api, headers = headers, data = data)
```

上記の流れでPython側は完了.
```shell
python main.py
```
でLINEにニュースが流れてくれば期待値です。

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/586805/5321cc0a-2cf7-d0ca-6ea7-a2d4ef9849de.png" width="300">

### 4. Crontab(Linuxのみ)を使って、毎朝9時にその日のニュースをLINEで配信するための定時実行環境を構築
定期実行の準備をします
色々方法はあると思いますが、今回は自分のPCで完結させたいため、crontabを使用します

```shell
$ crontab -e

(分)(時)(日)(月)(曜日) 実行するコマンドのパス
```

```vim
LANG=ja_JP.UTF-8
0  9  *  *  * pythonの絶対パス 実行ファイルの絶対パス

ex. 0  9  *  *  * /Library/Frameworks/Python.framework/Versions/3.6/bin/python3 /Users/develop/line_news/main.py
```

上記を保存すればジョブがスケジュールされ、毎朝９時にニュースがLINEにブーブー届き、嫌でもニュースをみてしまう生活が始まるわけです。


## 最後に
今回のこの記事をピンポイントで求めている人は極僅かだと思いますが、一例としてQiitaにしました。
ぜひこの情報社会で様々な情報を身直に置いてみてくだせい
ちなみに私は基本、SmartNewsでニュースをチェックしています。