前情提要
在自動交易的上集中,我們完成了永豐和FinLab相關的前置作頁,包括申請交易憑證、打包策略程式碼、加入下單模組。
在本篇文章中,我們會將這些東西上傳到GCP以完成Cloud Function部署,最後用Cloud Scheduler定期呼叫Cloud Function,這樣一切就大功告成了!
流程圖
附上流程圖幫大家複習一下,如果沒有看過上集的同學,記得先回去補課喔!
免責聲明
FinLab於此文章中所提供的程式碼僅供參考,會隨著套件版本更動、硬體設備之故障、失效或人為上之疏失導致,導致下單狀況不如交易者之預期。使用者在使用此文章之程式碼前,務必自行審慎評估,並自負投資風險及盈虧。如使用FinLab所提供之程式碼致生損失,本公司不負擔任何賠償及法律責任。
Google Cloud Platform (GCP)
Google Cloud Platform是Google的雲端平台,有著一系列由Google提供的雲端運算服務。
我們這次會使用到其中三個雲端服務:
- Cloud Storage:雲端的儲存空間,用來存放永豐的交易憑證
- Cloud Function:雲端執行FinLab選股策略和下單程式碼。
- Cloud Sceduler:雲端排程工具,定期執行部署的Cloud Function。
GCP 要收費嗎?
新用戶前三個月會贈送300美元的抵免額,對佈署自動交易程式來說足夠了。三個月過後,當你確認要付費繼續使用時,才會開始扣款。
依照目前 Cloud Function 的定價,試用期過後,每個月大約是1元台幣,詳細計算方式如下:
- 不論是否是試用期,Cloud Function 呼叫200萬次以內,都是免費的。即便每天執行10次,一個月也才300次,並不會達到收費門檻。
- 在文章中,會看到用 https 也就是網頁的方式,來呼叫 cloud function,這個部分,假如是 5GB 以內,也會是免費的,假設所產生的網頁以 500kb 來計算,每月要執行 200 萬次才會達到門檻。
- 由於我們上傳 google cloud function,會有存放系統的成本,所以每個月會酌收0.026美金,大約是 1 元台幣。
有疑問的同學可以到 Google cloud function 的定價來查看更詳細的定價,接下來就讓我們開始吧!
註冊帳號
首先到GCP的官網註冊一個帳號,註冊表單按照自己的狀況填即可。
辦好帳號後進入控制台,就可以在左邊找到Cloud Function 跟 Cloud Storage,建議把他們釘選到最上方,這樣在之後的使用會比較方便。
新增專案
大家可以自由地設定專案名稱,但建議專案ID跟專案名稱一致。
這樣就建立好專案囉,接下來請大家進入到新增好的專案中,之後的操作都會在此專案中進行。
上傳交易憑證
首先進入Cloud Storage的頁面如下,點選建立。
值區名稱可以自行設定,我這邊設定為trading_pass。
創建好後,進入資料夾中,將先前辦好的交易憑證檔案上傳。
部署 Cloud Function
啟用API
到Cloud Function的頁面,點選建立函式,並按照提示啟用API。
基本設定
環境選第一代、函式名稱可自定義、地區選台灣。
觸發條件設定
記憶體和時間配置設定
記憶體和時間的部分,個人習慣先配置到最大。等確定佈署成功之後,再自行調整縮小到適合的大小。
環境變數設定
環境變數的有四個值要改成自己的,作為登入永豐和FinLab驗證用。
剩餘兩個路徑變數則按照範例輸入即可,是為了因應Cloud Function規定存取和讀取都需要在/tmp目錄下面所做的特別設定。
程式碼初始設定
設定完成後進到程式碼頁面,會有一支預設程式碼和package檔。
將檔案全部刪掉,並把執行階段改為自己的Python版本,進入點改為main,並新增五個空的檔案,檔名如下圖。
接下來我會對每個檔案說明其作用,並附上程式碼。
run_strategy.py
將我們上面打包好的function,引入環境變數中的FinLab token,將FinLab登入的動作也寫在code裡面。
import finlab
import os
finlab.login(os.environ["FINLAB_API_TOKEN"])
from finlab.backtest import sim
from finlab import data
def run_strategy(): #將程式碼包裝成function,並回傳report這個物件(下單會用到)
close = data.get("price:收盤價")
position = (close == close.rolling(250).max())
report = sim(position, resample="M", name="創年新高策略",upload=False)
return report
make_order.py
首先請大家先看過FinLab官方文檔,會比較能理解下方的程式碼。
make_order有兩個輸入變數,一個是sim 所產生的report物件,另一個是這個策略的資金量,也就是你預計要拿多少錢來跑這個策略。
最後make_order會回傳一個dict物件,key是下單的股票代號、value則是股數,在測試的時候會比較方便確認下單是否正確。
如果不瞭解也沒關係,可以複製程式碼,再更改要投入的資金即可。
import os
os.chdir("/tmp") #轉到Cloud Function限定的tmp資料夾下面執行
from finlab.online.order_executor import Position
from finlab.online.sinopac_account import SinopacAccount
from finlab.online.order_executor import OrderExecutor
def make_order(report,fund=100000): #預設用100,000的資金跑策略
position = Position.from_report(report, fund)
acc = SinopacAccount()
order_executer = OrderExecutor(position , account=acc)
# 用模擬模式產生下單的明細並回傳,之後會輸出在網頁上 (optional)
record = order_executer.create_orders(view_only=True)
key_list = [f'order{i}:' for i in range(1,len(record)+1)]
value_list = [{i['stock_id']:i['quantity']} for i in record]
# 實際下單(會真的下單,初次使用建議收市時測試)
order_executer.create_orders(market_order=True) #用市價單(要注意滑價,可自行修改)
return dict(zip(key_list, value_list))
bucket.py
先前說過,Cloud Function規定資料的讀寫必須在/tmp目錄之下。
connect_storage的用處是將先前上傳到Cloud Storage的交易憑證,下載至/tmp的目錄下,讓Cloud Function能夠順利讀取,進而登入永豐的交易帳戶。
如果不瞭解可以直接複製程式碼即可。
from google.cloud import storage
def connect_storage():
storage_client = storage.Client()
bucket = storage_client.bucket('trading_pass')
model_filename = "Sinopac.pfx"
blob = bucket.blob(model_filename)
blob.download_to_filename('/tmp/Sinopac.pfx')
return
main.py
main.py裡面的main函式,是Cloud Function執行時的進入點,也就是真正Cloud Function真正執行的函式。
因此我們import了我們上述寫的三份程式碼檔案,在此一一呼叫,先將憑證移到/tmp目錄下,執行FinLab策略,最後執行永豐的下單程式。
from run_strategy import run_strategy
from make_order import make_order
from bucket import connect_storage
def main(request): #request要記得寫,這是Cloud Function 規定的格式
connect_storage() # 將交易憑證移到/tmp目錄下
report = run_strategy() #執行FinLab策略,回傳report物件
record = make_order(report,100000) #用十萬塊下單,回傳下單結果的名細
return record
requirements.txt
requirements.txt負責告訴GCP這支Cloud Function需要使用到哪些套件、哪些版本。以下是必定會使用到的套件,版本則可能因人而異,建議選取與本地端相同的版本,避免套件不同版本之間的相容性問題。若不特別標註版本號,則會自動採用該套件的最新版本。
大家在撰寫策略時,若有用到其他的套件(ex: pandas),都要記得自己再加上去喔!
# Function dependencies, for example:
# package==version
# 本篇示範皆使用當前最新版本,讀者可自行指定需固定之版本
finlab
shioaji==0.5.0.dev2 #(2023/2/6編輯)因應永豐API調整,請先暫定此版本
google-cloud-storage
如果不知道自己使用的套件版本,可以在jupyter執行以下程式碼。
# 假設你不知道自己使用的shioaji套件版本
import shioaji
print(shioaji.__version__) #印出套件的版本
# 輸出: 0.3.6.dev2 => 這就是你的shioaji套件版本
上傳Cloud Function
一切設定好後,點擊左下角的部署。若部署失敗,可以到logging的頁面,查看error為何,做進一步的修正後,再重新部署即可。
權限說明
成功部署Cloud Function後,到權限分頁點選新增,並設定讓所有使用者都可以呼叫此Cloud Function,以便後續Cloud Scheduler的調用。
Cloud Function測試
觸發條件頁面中,有一個觸發網址,點選它的時候就等同於執行該Cloud Function,也就是下單的動作!因此這個網址切記不要外洩,如果是淘汰或暫時不打算執行的策略,也記得要先下架。
還是會擔心的同學,GCP也有限制使用權限的方法,可以自行Google!
當你點選網址之後,順利的話會出現一個網頁(需要跑一陣子),網頁會顯示下單的明細,方便大家確認下的單是否正確。
備註:用Firefox的瀏覽器來看會比較清楚喔!
譬如以下就是做了三筆交易,分別買進了一張00864B、賣出一張1713、賣出兩張2832。
如果到永豐查看的話會類似下圖,但實際買賣的股票、張數會隨策略和資金的不同而改變,大家只需注意API下的單是否與策略相同即可。
提醒大家在測試的時候,記得要挑收盤的時候,測試完也要記得把委託單給刪掉,不然隔天真的成交就麻煩了XD
設定 Cloud Scheduler
恭喜大家來到最後一步!搜尋Cloud Scheduler,並點選建立工作。
定義排程的部分,名稱可自行設定,要注意的是執行頻率,像我是習慣開盤前(平日早上8:30)執行我的策略,如果想要自行設定其他時間點執行的話,可以參考這個網站將頻率轉換成Unix-Cron格式。
備註:建議於晚上7點之後執行,才能獲取最新的資料
設定執行作業時,需填入的網址就是前面Cloud Function的觸發網址。
測試Cloud Scheduler是否正常,點選強制執行,並到永豐帳戶中查看是否有順利下單。
Colab 版本下單
若在雲端部署上遇到困難,歡迎到Discord詢問我們,另外我們也提供了Colab下單腳本給大家,歡迎大家依照自己的需求選擇!
溫馨提醒
成功部署後,也要定期觀察下單狀況是否如你所預期,尤其是剛開始使用的時候,以免程式出了BUG,導致賠錢或被追繳的後果。
總結
恭喜執行到這裡的大家,已經完成所有的步驟,往後每天GCP都會自動幫大家執行選股策略並且進行下單了!
祝大家一切順利,天天在家睏飽數錢,有任何問題也歡迎在文章下方或到FinLab粉專留言!
這次自動交易的教學就告一段落了。我是阿榤,下次見,掰!(⁎⁍̴̛ᴗ⁍̴̛⁎)
(2023/4/6 更新) Shioaji Version >= 1.0 環境變數設定
因應永豐更新主要版本至1.0,採用了全新驗證方式。若要使用1.0以後的版本,請先到永豐官網申請API,將權限設置如下。
請將環境變數的設置改為以下