今回はこんな声に対応するガジェットです。
「ラインなら外出先でもすぐに使用できるし、いつも見ているので、ラインで家計簿を管理でき、残高もラインですぐに確認できるようになったらいいな。」
ライン家計簿どこでも簡単入力、簡単残高チェック
買い物をした際には、すぐにラインから使った金額や項目を家計簿データベースに入力でき、あとどのくらい使えるお金があるのかもラインですぐに確認できるガジェットです。
このガジェットでできることはこちら
- ライン上で使用したお金を入力、残高も一覧で確認できます。
- データはスプレッドシートで管理します。
- 会話形式ですので楽ちん。
注意点はこちら
- 今回は使用したお金の入力でテキストを使っており、決まったフォーマットでの入力にしています。そのため、フォーマットに合わないと入力できないので、今後改良が必要です。
評価(自己)
役立ち度 ★★★★(良し)
効率化 ★★★★(良し)
ミス防止 ★★(悪い)
楽しさ ★★★★(良し)
操作性 ★★(悪い)
※上の注意点にも書きましたが入力が決まったフォーマットに従わないといけないことと、選択形式にしていないので操作性は悪いです。また、なので打ち間違いが出る可能性があるのでミス防止も悪いにしています。(要改良)
実行環境
使用環境 GCP、Heroku、line messaging api
使用言語 python
使用ライブラリ flask、inebot、os、json、pandas、datetime、gspread、
oauth2client
今回のコード
from flask import Flask, request, abort
from linebot import (
LineBotApi, WebhookHandler
)
from linebot.exceptions import (
InvalidSignatureError
)
from linebot.models import (
MessageEvent, TextMessage, TextSendMessage,
)
import os
import json
import pandas as pd
from datetime import datetime
import gspread
from oauth2client.service_account import ServiceAccountCredentials
def auth():
SP_CREDENTIAL_FILE = 'secret.json'
SP_SCOPE = [
'https://spreadsheets.google.com/feeds',
'https://www.googleapis.com/auth/drive'
]
SP_SHEET_KEY = 'スプレッドシートのID'
SP_SHEET1 = 'accountbook'
SP_SHEET2 = 'this-month'
SP_SHEET3 = 'balance'
credentials = ServiceAccountCredentials.from_json_keyfile_name(SP_CREDENTIAL_FILE, SP_SCOPE)
gc = gspread.authorize(credentials)
sh = gc.open_by_key(SP_SHEET_KEY)
worksheet1 = sh.worksheet(SP_SHEET1)
worksheet2 = sh.worksheet(SP_SHEET2)
worksheet3= sh.worksheet(SP_SHEET3)
return worksheet1, worksheet2, worksheet3
def input_accountbook(contents):
worksheet1 = auth()[0]
data = worksheet1.get_all_values()
df = pd.DataFrame(data[1:])
df.columns = data[0]
timestamp = datetime.now()
date = timestamp.strftime('%m/%d')
df['支出金額'] = df['支出金額'].astype(int)
item = contents.split('/')[1]
money = int(contents.split('/')[2])
df = df.append({'日付': date, '支出品目': item, '支出金額': money}, ignore_index=True)
worksheet1.update([df.columns.values.tolist()] + df.values.tolist())
def input_balance(contents):
worksheet3 = auth()[2]
worksheet3.cell(2, 1).value
balance = int(contents.split('/')[1])
worksheet3.update_cell(2, 1, balance)
def output():
worksheet2 = auth()[1]
data2 = worksheet2.get_all_values()
df2 = pd.DataFrame(data2[1:])
df2.columns = data2[0]
df2 = df2.iloc[[32, 35, 37, 38, 39, 40, 41, 42, 43], :2]
food = df2['金額'].values[1]
free = df2['金額'].values[2]
clothes = df2['金額'].values[3]
rice= df2['金額'].values[4]
education = df2['金額'].values[5]
tobaco = df2['金額'].values[6]
cash = df2['金額'].values[7]
next_month = df2['金額'].values[8]
text = f'現金残は、{cash}円です。\n食費残は、{food}、\n被服費残は{clothes}円、\n教育費残は{education}円、\nタバコ代残は{tobaco}円、\n自由に使える金額は{free}円です。\n繰り越しは{next_month}円です'
return text
app = Flask(__name__)
line_bot_api = LineBotApi('Messaging api のChannel access token')
handler = WebhookHandler('Messaging apiのChannel secret')
@app.route("/callback", methods=['POST'])
def callback():
signature = request.headers['X-Line-Signature']
body = request.get_data(as_text=True)
app.logger.info("Request body: " + body)
try:
handler.handle(body, signature)
except InvalidSignatureError:
print("Invalid signature. Please check your channel access token/channel secret.")
abort(400)
return 'OK'
@handler.add(MessageEvent, message=TextMessage)
def handle_message(event):
if event.message.text[:2] == '入力':
input_accountbook(event.message.text)
line_bot_api.reply_message(
event.reply_token,
TextSendMessage(text='入力完了しました'))
elif event.message.text[:2] == '現金':
input_balance(event.message.text)
line_bot_api.reply_message(
event.reply_token,
TextSendMessage(text='入力完了しました'))
elif event.message.text[:2] == '残高':
line_bot_api.reply_message(
event.reply_token,
TextSendMessage(text=output()))
else:
line_bot_api.reply_message(
event.reply_token,
TextSendMessage(text='コメントは「入力/項目/金額」、「現金/金額」、また、「残高」のように入力してください'))
if __name__ == "__main__":
port = os.getenv("PORT")
app.run(host="0.0.0.0", port=port)