TradingViewWebHook Прямая ссылка

Автор:Маленькие мечты, Дата: 2020-08-03 09:58:19
Тэги:

Ссылки:https://www.fmz.com/bbs-topic/5969

Поскольку HTTPServer сам по себе имеет свои недостатки, подумайте об использовании ThreadingHTTPServer вместо него. Ссылки:https://docs.python.org/3.7/library/http.server.htmlДля этого требуется версия Python 3.7.

Опыт работы с HTTPServer:https://www.zybuluo.com/JunQiu/note/1350528


'''
请求格式:http://x.x.x.x:xxxx/data?access_key=xxx&secret_key=yyy&type=buy&amount=0.001
策略机器人参数:
- 类型:加密字符串,AccessKey , SecretKey ,可以用FMZ平台的低权限的API KEY,或者自己生成KEY也可以。
- 类型:字符串,合约ID,ContractType
- 类型:数值,端口号,Port
'''

import re
import _thread
import json
from http.server import ThreadingHTTPServer, BaseHTTPRequestHandler
from urllib.parse import parse_qs, urlparse

def url2Dict(url):
    query = urlparse(url).query  
    params = parse_qs(query)  
    result = {key: params[key][0] for key in params}  
    return result

class Executor(BaseHTTPRequestHandler):
    def do_GET(self):
        try:
            dictParam = url2Dict(self.path)
            Log("测试", dictParam)
        except Exception as e:
            Log("Provider do_GET error, e:", e)
    def do_POST(self):
        try:
            self.send_response(200)
            self.send_header("Content-type", "application/json")
            self.end_headers()
            dictParam = url2Dict(self.path)
            
            # 测试POST请求Body信息            
            data = self.rfile.read(200)   # 指定了读取长度
            Log("data:", data)            # 打印POST请求的数据,可以根据请求中的数据具体再让机器人执行对应的操作
            
            # 校验
            if len(dictParam) == 4 and dictParam["access_key"] == AccessKey and dictParam["secret_key"] == SecretKey:
                del dictParam["access_key"]
                del dictParam["secret_key"]
                Log("接收到请求", "参数:", dictParam, "#FF0000")
                '''
                map[access_key:xxx amount:0.001 secret_key:yyy type:buy]
                '''
                isSpot = True
                if exchange.GetName().find("Futures") != -1:
                    if ContractType != "":
                        exchange.SetContractType(ContractType)
                        isSpot = False 
                    else :
                        raise "未设置期货合约"
                                
                q = None
                if exchange.GetName() == "Futures_CTP" and UseMarketOrderForCTP == False:
                    q = ext.NewTaskQueue()
                
                if isSpot and dictParam["type"] == "buy":
                    exchange.Buy(-1, float(dictParam["amount"]))
                    Log(exchange.GetAccount())
                elif isSpot and dictParam["type"] == "sell":
                    exchange.Sell(-1, float(dictParam["amount"]))
                    Log(exchange.GetAccount())
                elif not isSpot and dictParam["type"] == "long":
                    exchange.SetDirection("buy")
                    if not q:
                        exchange.Buy(-1, float(dictParam["amount"]))
                    else :
                        q.pushTask(exchange, ContractType, "buy", float(dictParam["amount"]), lambda task, ret: Log(task["desc"], ret, "#FF0000"))
                    Log("持仓:", exchange.GetPosition())
                elif not isSpot and dictParam["type"] == "short":
                    exchange.SetDirection("sell")
                    if not q:
                        exchange.Sell(-1, float(dictParam["amount"]))
                    else :
                        q.pushTask(exchange, ContractType, "sell", float(dictParam["amount"]), lambda task, ret: Log(task["desc"], ret, "#FF0000"))
                    Log("持仓:", exchange.GetPosition())
                elif not isSpot and dictParam["type"] == "cover_long":
                    exchange.SetDirection("closebuy")
                    if not q:
                        exchange.Sell(-1, float(dictParam["amount"]))
                    else :
                        q.pushTask(exchange, ContractType, "closebuy", float(dictParam["amount"]), lambda task, ret: Log(task["desc"], ret, "#FF0000"))
                    Log("持仓:", exchange.GetPosition())
                elif not isSpot and dictParam["type"] == "cover_short":
                    exchange.SetDirection("closesell")
                    if not q:
                        exchange.Buy(-1, float(dictParam["amount"]))
                    else :
                        q.pushTask(exchange, ContractType, "closesell", float(dictParam["amount"]), lambda task, ret: Log(task["desc"], ret, "#FF0000"))
                    Log("持仓:", exchange.GetPosition())
                
                if q is not None:
                    while q.size() > 0:
                        q.poll()
                        Sleep(500)
            
            # 处理body数据
            if isDealBodyMsg:
                if exchange.GetName().find("Futures") != -1:
                    Log("data:", data.decode('utf-8'))  # 测试
                    if re.search(r'buy', data.decode('utf-8')):
                        Log("触发buy")
                        exchange.SetContractType(ct)
                        exchange.SetDirection("buy")
                        exchange.Buy(-1, amount)
                    elif re.search(r'sell', data.decode('utf-8')):
                        Log("触发sell")
                        exchange.SetContractType(ct)
                        exchange.SetDirection("sell")
                        exchange.Sell(-1, amount)
            
            # 写入数据应答
            self.wfile.write(json.dumps({"state": "ok"}).encode())
        except Exception as e:
            Log("Provider do_POST error, e:", e)


