-
Debugクラスのprint_log(), trace_write(), trace_warn(), trace_error(), sound_alert()メソッドを使ってみる
ここで解説するDebugクラスの各種メソッドは仮想通貨の取引の履歴をログとして保存するために使用します。
Debugクラスのメソッドは「print系」と「trace系」に分類されています。
print系の「print_log()」はGvarクラスのdebug_modeプロパティの値(True/False)にかかわらず常に表示されます。
しかし、trace系の「trace_write(), trace_warn(), trace_error()」は「debug_mode=True」のときのみ表示されます。
つまり、BOTをデバッグ中のときは「debug_mode=True」で実行させてデバッグ情報を表示させます。
そして本番で実行させるときは「debug_mode=False」にして「print_log()」のデータのみ表示させます。
trace系のコードはPythonのプログラムから削除する必要はありません。
どちらのメソッドを使用してもデータは画面とログファイル双方に出力されます。
Visual Studio Code (VS Code)を起動したら新規ファイルを作成して行1-70を入力(コピペ)します。
行2-27ではPythonのライブラリを取り込んでいます。
行28ではPythonの警告メッセージを抑止しています。
行42ではGvarクラスのインスタンスを生成しています。
行43-46ではGvarクラスのプロパティ(属性)を設定しています。
ちなみにGvarとは「Global Variables」の略称です。
行52ではDebugクラスのインスタンスを生成しています。
行54ではGvarクラスのdebug_modeプロパティに「True」を設定しています。
行56-59ではDebugクラスの各種メソッドを使用してメッセージを表示しています。
Debugクラスのメソッドを使用したときはメッセージが画面とログファイルに出力されます。
print_log()とtrace_write()は白色、trace_warn()は黄色、trace_error()は赤色で表示されます。
行63ではGvarクラスのdebug_modeプロパティに「False」を設定しています。
行65-68ではDebugクラスのprint系とtrace系のメソッドでメッセージを出力していますが、
「debug_mode=False」なのでprint系のメッセージのみ表示されます。
行60, 69ではDebugクラスのsound_alert()メソッドで警告音を鳴らしています。
このメソッドの引数には警告音の回数を指定します。
sound_alert()はBOTで深刻なエラーが発生したときや、
注文が約定したときなどに鳴らすといった使い方ができます。
demo1.py:
### Import the libraries
import os
import os.path
import time
from time import sleep
import datetime as dt
from datetime import timedelta
import numpy as np
import pandas as pd
import pandas_ta as pa
import matplotlib.pyplot as plt
from lib.base import Bcolors, Gvar, Coin, Gmo_dataframe
from lib.debug import Debug # dependencies Gvar
from lib.gmail import Gmail # dependencies Gvar, Debug, GmailConfig
from lib.gmail_config import GmailConfig
from lib.api import Api # dependencies Gvar, Coin
from lib.csv import Csv # dependencies Gvar, Coin
from lib.trade import Trade # dependencies Gvar, Coin
from lib.buy_sell import BuySell # dependencies Gvar, Coin
from lib.sell_buy import SellBuy # dependencies Gvar, Coin
import argparse
import warnings
warnings.simplefilter('ignore')
################################################################################################################
### MAIN : Demo [1] Debug class: print_log(), trace_write(), trace_warn(), trace_error(), sound_alert()
################################################################################################################
#############################################################
# instantiate gvar/debug classes and initialize properties
#############################################################
### define constants
FOLDER_NAME = 'bot'
### initiate Gvar class
gvar = Gvar()
gvar.exchange = FOLDER_NAME # bot
gvar.domain = os.environ['USERDOMAIN'].lower() # 'desktop-pc' or 'note-pc'
gvar.folder_gmo = f'{gvar.domain}/{gvar.exchange}/' # 'desktop-pc/bot/'
gvar.callers_method_name = '_main_:'
######################################################################################
# Debug class: print_log(), trace_write(), trace_warn(), trace_error(), sound_alert()
######################################################################################
gvar.callers_method_name = 'Demo1():'
debug = Debug(gvar)
debug.print_log(f'{Bcolors.OKGREEN}Demo1 Started{Bcolors.ENDC}')
gvar.debug_mode = True
debug.print_log(f'.... {Bcolors.HEADER}{gvar.debug_mode=}{Bcolors.ENDC}')
debug.print_log('.... Debug: print_log(1)...')
debug.trace_write('.... Debug: trace_write(1)...')
debug.trace_warn('.... Debug: trace_warn(1)...')
debug.trace_error('.... Debug: trace_error(1)...')
debug.sound_alert(1)
debug.print_log('.... ' + '.'*50)
gvar.debug_mode = False
debug.print_log(f'.... {Bcolors.HEADER}{gvar.debug_mode=}{Bcolors.ENDC}')
debug.print_log('.... Debug: print_log(2)...')
debug.trace_write('.... Debug: trace_write(2)...')
debug.trace_warn('.... Debug: trace_warn(2)...')
debug.trace_error('.... Debug: trace_error(2)...')
debug.sound_alert(2)
debug.print_log(f'{Bcolors.OKGREEN}Demo1 Ended{Bcolors.ENDC}')
図1-1は実行結果です。
Gvarのdebug_modeが「False」のときは、trace_write(), trace_warn(), trace_error()のメッセージが表示されません。
図1-2はログファイルの内容です。
画面と同様、debug_modeが「False」のときはtrace系のメソッドはメッセージがファイルに出力されません。
ちなみになぜ画面だけでなくファイルにも出力するかと言えば、VS Codeにはすべてのメッセージが表示されないバグがあるからです。
また、画面だと後で見たいときにその都度コピペしてファイルに保存しておく必要があります。
このような不都合を回避するためにメッセージをログとしてファイルにも出力しています。
-
Gmailクラスのsend_gmail_order()メソッドを使用して「買い注文」「売り注文」をGmailに送信してみる
ここではGoogleのGmailにメールを送信するGmailクラスの使い方を説明します。
Gmailクラスには通常のメールを送信するsend_gmail()メソッドと、
注文に関連するメールを送信するsend_gmail_order()メソッドの2種類あります。
ここでは「send_gmail_order()」を使って「買い注文」と「売り注文」をGmailに送信します。
Gmailを使用するには、2段階認証を設定してアプリ専用の16桁のパスワードを取得する必要があります。
Gmailの16桁のパスワードを取得する方法については
「記事(Article050)」で詳しく解説しています。
パスワードを取得したらVisual Studio Code (VS Code)を起動して新規ファイル「gmail_config.py」を作成して行1-7を入力します。
行5-7にはご自分のメールアドレスとパスワードを入力してください。
gmail_config.py:
################## GmailConfig class
class GmailConfig:
GMAIL_SERVER = 'smtp.gmail.com' # your smtp server
GMAIL_PORT = 587 # your port number
GMAIL_FROM = '●●●@gmail.com' # your from email id
GMAIL_TO = '●●●@gmail.com' # your to email ids
GMAIL_PASS = '●●●' # your email id's password
新規ファイルを作成したら行1-66を入力(コピペ)します。
行2-27ではPythonのライブラリを取り込んでいます。
行16-19では今回使用するGvar, Debug, Gamail, GmailConfigクラスを取り込んでいます。
行28ではPythonの警告メッセージを抑止しています。
行42-46ではGvarクラスのインスタンスを生成して各種プロパティを設定しています。
行53ではDebugクラスのインスタンスを生成しています。
行60ではGmailクラスのインスタンスを生成しています。
行61, 63ではGmailクラスのsend_gmail_order()メソッドを使用して「買い注文」と「売り注文」のメールを送信しています。
このメソッドの引数1には仮想通貨のシンボル(BTC_JPY)を指定します。
引数2には「BUY」「SELL」のいずれかを指定します。
引数3にはメールの本文を指定します。
行56-57ではメールの本文を定義しています。
demo2.py:
### Import the libraries
import os
import os.path
import time
from time import sleep
import datetime as dt
from datetime import timedelta
import numpy as np
import pandas as pd
import pandas_ta as pa
import matplotlib.pyplot as plt
from lib.base import Bcolors, Gvar, Coin, Gmo_dataframe
from lib.debug import Debug # dependencies Gvar
from lib.gmail import Gmail # dependencies Gvar, Debug, GmailConfig
from lib.gmail_config import GmailConfig
from lib.api import Api # dependencies Gvar, Coin
from lib.csv import Csv # dependencies Gvar, Coin
from lib.trade import Trade # dependencies Gvar, Coin
from lib.buy_sell import BuySell # dependencies Gvar, Coin
from lib.sell_buy import SellBuy # dependencies Gvar, Coin
import argparse
import warnings
warnings.simplefilter('ignore')
############################################################################
### MAIN Demo [2] Gmail class : send_gmail_order()
############################################################################
##########################################################
# instantiate gvar/coin class and initialize properties
##########################################################
### define constants
FOLDER_NAME = 'bot'
### initiate Gvar class
gvar = Gvar()
gvar.exchange = FOLDER_NAME # bot
gvar.domain = os.environ['USERDOMAIN'].lower() # 'desktop-pc' or 'note-pc'
gvar.folder_gmo = f'{gvar.domain}/{gvar.exchange}/' # 'desktop-pc/bot/'
gvar.callers_method_name = '_main_:'
###########################################################
# Gmail class : send_gmail_order()
###########################################################
gvar.callers_method_name = 'Demo2():'
gvar.debug_mode = True
debug = Debug(gvar)
debug.print_log(f'{Bcolors.OKGREEN}Demo2 {gvar.debug_mode=} Started{Bcolors.ENDC}')
buy_order = f"create_buy_order(2022-09-20 01:15:00, BTC_JPY, qty=0.01, price=999999)"
sell_order = f"create_sell_order(2022-09-20 01:20:00, BTC_JPY, qty=0.01, price=999999)"
# send_gmail(symbol: str, side: str, order: str) -> None:
gmail = Gmail(gvar, debug)
gmail.send_gmail_order('BTC_JPY', 'BUY', buy_order)
debug.sound_alert(1)
gmail.send_gmail_order('BTC_JPY', 'SELL', sell_order)
debug.sound_alert(1)
debug.print_log(f'{Bcolors.OKGREEN}Demo2 Ended{Bcolors.ENDC}')
図2-1は実行結果です。
図2-2はGmailの受信画面です。
2件の受信メールの件名が表示されています。
図2-3はメールの本文を開いた画像です。
メールの本文はHTML形式で送信します。
-
Apiクラスのget_crypto_try()メソッドを使ってビットコイン(BTC_JPY)の取引データを取得してみる
ここではBOTの肝となるApiクラスの各種クラスのうち取引データを取得するget_crypto_try()メソッドについて説明します。
get_crypto_try()メソッドはget_crypto()メソッドの親メソッドです。
子メソッドのget_crypto()でタイムアウト等のエラーが発生したときは5回再試行します。
VS Codeを起動したら新規ファイルを作成して行1-81を入力(コピペ)します。
行16ではGvar, Coinのクラスを取り込んでいます。
行17ではDebugのクラスを取り込んでします。
行20ではApiクラスを取り込んでいます。
行39ではBOTが使用するフォルダ名を定義します。
行42ではGvarクラスのインスタンスを生成しています。
行43-46ではGvarの各種プロパティを設定しています。
行56-57ではCoinクラスのインスタンスを生成してsymbolプロパティにビットコインのシンボル「BTC_JPY」を設定しています。
ちなみに現物取引のシンボルは「BTC」、レバレッジ取引のシンボルは「BTC_JPY」となります。
行58ではApiクラスのインスタンスを生成しています。
Apiクラスの引数1にはGvarクラスのオブジェクトを指定します。
引数2にはCoinクラスのオブジェクトを指定します。
ここではビットコイン(レバレッジ取引用)のCoinクラスを指定しています。
行61ではApiクラスのget_crypto_try()メソッドでビットコインの取引データ(決済データ)を取得しています。
このメソッドの引数1にはページ番号を指定します。
引数2にはページ当たりのデータ件数を指定します。
ここでは1ページ当たり100件のデータを取得することを指定しています。
つまり、ビットコインの直近100件の取引データ(レバレッジ取引)を取得しています。
get_crypto_try()メソッドからは、ステータスコード(status)と取引データがPandasのDataFrameに格納されて返されます。
このメソッドではタイムアウトなどのエラーが発生したときは5回再試行します。
行77ではDataFrameの先頭5件のデータを表示しています。
行79ではDataFrameの終端5件のデータを表示しています。
demo3.py:
### Import the libraries
import os
import os.path
import time
from time import sleep
import datetime as dt
from datetime import timedelta
import numpy as np
import pandas as pd
import pandas_ta as pa
import matplotlib.pyplot as plt
from lib.base import Bcolors, Gvar, Coin, Gmo_dataframe
from lib.debug import Debug # dependencies Gvar
from lib.gmail import Gmail # dependencies Gvar, Debug, GmailConfig
from lib.gmail_config import GmailConfig
from lib.api import Api # dependencies Gvar, Coin
from lib.csv import Csv # dependencies Gvar, Coin
from lib.trade import Trade # dependencies Gvar, Coin
from lib.buy_sell import BuySell # dependencies Gvar, Coin
from lib.sell_buy import SellBuy # dependencies Gvar, Coin
import argparse
import warnings
warnings.simplefilter('ignore')
#######################################################################################
### MAIN Demo [3] Api class : get_crypto_try(self, page: int, count: int) -> tuple:
#######################################################################################
###########################################################
# instantiate gvar/coin class and initialize properties
###########################################################
### define constants
FOLDER_NAME = 'bot'
### initiate Gvar class
gvar = Gvar()
gvar.exchange = FOLDER_NAME # bot
gvar.domain = os.environ['USERDOMAIN'].lower() # 'desktop-pc' or 'note-pc'
gvar.folder_gmo = f'{gvar.domain}/{gvar.exchange}/' # 'desktop-pc/bot/'
gvar.callers_method_name = '_main_:'
######################################################################
# Api class : get_crypto_try(self, page: int, count: int) -> tuple:
######################################################################
gvar.callers_method_name = 'Demo3():'
gvar.debug_mode = True
debug = Debug(gvar)
debug.print_log(f'{Bcolors.OKGREEN}Demo3 ({gvar.debug_mode=}) Started{Bcolors.ENDC}')
coin = Coin()
coin.symbol = 'BTC_JPY'
api = Api(gvar, coin)
# get_crypto_try(page: int, count: int) -> tuple: return (status, df)
status, df = api.get_crypto_try(page=1, count=100) # get crypto (BTC_JPY)
df = pd.DataFrame(df) # cast(df)
debug.print_log(f".... {gvar.callers_method_name} get_crypto_try(page=1, count=100) ▶ {status=}, {df.shape=} ")
# error ?
if status != 0:
debug.trace_error(f"get_crypto_try(page=1, count=5) ▶ {status=}, quit python... ")
quit()
# empty dataframe ?
if df.shape[0] == 0:
debug.trace_error(f"get_crypto_try(page=1, count=5) ▶ dataframe is empty: {df.shape[0]=}, quit python... ")
quit()
# no errors & no empty dataframe
print('-'*60)
print(df.head(5))
print('-'*60)
print(df.tail(5))
debug.print_log(f'{Bcolors.OKGREEN}Demo3 Ended{Bcolors.ENDC}')
図3は実行結果です。
GMO Coinからビットコインの取引データ(決済データ)が100件返されています。
決済データには価格、売買区分(BUY/SELL)、数量、タイムスタンプ(UTC)が格納されています。
BOTはこれらの決済データを元に自動取引します。
-
Csvクラスのwrite_buy_order(), get_buy_order(), update_buy_order()メソッドを使って注文ファイルを作成してみる
ここで紹介するメソッドは、BOTに標準的に用意されているメソッドを使用するのではなく、
独自の手法で自動トレードを行うときに使います。
ちなみに、BOTには簡単に自動トレードを行うためにbuy_sell()、sell_buy()などのメソッドが用意されています。
これらのメソッドを使えばGMOとの売買取引から取引ごとの損益の計算までをすべて自動化することができます。
ここではCsvクラスの各種メソッドの内、
write_buy_order(), get_buy_order(), update_buy_order()メソッドの使い方について説明します。
行42-46ではGvarクラスのインスタンスを生成して各種プロパティを設定しています。
行53ではDebugクラスのインスタンスを生成しています。
行56-58ではCoin, Api, Csvクラスのインスタンスを生成しています。
ちなみに、Coin()クラスはデフォルトでビットコイン(BTC_JPY)のクラスを生成します。
仮想通貨のシンボルには「BTC_JPY」が設定されるのでレバレッジ用の取引になります。
行61ではApiクラスのget_crypto_try()メソッドでGMOからビットコインの10件の取引データ(レバレッジ取引)を取得しています。
行70-73ではビットコインの直近の取引データから最新の取引価格、タイムスタンプを取得しています。
行76ではCsvクラスのwrite_buy_order()メソッドで買い注文のデータをCSVファイルに保存しています。
CSVファイルの名称は「buy_order(BTC_JPY).csv」になります。
行79ではCsvクラスのget_buy_order()メソッドで買い注文のCSVファイル「buy_order(BTC_JPY).csv」をPandasのDataFrameに取り込んでいます。
行87ではDataFrameの先頭から10件のデータを表示しています。
行90-94ではCsvクラスのupdate_buy_order()メソッドで買い注文の約定数量(real_qty)、約定価格(real_price)を更新しています。
行96-105ではCsvクラスのget_buy_order()メソッドで更新後の買い注文のデータをPandasのDataFrameに取り込んで先頭の10件を表示しています。
demo4.py:
### Import the libraries
import os
import os.path
import time
from time import sleep
import datetime as dt
from datetime import timedelta
import numpy as np
import pandas as pd
import pandas_ta as pa
import matplotlib.pyplot as plt
from lib.base import Bcolors, Gvar, Coin, Gmo_dataframe
from lib.debug import Debug # dependencies Gvar
from lib.gmail import Gmail # dependencies Gvar, Debug, GmailConfig
from lib.gmail_config import GmailConfig
from lib.api import Api # dependencies Gvar, Coin
from lib.csv import Csv # dependencies Gvar, Coin
from lib.trade import Trade # dependencies Gvar, Coin
from lib.buy_sell import BuySell # dependencies Gvar, Coin
from lib.sell_buy import SellBuy # dependencies Gvar, Coin
import argparse
import warnings
warnings.simplefilter('ignore')
#####################################################################################
### MAIN Demo [4] Csv class: write_buy_order(), get_buy_order(), update_buy_order()
#####################################################################################
###########################################################
# instantiate gvar/coin class and initialize properties
###########################################################
### define constants
FOLDER_NAME = 'bot'
### initiate Gvar class
gvar = Gvar()
gvar.exchange = FOLDER_NAME # bot
gvar.domain = os.environ['USERDOMAIN'].lower() # 'desktop-pc' or 'note-pc'
gvar.folder_gmo = f'{gvar.domain}/{gvar.exchange}/' # 'desktop-pc/bot/'
gvar.callers_method_name = '_main_:'
######################################################################
# Csv class: write_buy_order(), get_buy_order(), update_buy_order()
######################################################################
gvar.callers_method_name = 'Demo4():'
gvar.debug_mode = True
debug = Debug(gvar)
debug.print_log(f'{Bcolors.OKGREEN}Demo4 ({gvar.debug_mode=}) Started{Bcolors.ENDC}')
coin = Coin() # Coin('BTC_JPY')
api = Api(gvar, coin)
csv = Csv(gvar, coin)
### get crypto data from gmo via api
status, df = api.get_crypto_try(page=1, count=10) # get crypto (BTC_JPY)
debug.print_log(f".... {gvar.callers_method_name} get_crypto_try(page=1, count=10) ▶ {status=}, {df.shape[0]=} ")
if status != 0 or df.shape[0] == 0:
debug.trace_error(f"get_crypto_try(page=1, count=10) ▶ {status=}, {df.shape[0]=}: quit python... ")
quit()
### no errors and no empty dataframe
# get last timestamp and price from gmo dataframe
buy_time = df.iloc[-1]['timestamp']
sell_time = buy_time
qty = coin.qty
price = df.iloc[-1]['price']
### write_buy_order(buy_time: dt.datetime.utcnow, sell_time: dt.datetime.utcnow, qty: float, price: float, real_qty=0.0, real_price=0.0, real_fee=0.0) -> None:
csv.write_buy_order(buy_time, sell_time, qty, price)
### get_buy_order() -> pd.DataFrame:
df = csv.get_buy_order()
# empty dataframe ?
if df.shape[0] == 0:
debug.trace_error(f"get_buy_order() ▶ dataframe is empty: {df.shape[0]=}. quit python... ")
quit()
### no errors
print('-'*190)
print(df.head())
print('-'*190)
col_name_list = ['real_qty', 'real_price']
col_value_list = [qty, price + 100]
### update_buy_order(buy_time: dt.datetime.utcnow, col_name_list: list, col_value_list: list) -> None:
csv.update_buy_order(buy_time, col_name_list, col_value_list)
df = csv.get_buy_order()
# empty dataframe ?
if df.shape[0] == 0:
debug.trace_error(f"get_buy_order() ▶ dataframe is empty: {df.shape[0]=}. quit python... ")
quit()
### no errors
print('-'*190)
print(df.head())
print('-'*190)
debug.print_log(f'{Bcolors.OKGREEN}Demo4 Ended{Bcolors.ENDC}')
図4-1は実行結果です。
Csvクラスのwrite_buy_order()メソッドを実行して買い注文のCSVファイルを作成しています。
さらにupdate_buy_order()メソッドを実行して買い注文の約定数量と約定価格を更新しています。
図4-2は買い注文のCSVファイル「buy_order(BTC_JPY).csv」をExcelで開いた画面です。
注文の履歴をCSVファイルに保存しておくと後で確認するときに便利です。
-
BOTのcreate_buy_order(), create_sell_order(), update_order()メソッドを使用してトレードしてみる
ここではBuySellクラスの各種メソッドを使用してトレードする方法を説明します。
create_buy_order()メソッドは「買い注文」を自動的に行います。
内部的にはGMO CoinのAPI経由で実際の買い注文を出します。
ちなみに買い注文は「成行き」を使います。
成行きの買い注文が約定すると「買いポジション」を保持することになります。
さらに注文の履歴を残すために注文データをCSVファイルに保存します。
create_sell_order()メソッドは「売り注文」を自動的に出します。
内部的にはGMO CoinのAPI経由で買いポジションを決済します。
ちなみに買いポジションの決済は「指値」を使います。
さらに注文の履歴を残すために注文データをCSVファイルに保存します。
update_order()メソッドは、買いポジションの決済注文(売り注文)が約定したかどうか調べます。
約定しているときは損益ファイルに履歴を保存します。
まだ約定していないときは一定の時間待って再度約定しているか調べます。
これら一覧の処理を注文が約定するかストップロスの処理を行うまで繰り返します。
行58-62ではCoin, Api, Csv, Trade, BuySellクラスのインスタンスを生成しています。
Coinクラスはデフォルトでビットコイン(BTC_JPY)用に生成されます。
行70ではCsvクラスのdelete_file_driver()メソッドで「buy_sell」と「sell_buy」フォルダのすべてのファイルを削除します。
行81-86のforループではGMO Coinから取引データを100件単位で5回取得しています。
合計500件の取引データを取得しています。
行89では取引データが格納されている5個のDataFrameを連結してマージしています。
これでPandasのDataFrameには500件の取引データが格納されます。
行97ではPandasのDataFrameのsort_values()メソッドで取引データを「timestamp」の昇順に並べ替えています。
行100ではDataFrameのdrop_duplicates()メソッドで「taimestamp」が重複する取引データを削除しています。
重複しているときは最後の取引データを有効にします。
行104-106ではDataFrameの取引データをCSVファイル「master(BTC_JPY).csv」に保存しています。
行107ではCoinクラスのset_master_df()メソッドでCoinクラスのプロパティ「master_df」にDataFrameを保存しています。
行110ではCsvクラスのget_gmo_master()メソッドで行106で保存したCSVファイルをPandasのDataFrameに取り込んでいます。
行118-122ではDataFrameに新規のカラム名「symbol, buy_price, sell_price」を追加しています。
行125ではカラム値が空のとき前のデータで埋め込むようにしています。
行126ではDataFrameのカラム値が空のとき行を削除しています。
行133-135ではDataFrameに格納されている取引データを「秒」単位で丸めています。
つまり、1秒間隔の取引データを生成しています。
行138ではDataFrameのカラム「timestamp」が重複する行を削除しています。
このとき重複する最後の行を有効にしています。
行145-149ではDataFrameに新規カラム「open, close, low, high, size」を追加しています。
行155ではDataFrameのインデックスをリセットして採番しています。
行158ではDataFrameのカラム名「timestamp」を「time」に変更しています。
行159ではDataFrameのカラム名(列名)を並べ替えています。
行162ではCoinクラスのset_master2_df()メソッドでCoinクラスのプロパティ「master2_df」にDataFrameを保存しています。
行168ではBuySellクラスのreset_restart_process()メソッドで各種CSVファイルを初期化しています。
行179-180では取引データが格納されているDataFrame(mas_df)から「BUY」の取引データのみ抽出して「mas_buy_df」に保存しています。
行186-187では取引データ(買注文)から最終行のカラム値「time, buy_price」を取得しています。
行188ではCoinクラスのプロパティから「qty(数量)」を取得しています。
qtyプロパティにはデフォルトでビットコインの最小値(0.01)が設定されています。
行190ではBuySellクラスのcreate_buy_order()メソッドを実行して買い注文を出しています。
行198ではCsvクラスのget_buy_order()メソッドで買い注文のCSVファイルをPandasのDataFrameに取り込んでいます。
行206-207では取引データ(mas_df)から「SELL」のデータのみ抽出して「mas_sell_df」に保存しています。
行213-214では売りの取引データから最終行のカラム値「time, sell_price」を取得しています。
行215ではTradeクラスのget_sell_price()メソッドで売値を取得しています。
売値は買値に利益率を掛けて計算しています。
行218ではBuySellクラスのcreate_sell_order()メソッドで売り注文を出しています。
この場合、create_buy_order()で取得した買いポジションを決済(売り注文)していることになります。
ここでは利大損小になるように直近のマーケットの売値が計算した売値より高いときは、
マーケットの売値で指値の注文を出します。
行228ではBuySellクラスのupdate_order()メソッドで売り注文が約定したかどうか調べます。
約定しているときは損益のExcelファイルに履歴を保存します。
約定していないときは一定時間経過してから再度約定しているかどうか調べます。
Gvarクラスのstop_lossプロパティに「True」を設定すると自動的にストップロスの処理も行います。
demo5.py:
### Import the libraries
import os
import os.path
import time
from time import sleep
import datetime as dt
from datetime import timedelta
import numpy as np
import pandas as pd
import pandas_ta as pa
import matplotlib.pyplot as plt
from lib.base import Bcolors, Gvar, Coin, Gmo_dataframe
from lib.debug import Debug # dependencies Gvar
from lib.gmail import Gmail # dependencies Gvar, Debug, GmailConfig
from lib.gmail_config import GmailConfig
from lib.api import Api # dependencies Gvar, Coin
from lib.csv import Csv # dependencies Gvar, Coin
from lib.trade import Trade # dependencies Gvar, Coin
from lib.buy_sell import BuySell # dependencies Gvar, Coin
from lib.sell_buy import SellBuy # dependencies Gvar, Coin
import argparse
import warnings
warnings.simplefilter('ignore')
##############################################################################################################################################
### MAIN Demo [5] BuySell class: delete_file_driver(), reset_restart_process(), create_buy_order(), create_sell_order(), update_order()
##############################################################################################################################################
###########################################################
# instantiate gvar/coin class and initialize properties
###########################################################
### define constants
FOLDER_NAME = 'bot'
### initiate Gvar class
gvar = Gvar()
gvar.exchange = FOLDER_NAME # bot
gvar.domain = os.environ['USERDOMAIN'].lower() # 'desktop-pc' or 'note-pc'
gvar.folder_gmo = f'{gvar.domain}/{gvar.exchange}/' # 'desktop-pc/bot/'
gvar.callers_method_name = '_main_:'
##########################################################################################################################
# BuySell class: delete_file_driver(), reset_restart_process(), create_buy_order(), create_sell_order(), update_order()
##########################################################################################################################
gvar.real_mode = False
gvar.reset_mode = True
gvar.debug_mode = True
gvar.callers_method_name = 'Demo5():'
debug = Debug(gvar)
debug.print_log(f'{Bcolors.OKGREEN}Demo5 ({gvar.real_mode=}, {gvar.reset_mode=}, {gvar.debug_mode=}) Started{Bcolors.ENDC}')
coin = Coin() # Coin('BTC_JPY')
api = Api(gvar, coin)
csv = Csv(gvar, coin)
trade = Trade(gvar, coin)
buysell = BuySell(gvar, coin)
symbol = coin.symbol
########################################################################
### 1: delete all csv files from buy_sell, sell_buy folders
########################################################################
# delete_file_driver() -> None:
csv.delete_file_driver()
# debug.trace_warn(f".... delete_file_driver() ▶ completed... ")
########################################################################
### 2: load crypto data from GMO Coin
########################################################################
# load crypto data from GMO
df_list = [] # append 10 dataframe (GMO)
### get crypto market data from GMO 1-5 pages
for page in range(1, 6): # (1,2,...5)
### get_crypto_try(page: int, count: int) -> tuple: return (status, df)
status, df = api.get_crypto_try(page, count=100)
debug.trace_write(f".... get_crypto_try({page=}, count=100) ▶ {status=} {df.shape[0]=} ")
if status == 0: df_list.append(df)
sleep(5) # sleep 5 seconds
# concatinate 10 dataframes
df = pd.concat(df_list, axis=0) # price, side, size, timestamp(UTC) descending order
debug.trace_warn(f".... pd.concat(df_list={len(df_list)}, axis=0) ▶ {df.shape[0]=} ")
########################################################################
### 3: sort & drop duplicate data
########################################################################
# sort by timestamp (ascending order of timestamp)
df.sort_values('timestamp', ascending=True, inplace=True)
# drop duplicate time from the master dataframe
df.drop_duplicates(subset=['timestamp'], keep='last', inplace=True)
# debug.trace_warn(f".... df.drop_duplicates(subset=['timestamp'], keep='last', inplace=True) ▶ {df.shape[0]=} ")
# save gmo master to disk
csv_file = csv.folder_trading_type + f'master({symbol}).csv'
# decktop-pc/bot/buy_sell/master(BTC_JPY).csv
df.to_csv(csv_file, index=False) # overwrite 'master(BTC_JPY).csv' file
coin.set_master_df(df) # sorted by ascending order of timestamp
# get_gmo_master() -> pd.DataFrame:
df = csv.get_gmo_master()
# debug.trace_warn(f".... get_gmo_master() ▶ {df.shape[0]=} ")
##########################################################################################
### 4: add columns into the master dataframe: symbol, buy_price, sell_price
##########################################################################################
# add a symbol column into the master_df
df['symbol'] = symbol
# add buy_price, sell_price into the master_df ★
df['buy_price'] = df.apply(lambda row: row['price'] if row['side'] == 'BUY' else np.NaN, axis=1)
df['sell_price'] = df.apply(lambda row: row['price'] if row['side'] == 'SELL' else np.NaN, axis=1)
# fill null with previous price from the master_df
df.fillna(method='ffill', inplace=True)
df.dropna(inplace=True)
# debug.trace_warn(f".... df.fillna(method='ffill', inplace=True) ▶ df.dropna(inplace=True) ▶ {df.shape[0]=} ")
######################################################################
### 5: round the timestamp column to 1S (1 second) or 1T (1 minute)
######################################################################
# get a round timestamp freq
freq = coin.round_timestamp_freq # 1S or 1T
df['timestamp'] = df['timestamp'].apply(lambda x: x.round(freq=freq)) # round timestamp
df['timestamp'] = df['timestamp'].apply(lambda x: x.round(freq='S')) # round seconds
# drop duplicate timestamp from the master dataframe
df.drop_duplicates(subset=['timestamp'], keep='last', inplace=True)
# debug.trace_warn(f".... df.drop_duplicates(subset=['timestamp'], keep='last', inplace=True) ▶ {df.shape[0]=} ")
###############################################################################################
### 6: add open/close, low/high columns into the master dataframe : price => buy/sell price
###############################################################################################
df['open'] = df.groupby('timestamp')['price'].transform('first')
df['close'] = df.groupby('timestamp')['price'].transform('last')
df['low'] = df.groupby('timestamp')['price'].transform('min')
df['high'] = df.groupby('timestamp')['price'].transform('max')
df['size'] = df.groupby('timestamp')['size'].transform('sum')
###################################################################################################################################################
### 7: rename timestamp to time and reorder columns => 'time','open','close','low','high','price','buy_price','sell_price','side','size','symbol'
###################################################################################################################################################
df.reset_index(drop=False, inplace=True)
# rename and reorder columns of the master_df
df.rename(columns={'timestamp': 'time'}, inplace=True) # ★
df = df[['time','open','close','low','high','price','buy_price','sell_price','side','size','symbol']]
# save master_df to coin class
coin.set_master2_df(df) # save final master_df to coin class
debug.trace_warn(f".... coin.set_master2_df(df) ▶ after round({freq=}) {df.shape[0]=} ")
#############################################################################################################
### 8: reset_restart_process() -> None:
#############################################################################################################
buysell.reset_restart_process()
# debug.trace_warn(f".... reset_restart_process() completed...")
#############################################################################################################
### 9: create_buy_order(buy_time: dt.datetime.utcnow, qty: float, price: float) -> int: # return status
#############################################################################################################
_q_ = coin.qty_decimal; _p_ = coin.price_decimal
mas_df = df.copy()
# filter gmo master
filter_mask = mas_df['side'] == 'BUY'
mas_buy_df = mas_df[filter_mask]
if mas_buy_df.shape[0] == 0:
debug.trace_error(f".... buy master dataframe is empty: {mas_buy_df.shape[0]=}. quit python... ")
quit()
# get last buy_time, buy_price from gmo buy master
buy_time = mas_buy_df.iloc[-1]['time']
buy_price = mas_buy_df.iloc[-1]['buy_price']
qty = coin.qty
status = buysell.create_buy_order(buy_time, qty, buy_price)
# debug.trace_warn(f".... create_buy_order({buy_time=:%Y-%m-%d %H:%M:%S}, {qty=:,.{_q_}f}, {buy_price=:,.{_p_}f}) ▶ {status=} ")
# error ?
if status != 0:
debug.trace_error(f".... create_buy_order({buy_time=:%Y-%m-%d %H:%M:%S}, {qty=:,.{_q_}f}, {buy_price=:,.{_p_}f}) ▶ {status=}: quit python... ")
quit()
# get_buy_order()
buy_df = csv.get_buy_order()
# debug.trace_warn(f".... get_buy_order() ▶ {buy_df.shape[0]=} ")
###################################################################################################################
### 10: create_sell_order(sell_time: dt.datetime.utcnow, ms_price: float, buy_time: dt.datetime.utcnow) -> int:
###################################################################################################################
### filter gmo master
filter_mask = mas_df['side'] == 'SELL'
mas_sell_df = mas_df[filter_mask]
if mas_sell_df.shape[0] == 0:
debug.trace_error(f".... sell master dataframe is empty: {mas_sell_df.shape[0]=}. quit python... ")
quit()
# get last sell_time and sell_price from gmo sell master
sell_time = mas_sell_df.iloc[-1]['time']
mas_sell_price = mas_sell_df.iloc[-1]['sell_price']
new_sell_price = trade.get_sell_price(buy_price)
if mas_sell_price > new_sell_price: new_sell_price = mas_sell_price
status = buysell.create_sell_order(sell_time, new_sell_price, buy_time)
# debug.trace_warn(f".... create_sell_order({sell_time=:%Y-%m-%d %H:%M:%S}, {new_sell_price=:,.{_p_}f}, {buy_time=:%Y-%m-%d %H:%M:%S}) ▶ {status=} ")
# error ?
if status != 0:
debug.trace_error(f".... create_sell_order({sell_time=:%Y-%m-%d %H:%M:%S}, {new_sell_price=:,.{_p_}f}, {buy_time=:%Y-%m-%d %H:%M:%S}) ▶ {status=}: quit python... ")
quit()
#############################################
### 11: update_order() -> None:
#############################################
buysell.update_order()
# debug.trace_warn(f".... update_order() completed...")
debug.print_log(f'{Bcolors.OKGREEN}Demo5 Ended{Bcolors.ENDC}')
図5-1は実行結果です。
Csvクラスのdelete_file_driver()メソッドでは「buy_sell]と「sell_buy」フォルダからすべてのファイルを削除します。
Apiクラスのget_crypto_try()メソッドでは取引所のGMO Coinからビットコイン(BTC_JPY)の取引データを500件取得してPandasのDataFrameに格納します。
BuySellクラスのreset_restart_process()メソッドでは各種CSVファイルを初期化します。
BuySellクラスのcreate_buy_order()メソッドではGMO Coinに対して買い注文(成行注文)を実行して各種注文ファイルに履歴を作成します。
この時点で買いのポジションを保持することになります。
BuySellクラスのcreate_sell_order()メソッドでは買いのポジションを決済(売りの指値注文)します。
BuySellクラスのupdate_order()メソッドでは買いポジションの決済が約定したかどうか監視して、
約定したときは各種CSVファイルを作成・更新します。
さらに損益のExcelファイルも作成します。
図5-2はBOTのフォルダ構成です。フォルダ「desktop-pc」直下にサブフォルダ「bot」を作成します。
さらにフォルダ「bot」の直下にサブフォルダ「buy_sell」と「sell_buy」を作成します。
フォルダ「buy_sell」には「買い注文▶売り注文」の取引履歴がCSVファイルに作成されます。
フォルダ「sell_buy」には「空売り注文▶買戻し注文」の取引履歴がCSVファイルに作成されます。
ここでは「買い▶売り」注文を行っているので「buy_sell」フォルダに各種CSVファイルが作成されています。
損益のファイル「order(BTC_JPY).xlsx」はExcelの形式で作成されます。
-
BOTのbuy_sell(), update_order()メソッドを使用してビットコイン(BTC_JPY)を自動トレードしてみる(ストップロス機能なし)
ここではBuySellクラスの各種メソッドを使用してビットコイン(BTC_JPY)を自動トレードする方法を説明します。
前出のデモプログラムは修正して関数「auto_trade()」を作成します。
auto_trade()関数は前出のデモプログラムと類似しているので解説を省略します。
auto_trade() function:
###############################
def auto_trade(i: int) -> None:
gvar.callers_method_name = f'auto_trade({i}):'
debug.trace_warn(f".... auto_trade({i=})")
symbol = coin.symbol
########################################################################
### 1: load crypto data from GMO Coin
########################################################################
# load crypto data from GMO
df_list = [] # append 10 dataframe (GMO)
### get crypto market data from GMO 1-10 pages
for page in range(1, 11): # (1,2,...10)
### get_crypto_try(page: int, count: int) -> tuple: # return (status, df)
status, df = api.get_crypto_try(page, count=100) # (n, 100)
# debug.trace_write(f".... get_crypto_try({page=}, count=100) ▶ {status=} {df.shape[0]=} ")
if status == 0: df_list.append(df)
sleep(5) # sleep 5 seconds
# concatinate 10 dataframes
current_df = pd.concat(df_list, axis=0) # price, side, size, timestamp(UTC) descending order
debug.trace_warn(f".... pd.concat(df_list={len(df_list)}, axis=0) ▶ {current_df.shape[0]=} ")
### load gmo master
# get_gmo_master() -> pd.DataFrame:
master_df = csv.get_gmo_master()
# desktop-pc/bat/buysell/master(BTC_JPY).csv
# merge master_df and current_df to df
df = pd.concat([master_df, current_df], axis=0)
debug.trace_warn(f".... pd.concat([master_df, current_df], axis=0) ▶ {df.shape[0]=} ")
if df.shape[0] > 16_000:
start_row = df.shape[0] - 16_000
# drop N rows from gmo master
df = df.iloc[start_row:,:] # keep max 16,000 rows (4 hours)
########################################################################
### 2: sort & drop duplicate data
########################################################################
# sort by timestamp (ascending order of timestamp)
df.sort_values('timestamp', ascending=True, inplace=True)
# drop duplicate time from the master dataframe
df.drop_duplicates(subset=['timestamp'], keep='last', inplace=True)
# debug.trace_warn(f".... df.drop_duplicates(subset=['timestamp'], keep='last', inplace=True) ▶ {df.shape[0]=} ")
# save gmo master to disk
csv_file = csv.folder_trading_type + f'master({symbol}).csv'
# decktop-pc/bot/buy_sell/master(BTC_JPY).csv
# decktop-pc/bot/sell_buy/master(BTC_JPY).csv
df.to_csv(csv_file, index=False) # overwrite 'master(BTC_JPY).csv' file
coin.master_df = df # sorted by ascending order of timestamp
# get_gmo_master(self) -> pd.DataFrame:
df = csv.get_gmo_master()
# debug.trace_warn(f".... get_gmo_master() ▶ {df.shape[0]=} ")
##########################################################################################
### 3: add columns into the master dataframe: symbol, buy_price, sell_price
##########################################################################################
# add a symbol column into the master_df
df['symbol'] = symbol
# add buy_price, sell_price into the master_df ★
df['buy_price'] = df.apply(lambda row: row['price'] if row['side'] == 'BUY' else np.NaN, axis=1)
df['sell_price'] = df.apply(lambda row: row['price'] if row['side'] == 'SELL' else np.NaN, axis=1)
# fill null with previous price from the master_df
df.fillna(method='ffill', inplace=True)
df.dropna(inplace=True)
# debug.trace_warn(f".... df.fillna(method='ffill', inplace=True) ▶ df.dropna(inplace=True) ▶ {df.shape[0]=} ")
#####################################################################
### 4: round the timestamp column to 1S(1 second) or 1T (1 minute)
#####################################################################
# get a round timestamp freq
freq = coin.round_timestamp_freq
df['timestamp'] = df['timestamp'].apply(lambda x: x.round(freq=freq)) # round timestamp
df['timestamp'] = df['timestamp'].apply(lambda x: x.round(freq='S')) # round seconds
# drop duplicate timestamp from the master dataframe
df.drop_duplicates(subset=['timestamp'], keep='last', inplace=True)
# debug.trace_warn(f".... df.drop_duplicates(subset=['timestamp'], keep='last', inplace=True) ▶ {df.shape[0]=} ")
###############################################################################################
### 5: add open/close, low/high columns into the master dataframe : price => buy/sell price
###############################################################################################
df['open'] = df.groupby('timestamp')['price'].transform('first')
df['close'] = df.groupby('timestamp')['price'].transform('last')
df['low'] = df.groupby('timestamp')['price'].transform('min')
df['high'] = df.groupby('timestamp')['price'].transform('max')
df['size'] = df.groupby('timestamp')['size'].transform('sum')
###################################################################################################################################################
### 6: rename timestamp to time and reorder columns => 'time','open','close','low','high','price','buy_price','sell_price','side','size','symbol'
###################################################################################################################################################
df.reset_index(drop=False, inplace=True)
# rename and reorder columns of the master_df
df.rename(columns={'timestamp': 'time'}, inplace=True) # ★
df = df[['time','open','close','low','high','price','buy_price','sell_price','side','size','symbol']]
# save master_df to coin class
coin.master2_df = df # save final master_df to coin class
debug.trace_warn(f".... coin.master2_df = df ▶ after round({freq=}) {df.shape[0]=} ")
###################################################################################################################
### 7: buy_sell(algorithm_id: int) -> None:
###################################################################################################################
# buy_sell(algorithm_id: int) -> None:
buysell.buy_sell(algorithm_id=0)
# debug.trace_warn(f".... buy_sell(algorithm_id=0) completed... ")
###################################################################################################################
### 10: update_order() -> None:
###################################################################################################################
buysell.update_order()
# debug.trace_warn(f".... update_order() completed...")
debug.print_log('.... ' + '.'*180)
return
デモプログラムのメインでは関数「auto_trade()」を呼び込むように修正します。
行44-58ではGvarクラスのインスタンスを生成して各種プロパティを設定しています。
行60-65ではDebug, Coin, Api, Csv, Trade, BuySellクラスのインスタンスを生成しています。
行70-90ではGvarクラスのreset_modeプロパティが「True」のとき初期化処理を行います。
行75ではCsvクラスのdelete_file_driver()メソッドを呼び出してフォルダ「buy_sell」と「sell_buy」のすべてのファイルを削除します。
行83ではApiクラスのload_master_driver()メソッドを呼び出してGMOから取引データを取り込んでCSVファイルに保存します。
行88ではBuySellクラスのreset_restart_process()メソッドを呼び出して各種CSVファイルを初期化します。
行96-99のwhileループでは関数「auto_trade()」を呼び出してビットコインの自動トレードを行います。
無限ループさせるときは、行99のbreakをコメントアウトして実行してください。
demo6.py:
### Import the libraries
import os
import os.path
import time
from time import sleep
import datetime as dt
from datetime import timedelta
import numpy as np
import pandas as pd
import pandas_ta as pa
import matplotlib.pyplot as plt
from lib.base import Bcolors, Gvar, Coin, Gmo_dataframe
from lib.debug import Debug # dependencies Gvar
from lib.gmail import Gmail # dependencies Gvar, Debug, GmailConfig
from lib.gmail_config import GmailConfig
from lib.api import Api # dependencies Gvar, Coin
from lib.csv import Csv # dependencies Gvar, Coin
from lib.trade import Trade # dependencies Gvar, Coin
from lib.buy_sell import BuySell # dependencies Gvar, Coin
from lib.sell_buy import SellBuy # dependencies Gvar, Coin
import argparse
import warnings
warnings.simplefilter('ignore')
### <= insert auto_trade() function here
#################################################################################################################################
### MAIN Demo [6] BuySell class: BuySell class: delete_file_driver(), reset_restart_process(), buy_sell(), update_order()
#################################################################################################################################
############################################################################
# instantiate gvar/coin class and initialize properties
############################################################################
### define constants
FOLDER_NAME = 'bot'
### initiate Gvar class
gvar = Gvar()
gvar.exchange = FOLDER_NAME # bot
gvar.domain = os.environ['USERDOMAIN'].lower() # 'desktop-pc' or 'note-pc'
gvar.folder_gmo = f'{gvar.domain}/{gvar.exchange}/' # 'desktop-pc/bot/'
gvar.callers_method_name = '_main_:'
#####################################################################################################################
# Demo [6] BuySell class: BuySell class: delete_file_driver(), reset_restart_process(), buy_sell(), update_order()
####################################################################################################################
### start Demo6
gvar.real_mode = False
gvar.reset_mode = True
gvar.stop_loss = False
gvar.debug_mode = True
gvar.callers_method_name = 'Demo6():'
debug = Debug(gvar)
coin = Coin() # Coin('BTC_JPY')
api = Api(gvar, coin)
csv = Csv(gvar, coin)
trade = Trade(gvar, coin)
buysell = BuySell(gvar, coin)
symbol = coin.symbol
debug.print_log(f"{Bcolors.OKGREEN}Demo6 ({gvar.real_mode=}, {gvar.reset_mode=}, {gvar.stop_loss=}, {gvar.debug_mode=}) Started{Bcolors.ENDC}")
if gvar.reset_mode:
###############################################################
### 1: delete all csv files from buy_sell, sell_buy folder
###############################################################
# delete_file_driver() -> None:
csv.delete_file_driver()
# debug.trace_warn(f".... delete_file_driver() ▶ completed... ")
###################################################
### 2: load the master data from GMO
###################################################
gvar.callers_method_name = 'load_master_data():'
# load_master_driver(symbol_list: list, coin_list: list, page: int, count: int) -> None:
api.load_master_driver([coin.symbol], [coin], page=1, count=10)
#########################################
### 3: reset_restart_process() -> None:
#########################################
buysell.reset_restart_process()
# debug.trace_warn(f".... reset_restart_process() completed...")
debug.print_log('.... ' + '.'*180)
###########################
### auto trade
###########################
i = 0
while True:
i += 1
auto_trade(i)
break # <= comment out a break statement
# end of while True:
debug.print_log(f'{Bcolors.OKGREEN}Demo6 Ended{Bcolors.ENDC}')
図6は実行結果です。
画面には「auto_trade(i=1)」が表示されていますが、「i=1」は1回目のループであることを意味します。
これで自動トレードが何回繰り返し実行されているかがわかります。
-
BOTのbuy_sell(), update_order()メソッドを使用してビットコイン(BTC_JPY)を自動トレードしてみる(ストップロス機能付き)
ここでは前出のデモプログラムにストップロスの機能を追加しています。
ストップロスの機能を追加するにはGvarクラスのstop_lossプロパティに「True」を設定します。
これでBuySellクラスのupdate_order()メソッドを呼び出すと自動的にストップロスの処理が行われます。
ここではさらにGvarクラスのreset_modeプロパティに「False」を設定しています。
この場合、前出のデモ6の状態を引き継いで処理を継続します。
demo7.py:
### Import the libraries
import os
import os.path
import time
from time import sleep
import datetime as dt
from datetime import timedelta
import numpy as np
import pandas as pd
import pandas_ta as pa
import matplotlib.pyplot as plt
from lib.base import Bcolors, Gvar, Coin, Gmo_dataframe
from lib.debug import Debug # dependencies Gvar
from lib.gmail import Gmail # dependencies Gvar, Debug, GmailConfig
from lib.gmail_config import GmailConfig
from lib.api import Api # dependencies Gvar, Coin
from lib.csv import Csv # dependencies Gvar, Coin
from lib.trade import Trade # dependencies Gvar, Coin
from lib.buy_sell import BuySell # dependencies Gvar, Coin
from lib.sell_buy import SellBuy # dependencies Gvar, Coin
import argparse
import warnings
warnings.simplefilter('ignore')
###############################
def auto_trade(i: int) -> None:
:::
return
##############################################################################################################################################
### MAIN Demo [7] BuySell class: BuySell class: delete_file_driver(), reset_restart_process(), buy_sell(), update_order(), stop_loss=True
##############################################################################################################################################
############################################################################
# instantiate gvar/coin class and initialize properties
############################################################################
### define constants
FOLDER_NAME = 'bot'
### initiate Gvar class
gvar = Gvar()
gvar.exchange = FOLDER_NAME # bot
gvar.domain = os.environ['USERDOMAIN'].lower() # 'desktop-pc' or 'note-pc'
gvar.folder_gmo = f'{gvar.domain}/{gvar.exchange}/' # 'desktop-pc/bot/'
gvar.callers_method_name = '_main_:'
######################################################################################################################################
# Demo [7] BuySell class: BuySell class: delete_file_driver(), reset_restart_process(), buy_sell(), update_order(), stop_loss=True
#####################################################################################################################################
### start Demo7
gvar.real_mode = False
gvar.reset_mode = False # ★
gvar.stop_loss = True # ★
gvar.debug_mode = True
gvar.callers_method_name = 'Demo7():'
debug = Debug(gvar)
coin = Coin() # Coin('BTC_JPY')
api = Api(gvar, coin)
csv = Csv(gvar, coin)
trade = Trade(gvar, coin)
buysell = BuySell(gvar, coin)
symbol = coin.symbol
debug.print_log(f"{Bcolors.OKGREEN}Demo7 ({gvar.real_mode=}, {gvar.reset_mode=}, {gvar.stop_loss=}, {gvar.debug_mode=}) Started{Bcolors.ENDC}")
if gvar.reset_mode:
:::
###########################
### auto trade
###########################
i = 0
while True:
i += 1
auto_trade(i)
break # <= comment out a break statement
# end of while True:
debug.print_log(f'{Bcolors.OKGREEN}Demo7 Ended{Bcolors.ENDC}')
図7は実行結果です。
画面に「stop_loss(0)」が表示されています。
-
BOTの各種クラスを使用してビットコイン(BTC_JPY)を2種類の方法(「買い▶売り」「空売り▶買戻し」)で自動トレードしてみる
ここでは前出のデモプログラムを改善してビットコイン(BTC_JPY)を2種類の方法(「買い▶売り」「空売り▶買戻し」)で自動トレードする方法を説明します。
前出の関数「auto_trade()」をBuySellクラスとSellBuyクラスの双方に対応するように修正します。
行119のPythonのeval()では、BuySellクラスのbuy_sell()メソッドか、SellBuyクラスのsell_buy()メソッドのいずれかを呼び出します。
行130ではBuySellクラス、またはSellBuyクラスのいずれかのupdate_order()メソッドを呼び出します。
auto_trade() function:
###############################
def auto_trade(i: int) -> None:
gvar.callers_method_name = f'auto_trade({i}):'
debug.trace_warn(f".... auto_trade({i=})")
symbol = coin.symbol
#######################################
### 1: load crypto data from GMO Coin
#######################################
# load crypto data from GMO
df_list = [] # append 10 dataframe (GMO)
### get crypto market data from GMO 1-10 pages
for page in range(1, 11): # (1,2,...10)
### get_crypto_try(page: int, count: int) -> tuple: # return (status, df)
status, df = api.get_crypto_try(page, count=100) # (n, 100)
# debug.trace_write(f".... get_crypto_try({page=}, count=100) ▶ {status=} {df.shape[0]=} ")
if status == 0: df_list.append(df)
sleep(5) # sleep 5 seconds
# concatinate 10 dataframes
current_df = pd.concat(df_list, axis=0) # price, side, size, timestamp(UTC) descending order
debug.trace_warn(f".... pd.concat(df_list={len(df_list)}, axis=0) ▶ {current_df.shape[0]=} ")
### load gmo master
# get_gmo_master() -> pd.DataFrame:
master_df = csv.get_gmo_master()
# desktop-pc/bot/buysell/master(BTC_JPY).csv
# desktop_pc/bot/sellbuy/master(BTC_JPY).csv
# merge master_df and current_df to df
df = pd.concat([master_df, current_df], axis=0)
debug.trace_warn(f".... pd.concat([master_df, current_df], axis=0) ▶ {df.shape[0]=} ")
if df.shape[0] > 16_000:
start_row = df.shape[0] - 16_000
# drop N rows from gmo master
df = df.iloc[start_row:,:] # keep max 16,000 rows
########################################
### 2: sort & drop duplicate data
########################################
# sort by timestamp (ascending order of timestamp)
df.sort_values('timestamp', ascending=True, inplace=True)
# drop duplicate time from the master dataframe
df.drop_duplicates(subset=['timestamp'], keep='last', inplace=True)
# debug.trace_warn(f".... df.drop_duplicates(subset=['timestamp'], keep='last', inplace=True) ▶ {df.shape[0]=} ")
# save gmo master to disk
csv_file = csv.folder_trading_type + f'master({symbol}).csv'
# decktop-pc/bot/buy_sell/master(BTC_JPY).csv
# decktop-pc/bot/sell_buy/master(BTC_JPY).csv
df.to_csv(csv_file, index=False) # overwrite 'master(BTC_JPY).csv' file
coin.master_df = df # sorted by ascending order of timestamp
# get_gmo_master(self) -> pd.DataFrame:
df = csv.get_gmo_master()
# debug.trace_warn(f".... get_gmo_master() ▶ {df.shape[0]=} ")
##########################################################################################
### 3: add columns into the master dataframe: symbol, buy_price, sell_price
##########################################################################################
# add a symbol column into the master_df
df['symbol'] = symbol
# add buy_price, sell_price into the master_df ★
df['buy_price'] = df.apply(lambda row: row['price'] if row['side'] == 'BUY' else np.NaN, axis=1)
df['sell_price'] = df.apply(lambda row: row['price'] if row['side'] == 'SELL' else np.NaN, axis=1)
# fill null with previous price from the master_df
df.fillna(method='ffill', inplace=True)
df.dropna(inplace=True)
# debug.trace_warn(f".... df.fillna(method='ffill', inplace=True) ▶ df.dropna(inplace=True) ▶ {df.shape[0]=} ")
#####################################################################
### 4: round the timestamp column to 1S (1second) or 1T (1 minute)
#####################################################################
# get a round timestamp freq
freq = coin.round_timestamp_freq
df['timestamp'] = df['timestamp'].apply(lambda x: x.round(freq=freq)) # round timestamp
df['timestamp'] = df['timestamp'].apply(lambda x: x.round(freq='S')) # round seconds
# drop duplicate timestamp from the master dataframe
df.drop_duplicates(subset=['timestamp'], keep='last', inplace=True)
# debug.trace_warn(f".... df.drop_duplicates(subset=['timestamp'], keep='last', inplace=True) ▶ {df.shape[0]=} ")
###############################################################################################
### 5: add open/close, low/high columns into the master dataframe : price => buy/sell price
###############################################################################################
df['open'] = df.groupby('timestamp')['price'].transform('first')
df['close'] = df.groupby('timestamp')['price'].transform('last')
df['low'] = df.groupby('timestamp')['price'].transform('min')
df['high'] = df.groupby('timestamp')['price'].transform('max')
df['size'] = df.groupby('timestamp')['size'].transform('sum')
###################################################################################################################################################
### 6: rename timestamp to time and reorder columns => 'time','open','close','low','high','price','buy_price','sell_price','side','size','symbol'
###################################################################################################################################################
df.reset_index(drop=False, inplace=True)
# rename and reorder columns of the master_df
df.rename(columns={'timestamp': 'time'}, inplace=True) # ★
df = df[['time','open','close','low','high','price','buy_price','sell_price','side','size','symbol']]
# save master_df to coin class
coin.master2_df = df # save final master_df to coin class
debug.trace_warn(f".... coin.master2_df = df ▶ after round({freq=}) {df.shape[0]=} ")
##############################################
### 7: call buy_sell() or sell_buy()
##############################################
eval(f'tradeBoth.{coin.trade_type}')(0) # call 'tradeBoth.buy_sell' or 'tradeBoth.sell_buy' method
# if coin.trade_type == 'buy_sell':
# tradeBoth.buy_sell(algorithm_id=0)
# else: # 'sell_buy'
# tradeBoth.sell_buy(algorithm_id=0)
##############################################
### 8: update_order() -> None:
##############################################
tradeBoth.update_order()
# debug.trace_warn(f".... update_order() completed...")
return
デモプログラム(demo8.py)の行42ではビットコインのシンボル「BTC_JPY」をペアで定義します。
行46では「buy_sell」と「sell_buy」を定義します。
行51では2個のCoinクラスのインスタンスを生成して格納します。
行70-102のforループではビットコインのCoinクラスに各種プロパティを設定しています。
行153-167のwhileループでは関数「auto_trade()」を呼び出して自動トレードしています。
行166ではCoinクラスの「trade_type」プロパティを調べてBuySell, SellBuyクラスのインスタンスを生成して「tradeBoth」に保存します。
行167では関数「auto_trade()」を呼び出しています。
これで自動的に「buy_sell」と「sell_buy」の自動トレードが実行されます。
行170をコメントアウトすれば無限ループします。
つまり、24時間365日自動トレードできます。
demo8.py:
### Import the libraries
import os
import os.path
import time
from time import sleep
import datetime as dt
from datetime import timedelta
import numpy as np
import pandas as pd
import pandas_ta as pa
import matplotlib.pyplot as plt
from lib.base import Bcolors, Gvar, Coin, Gmo_dataframe
from lib.debug import Debug # dependencies Gvar
from lib.gmail import Gmail # dependencies Gvar, Debug, GmailConfig
from lib.gmail_config import GmailConfig
from lib.api import Api # dependencies Gvar, Coin
from lib.csv import Csv # dependencies Gvar, Coin
from lib.trade import Trade # dependencies Gvar, Coin
from lib.buy_sell import BuySell # dependencies Gvar, Coin
from lib.sell_buy import SellBuy # dependencies Gvar, Coin
import argparse
import warnings
warnings.simplefilter('ignore')
###############################
def auto_trade(i: int) -> None:
:::
return
################################################################################
### MAIN Demo [8] BuySell(), SellBuy() classes
################################################################################
# -----------------------------------------------------------------------------
# 1 2
# -----------------------------------------------------------------------------
symbol_list = ['BTC_JPY', 'BTC_JPY'] # crypto symbol for leverage trade
round_timestamp_list = ['1S', '1S'] # gmo master freq: H-hour, T-minute, S-seconds, L-milliseconds
suspend_list = [False, False] # active(BTC_JPY)
master_not_found_list = [False, False] # used to add coins
trade_type_list = ['buy_sell', 'sell_buy']
qty_list = [0.01, 0.01] # min qty
profit_rate_list = [1.0015, 1.0015]
leverage_fee_list = [0.0004, 0.0004]
stop_loss_rate_list = [0.0200, 0.0200]
coin_list = [Coin(), Coin()]
############################################################################
# instantiate gvar/coin class and initialize properties
############################################################################
### define constants
FOLDER_NAME = 'bot'
### initiate Gvar class
gvar = Gvar()
gvar.exchange = FOLDER_NAME # bot
gvar.domain = os.environ['USERDOMAIN'].lower() # 'desktop-pc' or 'note-pc'
gvar.folder_gmo = f'{gvar.domain}/{gvar.exchange}/' # 'desktop-pc/bot/'
gvar.callers_method_name = '_main_:'
gvar.coin_list = coin_list
### update Coin class properties
active_coin_list = []
for i, symbol in enumerate(symbol_list):
coin = coin_list[i]
coin.symbol = symbol
coin.suspend = suspend_list[i]
if not coin.suspend:
active_coin_list.append(coin)
coin.round_timestamp_freq = round_timestamp_list[i]
coin.master_csv_not_found = master_not_found_list[i]
coin.master_df = pd.DataFrame()
coin.master2_df = pd.DataFrame()
coin.real_mode = gvar.real_mode
coin.debug_mode = gvar.debug_mode
coin.fake_or_real = 'real' if gvar.real_mode else 'fake' # 'real' or 'fake'
coin.trade_type = trade_type_list[i] # 'buy_sell' or 'sell_buy'
coin.qty = qty_list[i]
coin.profit_rate = profit_rate_list[i]
coin.leverage_fee_rate = leverage_fee_list[i]
coin.stop_loss_rate = stop_loss_rate_list[i]
coin.price_decimal = 3 if coin.symbol == 'XRP_JPY' else 0
if coin.symbol in 'BTC_JPY' :
coin.qty_decimal = 2
elif coin.symbol in 'ETH_JPY,BCH_JPY':
coin.qty_decimal = 1
else: # 'LTC_JPY,XRP_JPY'
coin.qty_decimal = 0
############################################################################
# BuySell(), SellBuy() classes
############################################################################
### start Demo8
gvar.real_mode = False
gvar.reset_mode = True
gvar.debug_mode = True
gvar.stop_loss = True
gvar.callers_method_name = 'Demo8():'
debug = Debug(gvar)
coin = coin_list[0]
api = Api(gvar, coin)
csv = Csv(gvar, coin)
trade = Trade(gvar, coin)
debug.print_log(f"{Bcolors.OKGREEN}Demo8 ({gvar.real_mode=}, {gvar.reset_mode=}, {gvar.stop_loss=}, {gvar.debug_mode=}) Started{Bcolors.ENDC}")
if gvar.reset_mode:
########################################################################
### 1: delete all csv files from buy_sell, sell_buy folder
########################################################################
# delete_file_driver() -> None:
csv.delete_file_driver()
########################################################################
### 2: load crypto data from GMO
########################################################################
gvar.callers_method_name = 'load_master_data():'
# load_master_driver(symbol_list: list, coin_list: list, page: int, count: int) -> None:
api.load_master_driver(symbol_list, coin_list, page=1, count=10)
#######################################################################
### 3: reset_restart_process() -> None:
#######################################################################
gvar.callers_method_name = 'reset_restart_process():'
for i, _ in enumerate(symbol_list):
coin = coin_list[i]
if not coin.suspend:
if gvar.reset_mode or coin.master_csv_not_found:
tradeBoth = BuySell(gvar, coin) if coin.trade_type == 'buy_sell' else SellBuy(gvar, coin)
tradeBoth.reset_restart_process()
# end of for i, _ in enumerate(symbol_list):
#######################################################
### 4: auto_trade()
#######################################################
i = 0
while True:
i += 1
for j, symbol in enumerate(symbol_list):
# suspend coin ?
if coin_list[j].suspend: continue
### get or instantiate classes : Coin, Api, Csv, Trade, BuySell, SellBuy
coin = coin_list[j] # get coin class
api = Api(gvar, coin)
csv = Csv(gvar, coin)
trade = Trade(gvar, coin)
tradeBoth = BuySell(gvar, coin) if coin.trade_type == 'buy_sell' else SellBuy(gvar, coin)
auto_trade(i)
# end of for j, symbol in enumerate(symbol_list):
break # <= comment out
# end of while True:
debug.print_log(f'{Bcolors.OKGREEN}Demo8 Ended{Bcolors.ENDC}')
図8-1は実行結果です。
画面には「BuySell()」のログが表示されています。
図8-2は実行結果です。
画面には「SellBuy()」のログが表示されています。
-
前出のBOTに仮想通貨ごとの利益、約定件数、ロスカットの件数を表示する
ここでは前出のデモプログラムに仮想通貨ごとの利益、約定件数、ロスカットの件数を表示する機能を追加しています。
行172ではTradeクラスのprint_profit_driver()メソッドを呼び出して仮想通貨ごとの損益を表示します。
行176ではTradeクラスのprint_order_count_driver()メソッドを呼び出して仮想通貨ごとの約定件数を表示します。
行180ではTradeクラスのprint_loss_cut_count_driver()メソッドを呼び出して仮想通貨ごとのロスカット件数を表示します。
demo9.py:
### Import the libraries
import os
import os.path
import time
from time import sleep
import datetime as dt
from datetime import timedelta
import numpy as np
import pandas as pd
import pandas_ta as pa
import matplotlib.pyplot as plt
from lib.base import Bcolors, Gvar, Coin, Gmo_dataframe
from lib.debug import Debug # dependencies Gvar
from lib.gmail import Gmail # dependencies Gvar, Debug, GmailConfig
from lib.gmail_config import GmailConfig
from lib.api import Api # dependencies Gvar, Coin
from lib.csv import Csv # dependencies Gvar, Coin
from lib.trade import Trade # dependencies Gvar, Coin
from lib.buy_sell import BuySell # dependencies Gvar, Coin
from lib.sell_buy import SellBuy # dependencies Gvar, Coin
import argparse
import warnings
warnings.simplefilter('ignore')
###############################
def auto_trade(i: int) -> None:
:::
return
################################################################################
### MAIN Demo [9] profit, order count, loss cut count
################################################################################
# -----------------------------------------------------------------------------
# 1 2
# -----------------------------------------------------------------------------
symbol_list = ['BTC_JPY', 'BTC_JPY'] # crypto symbol for leverage trade
round_timestamp_list = ['1S', '1S'] # gmo master freq: H-hour, T-minute, S-seconds, L-milliseconds
suspend_list = [False, False] # active(BTC_JPY)
master_not_found_list = [False, False] # used to add coins
trade_type_list = ['buy_sell', 'sell_buy']
qty_list = [0.01, 0.01] # min qty
profit_rate_list = [1.0015, 1.0015]
leverage_fee_list = [0.0004, 0.0004]
stop_loss_rate_list = [0.0200, 0.0200]
coin_list = [Coin(), Coin()]
############################################################################
# instantiate gvar/coin class and initialize properties
############################################################################
### define constants
FOLDER_NAME = 'bot'
### initiate Gvar class
gvar = Gvar()
gvar.exchange = FOLDER_NAME # bot
gvar.domain = os.environ['USERDOMAIN'].lower() # 'desktop-pc' or 'note-pc'
gvar.folder_gmo = f'{gvar.domain}/{gvar.exchange}/' # 'desktop-pc/bot/'
gvar.callers_method_name = '_main_:'
gvar.coin_list = coin_list
### update Coin class properties
active_coin_list = []
for i, symbol in enumerate(symbol_list):
coin = coin_list[i]
coin.symbol = symbol
coin.suspend = suspend_list[i]
if not coin.suspend:
active_coin_list.append(coin)
coin.round_timestamp_freq = round_timestamp_list[i]
coin.master_csv_not_found = master_not_found_list[i]
coin.master_df = pd.DataFrame()
coin.master2_df = pd.DataFrame()
coin.real_mode = gvar.real_mode
coin.debug_mode = gvar.debug_mode
coin.fake_or_real = 'real' if gvar.real_mode else 'fake' # 'real' or 'fake'
coin.trade_type = trade_type_list[i] # 'buy_sell' or 'sell_buy'
coin.qty = qty_list[i]
coin.profit_rate = profit_rate_list[i]
coin.leverage_fee_rate = leverage_fee_list[i]
coin.stop_loss_rate = stop_loss_rate_list[i]
coin.price_decimal = 3 if coin.symbol == 'XRP_JPY' else 0
if coin.symbol in 'BTC_JPY' :
coin.qty_decimal = 2
elif coin.symbol in 'ETH_JPY,BCH_JPY':
coin.qty_decimal = 1
else: # 'LTC_JPY,XRP_JPY'
coin.qty_decimal = 0
############################################################################
# BuySell(), SellBuy() classes
############################################################################
### start Demo9
gvar.real_mode = False
gvar.reset_mode = True
gvar.debug_mode = True
gvar.stop_loss = True
gvar.callers_method_name = 'Demo9():'
debug = Debug(gvar)
coin = coin_list[0] # Coin('BTC_JPY')
api = Api(gvar, coin)
csv = Csv(gvar, coin)
trade = Trade(gvar, coin)
debug.print_log(f"{Bcolors.OKGREEN}Demo9 ({gvar.real_mode=}, {gvar.reset_mode=}, {gvar.stop_loss=}, {gvar.debug_mode=}) Started{Bcolors.ENDC}")
if gvar.reset_mode:
########################################################################
### 1: delete all csv files from buy_sell, sell_buy folder
########################################################################
# delete_file_driver() -> None:
csv.delete_file_driver()
########################################################################
### 2: load crypto data from GMO
########################################################################
gvar.callers_method_name = 'load_master_data():'
# load_master_driver(symbol_list: list, coin_list: list, page: int, count: int) -> None:
api.load_master_driver(symbol_list, coin_list, page=1, count=10)
#######################################################################
### 3: reset_restart_process() -> None:
#######################################################################
gvar.callers_method_name = 'reset_restart_process():'
for i, _ in enumerate(symbol_list):
coin = coin_list[i]
if not coin.suspend:
if gvar.reset_mode or coin.master_csv_not_found:
tradeBoth = BuySell(gvar, coin) if coin.trade_type == 'buy_sell' else SellBuy(gvar, coin)
tradeBoth.reset_restart_process()
# end of for i, _ in enumerate(symbol_list):
#######################################################
### 4: auto_trade()
#######################################################
i = 0
while True:
i += 1
for j, _ in enumerate(symbol_list):
# suspend coin ?
if coin_list[j].suspend: continue
### get or instantiate classes : Coin, Api, Csv, Trade, BuySell, SellBuy
coin = coin_list[j] # get coin class
api = Api(gvar, coin)
csv = Csv(gvar, coin)
trade = Trade(gvar, coin)
tradeBoth = BuySell(gvar, coin) if coin.trade_type == 'buy_sell' else SellBuy(gvar, coin)
auto_trade(i)
# end of for j, _ in enumerate(symbol_list):
### print monthly, weekly, daily profit
# print_profit_driver(symbol_list: list, coin_list: list) -> None:
trade.print_profit_driver(symbol_list, coin_list)
### print monthly, weekly, daily closed order count
# print_order_count_driver(symbol_list: list, coin_list: list) -> None:
trade.print_order_count_driver(symbol_list, coin_list)
### print loss cut count
# print_loss_cut_count_driver(symbol_list: list, coin_list: list) -> None:
trade.print_loss_cut_count_driver(symbol_list, coin_list)
break # <= comment out
# end of while True:
debug.print_log(f'{Bcolors.OKGREEN}Demo9 Ended{Bcolors.ENDC}')
図9-1は実行結果です。「BuySell」の注文が約定しています。
図9-2は実行結果です。
「BuySell」と「SellBuy」を22回繰り返した時点の損益、約定件数、ロスカットの件数が表示されています。
この画面では「BuySell」が1件約定しています。
-
BOTの各種クラスを使用して5種類の仮想通貨(BTC_JPY, ETH_JPY, BCH_JPY, LTC_JPY, XRP_JPY)を自動トレードしてみる
ここでは前出のデモプログラムを修正して5種類全ての仮想通貨を自動トレードするようにしています。
自動トレードは「buy_sell」と「sell_buy」の2種類行います。
行43では5種類の仮想通貨のシンボルをペアで定義します。
行45ではすべての仮想通貨に対して「False」を定義します。
行47では1~5までは「buy_sell」を、6~10までは「sell_buy」を定義します。
行157-168のforループでは全ての仮想通貨に対して「buy_sell」と「sell_buy」の注文を自動で行います。
もちろん無条件に注文を出すのではなく、一定のアルゴリズムに従って利大損小になるようにします。
無限ループさせるときは、行183をコメントアウトしてください。
demo10.py:
### Import the libraries
import os
import os.path
import time
from time import sleep
import datetime as dt
from datetime import timedelta
import numpy as np
import pandas as pd
import pandas_ta as pa
import matplotlib.pyplot as plt
from lib.base import Bcolors, Gvar, Coin, Gmo_dataframe
from lib.debug import Debug # dependencies Gvar
from lib.gmail import Gmail # dependencies Gvar, Debug, GmailConfig
from lib.gmail_config import GmailConfig
from lib.api import Api # dependencies Gvar, Coin
from lib.csv import Csv # dependencies Gvar, Coin
from lib.trade import Trade # dependencies Gvar, Coin
from lib.buy_sell import BuySell # dependencies Gvar, Coin
from lib.sell_buy import SellBuy # dependencies Gvar, Coin
import argparse
import warnings
warnings.simplefilter('ignore')
###############################
def auto_trade(i: int) -> None:
:::
return
################################################################################
### MAIN Demo [10] add all coins (buy_sell, sell_buy)
################################################################################
# -----------------------------------------------------------------------------------------------------------------------------------------------------------
# 1 2 3 4 5 6 7 8 9 10
# -----------------------------------------------------------------------------------------------------------------------------------------------------------
symbol_list = ['BTC_JPY', 'ETH_JPY', 'BCH_JPY', 'LTC_JPY', 'XRP_JPY', 'BTC_JPY', 'ETH_JPY', 'BCH_JPY', 'LTC_JPY', 'XRP_JPY'] # crypto symbol for leverage trade
round_timestamp_list = ['1S', '1T', '1T', '1T', '1T', '1S', '1T', '1T', '1T', '1T'] # gmo master freq: H-hour, T-minute, S-seconds, L-milliseconds
suspend_list = [False, False, False, False, False, False, False, False, False, False]
master_not_found_list = [False, False, False, False, False, False, False, False, False, False] # used to add coins
trade_type_list = ['buy_sell', 'buy_sell', 'buy_sell', 'buy_sell', 'buy_sell', 'sell_buy', 'sell_buy', 'sell_buy', 'sell_buy', 'sell_buy']
qty_list = [0.01, 0.1, 0.1, 1, 10, 0.01, 0.1, 0.1, 1, 10] # min qty
profit_rate_list = [1.0015, 1.0015, 1.0015, 1.0015, 1.0035, 1.0015, 1.0015, 1.0015, 1.0015, 1.0035]
leverage_fee_list = [0.0004, 0.0004, 0.0004, 0.0004, 0.0004, 0.0004, 0.0004, 0.0004, 0.0004, 0.0004]
stop_loss_rate_list = [0.0200, 0.0200, 0.0200, 0.0200, 0.0200, 0.0200, 0.0200, 0.0200, 0.0200, 0.0200]
coin_list = [Coin(), Coin(), Coin(), Coin(), Coin(), Coin(), Coin(), Coin(), Coin(), Coin()]
############################################################################
# instantiate gvar/coin class and initialize properties
############################################################################
### define constants
FOLDER_NAME = 'bot'
### initiate Gvar class
gvar = Gvar()
gvar.exchange = FOLDER_NAME # bot
gvar.domain = os.environ['USERDOMAIN'].lower() # 'desktop-pc' or 'note-pc'
gvar.folder_gmo = f'{gvar.domain}/{gvar.exchange}/' # 'desktop-pc/bot/'
gvar.callers_method_name = '_main_:'
gvar.coin_list = coin_list
### update Coin class properties
active_coin_list = []
for i, symbol in enumerate(symbol_list):
coin = coin_list[i]
coin.symbol = symbol
coin.suspend = suspend_list[i]
if not coin.suspend:
active_coin_list.append(coin)
coin.round_timestamp_freq = round_timestamp_list[i]
coin.master_csv_not_found = master_not_found_list[i]
coin.master_df = pd.DataFrame()
coin.master2_df = pd.DataFrame()
coin.real_mode = gvar.real_mode
coin.debug_mode = gvar.debug_mode
coin.fake_or_real = 'real' if gvar.real_mode else 'fake' # 'real' or 'fake'
coin.trade_type = trade_type_list[i] # 'buy_sell' or 'sell_buy'
coin.qty = qty_list[i]
coin.profit_rate = profit_rate_list[i]
coin.leverage_fee_rate = leverage_fee_list[i]
coin.stop_loss_rate = stop_loss_rate_list[i]
coin.price_decimal = 3 if coin.symbol == 'XRP_JPY' else 0
if coin.symbol in 'BTC_JPY' :
coin.qty_decimal = 2
elif coin.symbol in 'ETH_JPY,BCH_JPY':
coin.qty_decimal = 1
else: # 'LTC_JPY,XRP_JPY'
coin.qty_decimal = 0
############################################################################
# BuySell(), SellBuy() classes
############################################################################
### start Demo10
gvar.real_mode = False
gvar.reset_mode = True
gvar.debug_mode = True
gvar.stop_loss = True
gvar.callers_method_name = 'Demo10():'
debug = Debug(gvar)
coin = coin_list[0] # Coin('BTC_JPY')
api = Api(gvar, coin)
csv = Csv(gvar, coin)
trade = Trade(gvar, coin)
debug.print_log(f"{Bcolors.OKGREEN}Demo10 ({gvar.real_mode=}, {gvar.reset_mode=}, {gvar.stop_loss=}, {gvar.debug_mode=}) Started{Bcolors.ENDC}")
if gvar.reset_mode:
########################################################################
### 1: delete all csv files from buy_sell, sell_buy folder
########################################################################
# delete_file_driver() -> None:
csv.delete_file_driver()
########################################################################
### 2: load crypto data from GMO
########################################################################
gvar.callers_method_name = 'load_master_data():'
# load_master_driver(symbol_list: list, coin_list: list, page: int, count: int) -> None:
api.load_master_driver(symbol_list, coin_list, page=1, count=10)
#######################################################################
### 3: reset_restart_process() -> None:
#######################################################################
gvar.callers_method_name = 'reset_restart_process():'
for i, _ in enumerate(symbol_list):
coin = coin_list[i]
if not coin.suspend:
if gvar.reset_mode or coin.master_csv_not_found:
tradeBoth = BuySell(gvar, coin) if coin.trade_type == 'buy_sell' else SellBuy(gvar, coin)
tradeBoth.reset_restart_process()
# end of for i, _ in enumerate(symbol_list):
#######################################################
### 4: auto_trade()
#######################################################
i = 0
while True:
i += 1
for j, _ in enumerate(symbol_list):
# suspend coin ?
if coin_list[j].suspend: continue
### get or instantiate classes : Coin, Api, Csv, Trade, BuySell, SellBuy
coin = coin_list[j] # get coin class
api = Api(gvar, coin)
csv = Csv(gvar, coin)
trade = Trade(gvar, coin)
tradeBoth = BuySell(gvar, coin) if coin.trade_type == 'buy_sell' else SellBuy(gvar, coin)
auto_trade(i)
# end of for j, _ in enumerate(symbol_list):
### print monthly, weekly, daily profit
# print_profit_driver(symbol_list: list, coin_list: list) -> None:
trade.print_profit_driver(symbol_list, coin_list)
### print monthly, weekly, daily closed order count
# print_order_count_driver(symbol_list: list, coin_list: list) -> None:
trade.print_order_count_driver(symbol_list, coin_list)
### print loss cut count
# print_loss_cut_count_driver(symbol_list: list, coin_list: list) -> None:
trade.print_loss_cut_count_driver(symbol_list, coin_list)
break # <= comment out
# end of while True:
debug.print_log(f'{Bcolors.OKGREEN}Demo10 Ended{Bcolors.ENDC}')
図10-1は実行結果です。
これは自動トレードを11回繰り返した時点の画像です。
合計12件が約定しています。
「BTC_JPY(buy_sell)」と「LTC_JPY(sell_buy)」がともに3件でトップとなっています。
このデモでは注文時の数量を最小値にしているので利益の金額は無視してください。
画面から「SellBuy(空売り▶買戻し)」の注文が多く約定しているのがわかります。
ちなみに当日は仮想通貨が暴落したときでした。
この画面からも分かるようにレバレッジ取引は空売りの注文ができるので、
相場が上がっても下がっても利益を出すことができます。
図10-2は仮想通貨(BCH_JPY)の「BuySell」の取引の損益をExcelで開いた画像です。
図10-1の利益額(29円)と一致しています。
注文数が最小値なので金額の大小は無視してください。
図10-3は仮想通貨(LTC_JPY)の「SellBuy」の取引の損益をExcelで開いた画像です。
図10-1の利益額(132円)と一致しています。
注文数が最小値なので金額の大小は無視してください。