通知:获利/止损所需采取的行动。 如果您的经纪人不支持这些订单

有一家俄罗斯经纪人-Tinkoff银行。 现在的问题是:经纪人不支持止盈和止损定单。 完全没有 如果您想在交易时感到更方便,则需要针对这种情况的解决方法,直到Tinkoff Bank开发人员最终释放这些订单作为杀手级功能。 在本文中,我将向您展示我的解决方法。
更新: 2019年3月22日,Broker在Google Play中发布了3.0.0平台(重大更新)。 变更日志功能接受获利/止损订单

我为什么决定在这里发布文章? 我有一个假设,Tinkoff Bank及其产品在俄罗斯的IT人群中颇受欢迎,可能其中一些具有相同的需求,但没有足够的时间或意愿来开发自己的临时解决方法。 这就是为什么我分享我的解决方案和解决方案的历史的原因。

在这里,我应该说一下经纪人提供的解决方法。 首先,经纪人有限价单。 该功能于2019年2月发布(客户等待了将近两年)。 它们的特点是在一个交易日内工作。 因此,您需要在每个交易日重新设置它们。 另一个缺陷:您无法根据需要设置限制。 有一定的价格范围,您不能以超出该范围的价格下达限价单。 而且这个范围非常狭窄。 在动荡的市场上,这会让您感到不便。 最后,您不能创建两个多方向定单(在我的情况下,即使第一个限价定单也会导致经纪人移动应用立即崩溃,而经纪人的站点不提供此功能)。

其次,经纪人的移动应用程序提供了一项功能:您可以订阅资产的价格变动。 如果超过了阈值(绝对价格或相对百分比),您将收到通知。 但是同样,您不能为资产创建两个阈值。

我的解决方法很简单:

  1. 我们确实有资产的门槛。 我们自己计算阈值。 如果超过了阈值,我们将采取手动操作:通过卖出或购买来获得损益。
  2. 我们应该获取数据源,以获取实际资产的价格
  3. 如果超过了阈值,我们应该发送通知。

它看起来很简单,但是我的解决方案中有一些细节需要分享和讨论。

1.虽然我的证券投资组合只有一种资产,但在脚本中定义了阈值,并且股票搜索变得简单,简单且根本不可配置。 这是一个不好的解决方案,但很快就表明这个想法是正确的。 当我在投资组合中获取新资产时,我从文件中加载了股票名称,交易所,阈值。

2.我的第一个资产是外国股票,该外国股票只能在圣彼得堡交易所买卖。 我最急的是解析SPb交易所的站点

由于存在数量递减的排序方式,因此很容易解析,因为我的资产始终位于第一页上。 但是3月8日它被打破了。 我不知道为什么,但是TSLA在第25页上弹出。 他们的分页器使用JavaScript下载页面数据。 有一个简单的解决方案:下载并解析所有页面并找到资产。 但是在每个循环中需要花费大量时间来下载和解析25个以上的页面。

取而代之的是,我决定将tradingview.com网站添加为另一个数据源。 无需分析很多页面来查找股票,因为每种资产都有自己的页面,如下所示:
www.tradingview.com/symbols/NASDAQ-TSLA

我以为,现在我的问题了,但是我错了。 页面上的数据仅使用JS加载和更新。 因此,我过去用于下载页面的请求失败。

对于这个问题,我知道三种不同的解决方案:

PyQT,硒(网络驱动程序)和扩展请求-HTML。 因为我的项目中已经有Requests模块,所以我决定使用Requests-HTML。

令我失望的是,它并不是很稳定,直到我找到有关StackOverFlow的一些线索。

session = HTMLSession() r = session.get(url) my = r.html.render(timeout=30) selector = 'span.tv-symbol-header-quote__value.tv-symbol-header-quote__value--large.js-symbol-last' price = r.html.find(selector)[0].text r.close() session.close() 

注意超时以及两个close()调用。 大多数示例都缺少这些细节,并且可能会出现一些问题。

3.现在,当我们下载了带有JS数据的页面,对其进行了解析并决定了是否需要发送通知时,只有一个问题:“我们如何发送通知?”。 就我而言,sms.ru提供了便捷的API和每天5条免费短信。 在SMS门上注册。 创建一个API密钥。 关键是这样的:

 24A41EA5-EEEE-CCCC-5555-094143C2EDDD 

从我的解决方案的早期版本发送短信功能:

 def send_message(mymessage): sms_url = 'https://sms.ru/sms/send?api_id=key&to=number&msg=message&json=1' sms_url = sms_url.replace('key', mykey) sms_url = sms_url.replace('number', mynumber) sms_url = sms_url.replace('message', mymessage) sms_response = requests.get(sms_url) 

它运作良好。 我遇到一个问题:如果我们已经发送了SMS,该怎么办? 第一个版本没有任何检查,因此它在每个循环内发送一条SMS。 一次又一次。

我添加了SMS计数器,脚本在调用send_message之前会对其进行检查。

  global sms_counter sms_counter = sms_counter + 1 

好,知道了 但是随着新的一天的到来,出现了一个新的问题:如何刷新SMS计数器? 或者,实际上,什么时候? 我看到了三种不同的方式:将计数器存储在数据库中(但我的解决方案目前是无状态的),解析日期/时间以在交易日之间刷新计数器并在两个交易日之间的某个时间点重新启动脚本。 目前,我实现了最新的变体,但是将来,我可能会对其进行更改。

我的解决方案现在可以运行了,您可以从GitHub下载它。

对于不知道如何处理Python脚本的用户,我提供Windows打包解决方案 (由PyInstaller提供)。

待办事项:

  1. 解析日期时间以刷新SMS计数器,而不是重新启动脚本;
  2. 现在是无状态应用程序,我想添加一个数据库;
  3. 在#2之后,最好跟踪资产价格的大幅上涨或下跌(相对于前一个交易日的收盘价);
  4. 扩展通信路径(电报,Viber,语音呼叫)和提供程序(出于可靠性目的,我想添加smsc.ru SMS门,因为sms.ru有时会卡住,尽管发送了SMS却不会返回sms_response)。

Source: https://habr.com/ru/post/zh-CN443434/


All Articles