FMZ
이 참조 계정 및 동기화 계정을 관리하는 하나의 전략에서 순서 및 위치 동기화를 달성합니다. 그리고 오늘 우리는 다른 디자인을 시도 할 것입니다. 우리는 FMZ 양자 거래 플랫폼의 강력한 확장 API 인터페이스를 기반으로 주문 동기화 관리 시스템을 설계 할 것입니다.
먼저, 우리는 몇 가지 좋은 제안과 필요를 필요로 합니다. 위의 두 가지 이전 순서와 위치 동기화 전략, 우리는 함께 논의 할 몇 가지 명백한 결함이 있습니다.
해결책:
FMZOrder Synchronous Server
실제 봇에서 전략). 그러면 그냥 FMZ 확장 API 키를 제공 (이 교환 계정의 API 키가 아니라는 점에 유의) 및 주문 동기 서버 실제 봇 ID 참조 계정 소유자 (명령 리더).
레퍼런스 계정 소유자 (오더 추종자) 가 실제 봇 (사용자) 이면Order Synchronization Management System Class Library (Single Server)
이 문서에서 설계된 시스템에서) 신호를 보내면 동기화 계정 소유자의 실제 봇은 거래 신호를 수신하고 자동으로 다음 명령을합니다.
Order Synchronization Management System Class Library (Single Server)
이 문서에서 설계된 시스템에서 전략), 그래서 참조 계정 소유자 (질서 리더) 는 순서와 위치 동기화 기능을 달성하기 위해 자신의 전략에 직접 이 템플릿 클래스 라이브러리를 삽입 할 수 있습니다.이 시스템은 두 부분으로 구성되어 있습니다.
일단 우리의 필요를 정의하면, 디자인을 시작합시다!
참고로 이것은 전략이 아닙니다. 그것은 FMZ의 템플릿 클래스 라이브러리입니다. 템플릿 클래스 라이브러리의 개념은 FMZ API 문서에서 검색 할 수 있으며 다시 반복하지 않을 것입니다.
템플릿 클래스 라이브러리 코드:
// Global variables
var keyName_label = "label"
var keyName_robotId = "robotId"
var keyName_extendAccessKey = "extendAccessKey"
var keyName_extendSecretKey = "extendSecretKey"
var fmzExtendApis = parseConfigs([config1, config2, config3, config4, config5])
var mapInitRefPosAmount = {}
function parseConfigs(configs) {
var arr = []
_.each(configs, function(config) {
if (config == "") {
return
}
var strArr = config.split(",")
if (strArr.length != 4) {
throw "configs error!"
}
var obj = {}
obj[keyName_label] = strArr[0]
obj[keyName_robotId] = strArr[1]
obj[keyName_extendAccessKey] = strArr[2]
obj[keyName_extendSecretKey] = strArr[3]
arr.push(obj)
})
return arr
}
function getPosAmount(pos, ct) {
var longPosAmount = 0
var shortPosAmount = 0
_.each(pos, function(ele) {
if (ele.ContractType == ct && ele.Type == PD_LONG) {
longPosAmount = ele.Amount
} else if (ele.ContractType == ct && ele.Type == PD_SHORT) {
shortPosAmount = ele.Amount
}
})
var timestamp = new Date().getTime()
return {ts: timestamp, long: longPosAmount, short: shortPosAmount}
}
function sendCommandRobotMsg (robotId, accessKey, secretKey, msg) {
// https://www.fmz.com/api/v1?access_key=xxx&secret_key=yyyy&method=CommandRobot&args=[186515,"ok12345"]
var url = "https://www.fmz.com/api/v1?access_key=" + accessKey + "&secret_key=" + secretKey + "&method=CommandRobot&args=[" + robotId + ',"' + msg + '"]'
Log(url)
var ret = HttpQuery(url)
return ret
}
function follow(nowPosAmount, symbol, ct, type, delta) {
var msg = ""
var nowAmount = type == PD_LONG ? nowPosAmount.long : nowPosAmount.short
if (delta > 0) {
// open the position
var tradeDirection = type == PD_LONG ? "buy" : "sell"
// send signals
msg = symbol + "," + ct + "," + tradeDirection + "," + Math.abs(delta)
} else if (delta < 0) {
// close the position
var tradeDirection = type == PD_LONG ? "closebuy" : "closesell"
if (nowAmount <= 0) {
Log("no positions found")
return
}
// send signals
msg = symbol + "," + ct + "," + tradeDirection + "," + Math.abs(delta)
} else {
throw "error"
}
if (msg) {
_.each(fmzExtendApis, function(extendApiConfig) {
var ret = sendCommandRobotMsg(extendApiConfig[keyName_robotId], extendApiConfig[keyName_extendAccessKey], extendApiConfig[keyName_extendSecretKey], msg)
Log("call the CommandRobot interface, ", "label:", extendApiConfig[keyName_label], ", msg:", msg, ", ret:", ret)
Sleep(1000)
})
}
}
$.PosMonitor = function(exIndex, symbol, ct) {
var ts = new Date().getTime()
var ex = exchanges[exIndex]
// judge the type of ex
var exName = ex.GetName()
var isFutures = exName.includes("Futures_")
var exType = isFutures ? "futures" : "spot"
if (!isFutures) {
throw "only future-following is supported"
}
if (exType == "futures") {
// caching symbol ct
var buffSymbol = ex.GetCurrency()
var buffCt = ex.GetContractType()
// switch to the corresponding contract pair, contract code
ex.SetCurrency(symbol)
if (!ex.SetContractType(ct)) {
throw "SetContractType failed"
}
// monitor positions
var keyInitRefPosAmount = "refPos-" + exIndex + "-" + symbol + "-" + ct // refPos-exIndex-symbol-contractType
var initRefPosAmount = mapInitRefPosAmount[keyInitRefPosAmount]
if (!initRefPosAmount) {
// no initialization data, initialize it
mapInitRefPosAmount[keyInitRefPosAmount] = getPosAmount(_C(ex.GetPosition), ct)
initRefPosAmount = mapInitRefPosAmount[keyInitRefPosAmount]
}
// monitor
var nowRefPosAmount = getPosAmount(_C(ex.GetPosition), ct)
// calculate the position changes
var longPosDelta = nowRefPosAmount.long - initRefPosAmount.long
var shortPosDelta = nowRefPosAmount.short - initRefPosAmount.short
// detect changes
if (!(longPosDelta == 0 && shortPosDelta == 0)) {
// Perform long positions
if (longPosDelta != 0) {
Log(ex.GetName(), ex.GetLabel(), symbol, ct, "Perform long position-following, changes in volume:", longPosDelta)
follow(nowRefPosAmount, symbol, ct, PD_LONG, longPosDelta)
}
// Perform short positions
if (shortPosDelta != 0) {
Log(ex.GetName(), ex.GetLabel(), symbol, ct, "Perform short position-following, changes in volume:", shortPosDelta)
follow(nowRefPosAmount, symbol, ct, PD_SHORT, shortPosDelta)
}
// Update after performing the order-following operation
mapInitRefPosAmount[keyInitRefPosAmount] = nowRefPosAmount
}
// restore symbol ct
ex.SetCurrency(buffSymbol)
ex.SetContractType(buffCt)
} else if (exType == "spot") {
// Spots
}
}
$.getTbl = function() {
var tbl = {
"type" : "table",
"title" : "synchronization of data",
"cols" : [],
"rows" : []
}
// construct the table headers
tbl.cols.push("monitor the account: refPos-exIndex-symbol-contractType")
tbl.cols.push(`monitor the position: {"timestamp":xxx,"long positions":xxx,"short positions":xxx}`)
_.each(fmzExtendApis, function(extendApiData, index) {
tbl.cols.push(keyName_robotId + "-" + index)
})
// Write data in
_.each(mapInitRefPosAmount, function(initRefPosAmount, key) {
var arr = [key, JSON.stringify(initRefPosAmount)]
_.each(fmzExtendApis, function(extendApiData) {
arr.push(extendApiData[keyName_robotId])
})
tbl.rows.push(arr)
})
return tbl
}
// Example of the strategy call that references the template class library
function main() {
// Clear all logs
LogReset(1)
// Switch to OKEX demo to test
exchanges[0].IO("simulate", true)
// Set the contract
exchanges[0].SetCurrency("ETH_USDT")
exchanges[0].SetContractType("swap")
// Timed trading interval
var tradeInterval = 1000 * 60 * 3 // Trade for every three minutes to observe the order-following signals
var lastTradeTS = new Date().getTime()
while (true) {
// Other logic of the strategy...
// Simulated trading triggers for testing
var ts = new Date().getTime()
if (ts - lastTradeTS > tradeInterval) {
Log("Trade the simulation order-leading strategies, position changes", "#FF0000")
exchanges[0].SetDirection("buy")
exchanges[0].Buy(-1, 1)
lastTradeTS = ts
}
// Interface functions that use templates
$.PosMonitor(0, "ETH_USDT", "swap") // Multiple monitors can be set up to monitor different exchange objects on the order-following strategy
var tbl = $.getTbl()
// Display status bar
LogStatus(_D(), "\n" + "`" + JSON.stringify(tbl) + "`")
Sleep(1000)
}
}
디자인은 매우 간단합니다, 클래스 라이브러리는 2 가지 기능이 있습니다. FMZ 플랫폼의 프로그래밍 거래 전략이 템플릿 클래스 라이브러리를 참조하면Order Synchronization Management System Class Library (Single Server)
그러면 전략은 다음 함수를 사용할 수 있습니다.
$. 포스 모니터 이 함수의 목적은 전략에서 교환 객체의 위치 변화를 모니터링하고 다음 템플릿의 매개 변수에서 설정된 실제 봇 시장에 거래 신호를 전송하는 것입니다: 주문 동기화 관리 시스템 클래스 라이브러리 (Single Server).
$.getTbl 감시된 동기화 데이터로 돌아가
사용 예는main
주문 동기화 관리 시스템 클래스 라이브러리 (단독 서버) 템플릿의 함수:
// Example of the strategy call that references the template class library
function main() {
// Clear all logs
LogReset(1)
// Switch to OKEX demo to test
exchanges[0].IO("simulate", true)
// Set the contract
exchanges[0].SetCurrency("ETH_USDT")
exchanges[0].SetContractType("swap")
// Timed trading interval
var tradeInterval = 1000 * 60 * 3 // Trade for every three minutes to observe the order-following signals
var lastTradeTS = new Date().getTime()
while (true) {
// Other logic of the strategy...
// Simulated trading triggers for testing
var ts = new Date().getTime()
if (ts - lastTradeTS > tradeInterval) {
Log("Trade the simulation order-leading strategies, position changes", "#FF0000")
exchanges[0].SetDirection("buy")
exchanges[0].Buy(-1, 1)
lastTradeTS = ts
}
// Interface functions by using templates
$.PosMonitor(0, "ETH_USDT", "swap") // Multiple monitors can be set up to monitor different exchange objects on the order-following strategy
var tbl = $.getTbl()
// Display status bar
LogStatus(_D(), "\n" + "`" + JSON.stringify(tbl) + "`")
Sleep(1000)
}
}
템플릿 클래스 라이브러리 또한 자체적으로 전략 리얼 봇을 만들 수 있습니다. 일반적으로 템플릿 클래스 라이브러리를 테스트하는 데 사용됩니다.main
템플릿의 함수는main
자신의 전략 중 하나에 대한 기능입니다.
테스트 코드는 테스트를 위해 OKEX 데모를 사용하여 작성되었습니다. FMZ에서 OKEX 데모 API 키를 참조 계정 (오더 리딩) 으로 구성해야하며 주요 기능에서 데모로 전환됩니다. 그 다음 거래 쌍을 ETH_USDT로 설정하고 계약을 교환하도록 설정합니다. 그 다음 while 루프에 입력합니다. 루프에서 전략 거래의 트리거를 시뮬레이션하기 위해 3 분마다 주문이 배치됩니다.$.PosMonitor(0, "ETH_USDT", "swap")
이 함수의 첫 번째 매개 변수는 0으로 전달됩니다. 이것은 교환 객체 교환을 모니터링하는 것을 의미합니다[0], ETH_USDT 거래 쌍, 교환 계약을 모니터링합니다.$.getTbl()
그래프 정보를 얻기 위해,LogStatus(_D(), "\n" + "`" + JSON.stringify(tbl) + "`")
상태 표시줄에 표시되는 차트 데이터를 만들기 위해서입니다.
그래서 우리는 전략이 특정 종의 위치를 모니터링 할 수 있는 능력을 가지고 있다는 것을 볼 수 있습니다. 그리고 위치를 변경하여 메시지를 전송하는 방법을 사용할 수 있습니다.$.PosMonitor(0, "ETH_USDT", "swap")
이 계열에 해당하는 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 모든 계열에 해당하는 계열에 해당하는 모든 계열에 해당하는 계열에 해당하는 모든 계열에 해당하는 계열에 해당하는 계열에 해당하는 모든 계열에 해당하는 계열에 해당하는 계열에
테스트 전에, 우리는 전략 매개 변수 디자인을 설명합니다Order Synchronization Management System Class Library (Single Server)
- 그래요
우리는 방금 어떻게 템플릿의 인터페이스 함수를 사용하여 전략을 업그레이드 하 고 순서 선도 함수를 가지고 이야기 했습니다. 위치 변경 때 전송 된 신호에 대해 어떻게, 누가 전송 될 것입니다?
누가 보내야 하는지에 대한 질문은Order Synchronization Management System Class Library (Single Server)
.
우리는 5 매개 변수가 있다고 볼 수 있습니다, 최대 5 푸시를 지원 (이 증가해야하는 경우 자체로 확장 될 수 있습니다), 기본 매개 변수는 빈 문자열, 즉, 처리되지 않습니다. 구성 문자열 형식: 라벨,로봇Id,accessKey,secretKey
라벨 동기화 계정에 대한 라벨, 원하는 이름으로 계정에 대한 라벨을 설정하는 데 사용됩니다.
로봇
로봇 ID,Order Synchronous Server
동시 계정 소유자가 만든 실제 봇입니다.
accessKey 확장된 API 액세스 FMZ 키
비밀 키 FMZ의 확장된 API 비밀 키
주문 동기화 관리 시스템 (동시 서버) 의 임시 코드:
function main() {
LogReset(1)
while (true) {
var cmd = GetCommand()
if (cmd) {
// cmd: ETH_USDT,swap,buy,1
Log("cmd: ", cmd)
}
Sleep(1000)
}
}
우리는 동기화 된 계정 소유자의 실제 봇이 메시지를 받았다는 것을 볼 수 있습니다:ETH_USDT,swap,buy,1
- 그래요
다음 단계에서는 트레이딩 쌍, 계약 코드, 거래 방향 및 정보의 양에 따라 자동 주문을 수행 할 수 있습니다.
현재까지,Order Synchronization Management System (Synchronous Server)
임시 코드입니다. 우리는 다음 주에서 그 디자인을 계속 탐구할 것입니다.