Tinkoff / invest-openapi

Документация для Тинькофф Инвестиции OpenApi
https://tinkoff.github.io/invest-openapi/
456 stars 52 forks source link

Ошибка при запуске скрипта (Ошибка tinvest.exceptions.UnexpectedError: 500 ) #687

Open Kloblok opened 1 year ago

Kloblok commented 1 year ago

Traceback (most recent call last): File "/home/user/Desktop/bot/v2/tb2.1.py", line 104, in asyncio.run(main()) File "/usr/lib/python3.10/asyncio/runners.py", line 44, in run return loop.run_until_complete(main) File "/usr/lib/python3.10/asyncio/base_events.py", line 646, in run_until_complete return future.result() File "/home/user/Desktop/bot/v2/tb2.1.py", line 44, in main await client.register_sandbox_account(SandboxRegisterRequest(broker_account_type=BrokerAccountType.tinkoff)) File "/usr/local/lib/python3.10/dist-packages/tinvest/clients.py", line 134, in register_sandbox_account return await sandbox_register_post(self._request, body) File "/usr/local/lib/python3.10/dist-packages/tinvest/clients.py", line 117, in _request raise UnexpectedError(response.status, await response.text()) tinvest.exceptions.UnexpectedError: 500

14.06 код работал исправно, 15.06 код начал выдавать ошибку указанную выше. Изменения не вносились. Ошибка tinvest.exceptions.UnexpectedError: 500 указывает на внутреннюю ошибку на стороне сервера при обработке запроса к API брокера Tinkoff. Посчитал, что ошибка может быть вызвана конфликтом библиотек, установленных после последнего удачного запуска кода. Удалил их. Ошибка не пропала. Помогите, пожалуйста

Вот код:

mport asyncio
from datetime import datetime, timedelta
from tinvest import CandleResolution, AsyncClient, SandboxRegisterRequest, BrokerAccountType
from prettytable import PrettyTable
from colorama import Fore, Style
import os

#Определение токена и акций, которые нужно отслеживать.
SANDBOX_TOKEN = 'TOKEN'

stocks_to_track = {
    'BBG00JXPFBN0': 'X5',
    'BBG004S68B31': 'Алроса',
    'BBG000R607Y3': 'Полюс',
    'BBG004730RP0': 'Газпром',
    'BBG004731489': 'Норникель',
    'BBG004731032': 'Лукойл',
    'BBG004S681W1': 'МТС',
    'BBG00475KKY8': 'Новатэк',
    'BBG004731354': 'Роснефть',
    'BBG004730N88': 'Сбер',
    'BBG0047315D0': 'Сургутнефтегаз',
    'BBG004RVFFC0': 'Татнефть',
    'BBG004PYF2N3': 'Polymetal',
    'BBG006L8G4H1': 'Яндекс'
}  # словарь figi-названий акций для отслеживания

#Инициализация словарей для хранения изменений цен и начальных цен акций
price_changes = {stock: 0.0 for stock in stocks_to_track.values()}  # инициализируем словарь для хранения изменений цен
total_changes = {stock: 0.0 for stock in stocks_to_track.values()}  # инициализируем словарь для хранения общих изменений
initial_prices = {stock: None for stock in stocks_to_track.values()}  # инициализируем словарь для хранения начальных цен

#Функция get_color используется для выбора цвета в зависимости от того, является ли изменение цены положительным или отрицательным.
def get_color(value: float) -> str:
    if value < 0:
        return Fore.RED
    else:
        return Fore.GREEN

#main функция, которая запускает отслеживание изменений цен для каждой акции.
async def main():
    async with AsyncClient(SANDBOX_TOKEN, use_sandbox=True) as client:
        # Регистрация в сандбоксе
        await client.register_sandbox_account(SandboxRegisterRequest(broker_account_type=BrokerAccountType.tinkoff))

        # Отслеживание цен
        tasks = [track_price_change(client, figi, 0.001, stocks_to_track[figi]) for figi in stocks_to_track.keys()]
        await asyncio.gather(*tasks)

#track_price_change функция, которая отслеживает изменение цены акции и обновляет таблицу в консоли.
async def track_price_change(client, figi, change_percentage, stock_name):
    last_price = None
    while True:
        now = datetime.utcnow()
        hour_ago = now - timedelta(hours=1)
        candles = await client.get_market_candles(figi, hour_ago.isoformat() + 'Z', now.isoformat() + 'Z', CandleResolution.min1)
        current_price = candles.payload.candles[-1].c

        if initial_prices[stock_name] is None:
            initial_prices[stock_name] = current_price

        if last_price is None:
            last_price = current_price

        actual_change = (current_price - last_price) / last_price
        total_change = (current_price - initial_prices[stock_name]) / initial_prices[stock_name]

        if abs(actual_change) >= change_percentage:
            last_price = current_price
            price_changes[stock_name] = actual_change * 100  # обновляем словарь с изменениями цен

        total_changes[stock_name] = total_change * 100

        # Выводим обновленную таблицу
        os.system('clear')
        table = PrettyTable()
        table.field_names = ["Stock", "Change (%)", "Total Change (%)"]

        min_change = min(price_changes.values())
        max_change = max(price_changes.values())
        min_total_change = min(total_changes.values())
        max_total_change = max(total_changes.values())

        for stock in stocks_to_track.values():
            change_str = f"{price_changes[stock]:+.2f}"
            if price_changes[stock] == min_change:
                change_str = "*" + change_str + "*"
            elif price_changes[stock] == max_change:
                change_str = "**" + change_str + "**"

            total_change_str = f"{total_changes[stock]:+.2f}"
            if total_changes[stock] == min_total_change:
                total_change_str = "*" + total_change_str + "*"
            elif total_changes[stock] == max_total_change:
                total_change_str = "**" + total_change_str + "**"

            table.add_row([stock, get_color(price_changes[stock]) + change_str + Style.RESET_ALL, get_color(total_changes[stock]) + total_change_str + Style.RESET_ALL])
        print(table)

        await asyncio.sleep(20)  # Проверка

if __name__ == "__main__":
    asyncio.run(main())
KirillKaverin commented 1 year ago

Api V1 вырубили. Переходите на V2. Для перехода было достаточно времени (больше года) и есть пакеты под Python.