The aim of this repository is to interact with FTX APIs to book orders (spot,future etc) and get market price.
Currently, this repository is mainly used for below cloud functions:
- conversion_request_place_order_api
- UpdatePriceHistory
- purge_old_market_price
-
This function place future order in
BYBITexchange and for stable coin (eg:USDC,USDT) additionally books spot order inFTXexchange. -
This function is triggered when user makes a conversion request from front end and a corresponding document is added by another backend cloud function
conversion_requestto firestore tableconvert_history\{uid}\history\{assetType} -
When a document is inserted into above firestore table, this function is auto triggered and an order is placed in bybit( and ftx) using external apis.
-
On successful creation of order, a sub-document is inserted under sub-collection
orderwith order details returned from bybit (and ftx). eg:convert_history\{uid}\history\{assetType}\order\{id}\<details of order> -
On failure, a subdocument is inserted under sub-scollection
orderwith error details returned from bybit (and ftx). eg:convert_history\{uid}\history\{assetType}\order\{id}\<error message> -
After order book request is done, the final
statusof firestore document is updated frompendingtosentorerror. eg:convert_history\{uid}\history\{assetType}\<{status = 'sent' or 'error'}> -
There is pub/sub function
conversion_batchwhich is auto triggered by scheduler jobconvert_triggerand is scheduled to run daily around 9.10 AM JST. The pub/sub function looks for all the documents of this table having statussentand do the conversion fromXYZtoUSDSorUSDStoXYZand finally marks the document status fromsenttodone
-
This function currently used
FTXapi exchange as its default. -
This cloud function is a pub/sub function which is auto triggered by schedule job
update_market_price_triggerand is schedule to run after each minute. -
When this function is triggered, it gets the prices of all target markets configured in runtime enviornment variable
TARGET_MARKETS(eg; BTC-PERP|ETH-PERP) usingFTXapi and save the price in a new document of tableprice_histories. -
This pre save/added price is used by front end conversion form/window for a given currency pair (eg: BTC-USD).
-
This cloud function is a pub/sub function which is auto triggered by schedule job
purge_old_market_price_triggerand is schedule to run once daily at 2 AM JST time. -
This function auto purges/deletes all the old documents (older than 3 days) from
price_historiestable to avoid any future performance issue because of big size of table.
-
All API specific secrets have been added/uploaded to secret manager.
-
Because above cloud functions run under default service account
App Engine default service account, all secret keys must be created under same account, otherwise you will have to grantSecret Manager Secret Accessorrole to another account -
Below are the scret keys currently used:
BYBIT_IS_TESTNET:Truefor non-production,Falsefor production.BYBIT_API_KEYBYBIT_API_SECRETFTX_API_KEYFTX_API_SECRETFTX_SUB_ACCOUNT
-
Notes:
-
for
conversion_request_place_order_apifunction, if you plan to change Bybit's API KEYS, you need to set static ip address used by cloud function in your api keys management. (refer below section for more details) -
UpdatePriceHistoryfunction always usesFTXexchange. (No static ip address is required)
-
-
conversion_request_place_order_apino enviornment variables: -
UpdatePriceHistoryandpurge_old_market_price_triggeruse below enviornment variables:TARGET_MARKET: Current production setting isBTC-PERP|ETH-PERP
-
This setup/configuration is required only for
conversion_request_place_order_apifunction. The reason is, this function uses Bybit exchange which allows requests only from explicitly specified IP addresses and should be configured in Bybit API Key(s) in their portal. For FTX, there is no static ip required. -
As cloud function is a stateless service and doesn't have a static ip address. The idea is, first to route egress traffic from cloud function to VPC (Virtual private network) through VPC connector to adhere all the rules set on this VPC network and then setup Cloud NAT gateway with static ip address to give access to the function to connect to internet.
-
More details and explained steps can be found here: https://cloud.google.com/functions/docs/networking/network-settings#associate-static-ip
-
Below are the steps to follow:
- Route function's egress through VPC network
- Setup a VPC network
- This step can be omitted as we will be using soteria's
defaultVPC network.
- This step can be omitted as we will be using soteria's
- Set up a Serverless VPC Access connector
- In google cloud, go to
Serverless VPC access - Enable
Serverless VPC Access API(if not enabled before) - Click on
CREATE CONNECTOR- Name =
soteria-connector - Region =
us-central1(or anything) - Network =
default(choose VPC network of that region, let it be default) - Subnet = Select
Custom IP rangeand in IP range enter10.8.0.0
- Name =
- Let other values to be defaulted one and click on
CREATE
- In google cloud, go to
- Set up Cloud NAT and specify a static IP address
- In google cloud, go to
Cloud NAT - Click on
CREATE NAT GATEWAY - Name =
soteria-gateway - VPC network=
default - Region =
us-central1(use same selected at the time of connector creation) - Cloud router = create a new router with name
soteria-router - NAT Mapping/Source Internal = let
Primary and secondary ranges for all subnetsas default - NAT Mapping/NAT IP Address =
Manual(Click on IP address, it will allow you to create a new static IP address, give the nameapi-static-ip) - Finally click on
CREATE
- In google cloud, go to
- Setup a VPC network
- Route function's egress through VPC network
-
The static ip address created in last step has to be configured in Bybit API key. (Go to bybit portal and then
APIsection and modify your key to add this ip address)
Make sure you have checked all steps mentioned in Configuration/Setup section.
Set the project enviornment
gcloud auth login
gcloud config set project <project name of the environment you want to deploy to>
# Existing function
gcloud functions deploy conversion_request_place_order_api
# New function
gcloud functions deploy conversion_request_place_order_api --entry-point=place_order_api --runtime=python37 --trigger-event=providers/cloud.firestore/eventTypes/document.create --trigger-resource=projects/{project_id}/databases/(default)/documents/convert_history/{uid}/history/{assetType} --vpc-connector=soteria-connector --egress-settings=all
# Note:
## Replace {project_id} with stagging/production project id
## Make sure vpc-connector is created already.# Existing function
gcloud functions deploy UpdatePriceHistory
# New function
gcloud functions deploy UpdatePriceHistory --entry-point=update_market_price --runtime=python37 --trigger-topic=update_market_price_topic --set-env-vars=TARGET_MARKETS="BTC-PERP|ETH-PERP"
# Note: Make sure topic and scheduler exists already# Existing function
gcloud functions deploy purge_old_market_price
# New function
gcloud functions deploy purge_old_market_price --entry-point=purge_old_market_price --runtime=python37 --trigger-topic=purge_old_market_price_topic --set-env-vars=TARGET_MARKETS="BTC-PERP|ETH-PERP" --timeout=540s
# Note: Make sure topic and scheduler exists already