Oisix ra daichi Creator's Blog(オイシックス・ラ・大地クリエイターズブログ)

オイシックス・ラ・大地株式会社のエンジニア・デザイナーが執筆している公式ブログです。

Pythonでslackにデータベースのデータを通知する

こんにちは!Oisix ra daichiの平島です。

この業界に入ってから勉強の毎日で、まだまだ分からないことだらけですが、

業務効率化のために日々挑戦しています。

 

slack×pythonは 日々の業務の中で、データの件数に異常がないか確認するために利用しています。

今回はその実装方法を紹介します。

※個別のモジュールのインストールについては割愛しています。

slackのwebhook_urlを取得する

参考: api.slack.com ※Qiita等にわかりやすい記事があるので参考にしてください。

一番簡単なメッセージを投稿してみる

import requests
import json

incoming_webhook_url = "***"

payload = json.dumps({
    'text': "私はトマトです",
    'channel': "@user_name",
    'username': "tomato",
    'icon_emoji': ":tomato:"
})
requests.post(incoming_webhook_url, data=payload)

このpythonファイルを実行すると、下記のようにメッセージが来ます。

f:id:oitech:20181213093541p:plain

データベースに接続する

cx_Oracleを使います。 参考:

cx_Oracle - Python Interface for Oracle Database

 

ユーザ名、パスワード、ホスト名、ポート番号、サービス名を入力しDBに接続する。

import cx_Oracle

user = ""
password = ""
hostname = ""
port = ""
service_name = ""

conn = cx_Oracle.connect(user, password, hostname + ':' + port + '/' + service_name, encoding="UTF-8", nencoding="UTF-8")
cur = conn.cursor()

データベースからデータを取得する

今回は下記のようなテスト用テーブルを作成しました。

ID FRUIT PRICE
1 りんご 200
2 ぶどう 300
3 みかん 100

データを検索する。この際にpandasを使ってみようと思います。

pandasはDataFrameという強力なクラスを持っています。

RDBのようにデータを取り扱うことが可能で、並列計算ができるので処理も高速です。

import pandas as pd
sql = "SELECT ID, FRUIT, PRICE FROM FRUIT_PRICE"
cur.execute(sql)
fruit_price_df = pd.DataFrame(cur.fetchall())

結果は以下のように返ってきます。これが今fruit_price_df に入ってい

0 1 2
0 1 りんご 200
1 2 ぶどう 300
2 3 みかん 100

列名が入っておらず扱いづらいため、列名を付与します。

fruit_price_df .columns = ["ID", "FRUIT", "PRICE"]
ID FRUIT PRICE
0 1 りんご 200
1 2 ぶどう 300
2 3 みかん 100

slackに通知します

基本のテキストを用意します。{}には文字列を代入できます。

message_base = "{}の価格は{}円です。"

これをmessageにします。

message = ""
for i in range(len(fruit_price_df.index)):
    message += "{}の価格は{}円です。\n".format(fruit_price_df["FRUIT"][i] , fruit_price_df["PRICE"][i])

#for index, rows in fruit_price_df.iterrows():  こういう書き方もできます。本当はこちらの書き方が良いです。
#    message += "{}の価格は{}円です。\n".format(rows[1], rows[2])

これでmessageが完成したので、後は最初に用意した「私はトマトです」をmessageに置き換えるだけです。 一貫するとこうなります。

import requests
import json
import pandas as pd

incoming_webhook_url = "***"

import cx_Oracle

user = ""
password = ""
hostname = ""
port = ''
service_name = ""

conn = cx_Oracle.connect(user, password, hostname + ':' + port + '/' + service_name, encoding="UTF-8", nencoding="UTF-8")
cur = conn.cursor()

sql = "SELECT ID, FRUIT, PRICE FROM FRUIT_PRICE"
cur.execute(sql)
fruit_price_df = pd.DataFrame(cur.fetchall())
fruit_price_df.columns = ["ID", "FRUIT", "PRICE"]

message = ""
for i in range(len(fruit_price_df.index)):
    message += "{}の価格は{}円です。\n".format(fruit_price_df["FRUIT"][i] , fruit_price_df["PRICE"][i])

#for index, rows in fruit_price_df.iterrows():
#    message += "{}の価格は{}円です。\n".format(rows[1], rows[2])

payload = json.dumps({
    'text': message,
    'channel': "@user_name",
    'username': "tomato",
    'icon_emoji': ":tomato:"
})
requests.post(incoming_webhook_url, data=payload)

f:id:oitech:20181213100012p:plain

弊社ではこのpythonファイルをcronではなくdigdagで実行しています。

digdagについての詳しい話はそのうち公開されますので、楽しみにしていてください。

おまけ

webhook urlだけでも、いろいろな表現ができます。

この時の

requests.post(incoming_webhook_url, data=payload)

payloadの中身を下記に記載しておきます。

{'attachments': [{'actions': [{'name': 'ボタンの名前です(表示はされない',
                               'style': 'primary',
                               'text': 'OISIX\u3000HP',
                               'type': 'button',
                               'url': 'ボタンのリンク'}],
                  'author_icon': 'アイコンの画像',
                  'author_link': 'アイコンの横の文字のリンク',
                  'author_name': 'oisix',
                  'color': 'good',
                  'fields': [{'short': True,
                              'title': '記事1',
                              'value': '<'埋め込みリンク'|あめトマト>'},
                             {'short': True,
                              'title': '記事2',
                              'value': '<'埋め込みリンク'|みつトマト>'}],
                  'footer': 'tomatoでした',
                  'footer_icon': 'フッターの画像(「tomatoでした」の左)のリンク',
                  'pretext': 'oisixの記事について、まとめました。',
                  'text': 'トマトを食べよう!',
                  'thumb_url': 'サムネイルのリンク(ミニトマト)',
                  'title': 'トマトのページ',
                  'title_link': 'タイトルのリンク',
                  'ts': 1544595510}],
 'channel': '@user_name',
 'icon_emoji': ':tomato:',
 'link_names': 1,
 'text': '私はトマトです<!here>',
 'username': 'tomato'}

 

現在はbotを製作中です。また機会があれば書きたいと思います。

 

アドベントカレンダーにて、他のメンバーもブログを書いています!

ぜひご覧下さい!

adventar.org

Oisix ra daichi Creator's Blogはオイシックス・ラ・大地株式会社のエンジニア・デザイナーが執筆している公式ブログです。

オイシックス・ラ・大地株式会社では一緒に働く仲間を募集しています