def createServer(host):
    try:
        server = ThreadingHTTPServer(host, Executor)
        Log("Starting server, listen at: %s:%s" % host)
        server.serve_forever()
    except Exception as e:
        Log("createServer error, e:", e)
        raise Exception("stop")

def main():
    # 开启一个线程
    try:
        _thread.start_new_thread(createServer, (("0.0.0.0", Port), ))         # VPS服务器上测试           
    except Exception as e:        
        Log("错误信息:", e)
        raise Exception("stop")    
    if exchange.GetName().find("Futures") != -1:
        exchange.SetContractType(ContractType)
    Log("账户资产信息:", _C(exchange.GetAccount))
    while True:
        if exchange.GetName() == "Futures_CTP":
            if exchange.IO("status"):
                LogStatus(_D(), "CTP连接")
            else:
                LogStatus(_D(), "CTP未连接")
        else:
            LogStatus(_D())
        Sleep(2000)

Больше

Эт8888/upload/asset/2457669d9c32568732cb7.jpg Открыть диск, чтобы указать эту ошибку.

Эт8888/upload/asset/2457669d9c32568732cb7.jpg Открыть диск, чтобы указать эту ошибку.

Уосан о мечахУчитель: Можно добавить в текстовое сообщение?

Уосан о мечах2021/11/21 11:53:33 CMD 199866 buy=0.1, Администратор получил это сообщение, и робот не сделал ничего.

суперонЯ смотрю эту ночь и не понимаю, может быть, перепишите?

Фучжи 1.Можно ли написать полный список телевизионных сигналов, как получить информацию из тела?

DietQuantУчитель, как изменить, чтобы увеличить двойную валюту на диске?

Восемь цифр для мечты.Боже мой, ты можешь выпустить симулятор OKv5?

СССССУчитель, вопрос: версия 3.7 - это версия администратора развертывания? Как его обновить? 2021-08-11 11:08:55 Ошибка Traceback (most recent call last): Файл "", line 999, in __init_ctx__ Файл "", line 4, in ImportError: cannot import name 'ThreadingHTTPServer' (Невозможно импортировать имя "ThreadingHTTPServer") 2021-08-11 11:08:55 Информация Коммерческие фьючерсные биржи успешно загружены 2021-08-11 11:08:55 Информация Вы используете Python версии 3.5 для Python компиляторной среды.

qq3390214355Я смотрю всю ночь и не понимаю, можно переписать, как связаться?

Чэнь НасанУчитель, привет, как пишется веб-адрес веб-хока, чтобы напрямую предупредить о направлении сделки на телевидении?

ланбнХорошо, спасибо, учитель, я попробую!

ланбнПрофессор, привет, пожалуйста, пожалуйста, напишите немного подробности о том, как написать код для контракта, программист очень неплох, спасибо!

Маленькие мечтыВ документации FMZ API финиширует функция переключения диска OKEX.

wbe3- маленький фрикадельникКак переключить дисковую панель? Всегда напоминает мне, что среда не подходит.

Маленькие мечтыОшибка возникла из-за отсутствия в Python соответствующего модуля ThreadingHTTPServer

Ключ 986Вы решили эту проблему?

Эт8888Узнайте.

Маленькие мечтыНе рекомендуется создавать запрос на сервис для прослушивания телевидения таким образом, используйте расширенный API FMZ.

Маленькие мечтыЭта стратегия используется в качестве примера для товарных фьючерсов, если вам нужно установить контрактный код, чтобы запустить цифровую валюту.

Маленькие мечтыПримером этой стратегии является то, что робот-тактик создает сервис для прослушивания запросов на сигналы от телевизора. `` # Проверка POST запроса на сообщение Body data = self.rfile.read ((200) # Указывает длину чтения Log (("data:", data) # Принтирует данные запроса POST, которые могут быть запрошены в соответствии с данными запроса и затем выполнены роботом. `` В коде уже есть комментарий, где указана информация о телеведущем, обрабатывающем запрос.

Маленькие мечтыВ этом случае мы должны быть готовы к тому, что они будут менять свою стратегию в соответствии со своими потребностями.

Маленькие мечтыВ FMZ настраивается API KEY для OKEX-амолокации, затем в коде добавляется слово ``exchange.

Маленькие мечтыЯ не понимаю, где, по-моему, я ошибся при использовании, проверьте.

Чэнь НасанСпасибо, если мой веб-адрес указывает направление покупки, но в сигнале "tv-стратегия" указано "продажа"?

Маленькие мечтыhttps://www.fmz.com/bbs-topic/5969 Статьи и стратегии содержат примеры.

Маленькие мечтыhttps://www.fmz.com/api#exchange.setcontracttype... В описании функции есть, смотрите.

PY008Что такое контрактный код?

Маленькие мечтыНепристойность.

Маленькие мечтыЕсли вы заключаете контракт на биржу, запишите адрес вебхука на телевизоре: Я хочу, чтобы вы сделали еще один контракт: `` http://x.x.x.x:xxxx/data?access_key=xxx&secret_key=yyy&type=long&amount=1 `` Но это не значит, что они не смогут выполнить это. `` http://x.x.x.x:xxxx/data?access_key=xxx&secret_key=yyy&type=cover_long&amount=1 `` Помните, что в параметрах стратегии настройка контрактного кода.