Artigo relacionado:https://www.fmz.com/bbs-topic/5969
Como o servidor HTTPS tem algumas falhas em si, considere usar o ThreadingHTTPServer em vez disso. Referências:https://docs.python.org/3.7/library/http.server.htmlO Python 3.7 é necessário.
Informações sobre o problema do 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)
ETH8888/upload/asset/2457669d9c32568732cb7.jpg Abra o disco real e este erro é sugerido, onde está errado
ETH8888/upload/asset/2457669d9c32568732cb7.jpg Abra o disco real e este erro é sugerido, onde está errado
A espada de Hu YanshanT: Posso enviar uma mensagem?
A espada de Hu Yanshan2021/11/21 11:53:33 CMD 199866 buy=0.1, o administrador recebeu esta mensagem, mas não há nenhuma ação no robô
superãoSe você não entendeu, pode traduzir?
O que é isso?Pode-se escrever um exemplo de uma lista completa de sinais de televisão, como obter informações dentro do corpo.
DietQuantProfessor, como mudar para aumentar a moeda binária no disco único?
Sonhos custam oito dígitosMeu Deus, você pode fazer uma simulação de OKv5?
SssxxxdPor favor, professor, uma pergunta: a versão 3.7 é a versão do administrador de implementação?
2021-08-11 11:08:55 Erro Traceback (most recent call last): File "
QQ3390214355Eu não entendo, mas se você pode traduzir, como entrar em contato?
Chen NanshanOlá, professor, como é escrito o endereço do webhook da política de alarme direto na TV?
lanbnMuito bem, obrigada professora, vou experimentar!
lanbnProfessora, olá, você pode me dar um pouco mais de detalhes sobre como escrever um pouco de código no contrato?
Inventor quantificado - sonho pequenoA documentação da API FMZ termina com a função OKEX para trocar discos analógicos.
N95A estratégia para receber sinais de TV, como mudar o disco analógico?
Inventor quantificado - sonho pequenoO erro ocorre porque o Python não tem um módulo relacionado ao ThreadingHTTPServer
chave986Não resolveste esse problema?
ETH8888É claro.
Inventor quantificado - sonho pequenoNão é recomendável criar um serviço de solicitação de escuta de TV, use a extensão da API do FMZ.
Inventor quantificado - sonho pequenoEsta estratégia é usada como um exemplo de commodity futures, se você precisa definir um código de contrato para executar uma moeda digital.
Inventor quantificado - sonho pequenoO exemplo da estratégia é direto: um robô estratégico cria um serviço para ouvir as solicitações de sinais da TV. Não. # Teste POST solicita informação do corpo data = self.rfile.read ((200) # Especifica a duração da leitura Log (("data:", data) # Imprime os dados da solicitação POST, que podem ser especificados com base nos dados da solicitação e depois o robô executa as operações correspondentes Não. O código já tem uma anotação, e aqui está o corpo de informações para processar os pedidos enviados pela TV.
Inventor quantificado - sonho pequenoA política é a mesma para todos.
Inventor quantificado - sonho pequenoConfigure o API KEY do disco OKEX no FMZ, e adicione uma palavra ``exchange no código.
Inventor quantificado - sonho pequenoNão entendo, acho que foi um erro, verifique.
Chen NanshanObrigado, se o meu endereço do webhook diz que a direção da transação é comprar, mas a dica do tv strategy alert é vender?
Inventor quantificado - sonho pequenoO site https://www.fmz.com/bbs-topic/5969 tem exemplos de artigos e estratégias.
Inventor quantificado - sonho pequenohttps://www.fmz.com/api#exchange.setcontracttype... está na descrição da função e pode ver.
PY008O que é o código do contrato?
Inventor quantificado - sonho pequenoNão é cortês.
Inventor quantificado - sonho pequenoSe você está fazendo um contrato com uma bolsa, escreva o endereço do webhook na TV: O que é que ele está a fazer? Não. http://x.x.x.x:xxxx/data?access_key=xxx&secret_key=yyy&type=long&amount=1 Não. O contrato é simples: Não. http://x.x.x.x:xxxx/data?access_key=xxx&secret_key=yyy&type=cover_long&amount=1 Não. Lembre-se de definir o código do contrato no parâmetro da política.