Files
docs/features/tbank-connection.md
T

6.0 KiB
Raw Blame History

Подключение T-Bank

Авторизованный пользователь управляет одним подключением к T-Bank Invest в настройках. Токен вводится только в поле пароля, отправляется в backend для проверки и больше не отображается.

sequenceDiagram
  participant F as Frontend
  participant B as Backend
  participant T as T-Bank gRPC
  participant D as SQLite
  F->>B: PUT /api/v1/tbank-connection (Bearer, token)
  B->>T: GetAccounts(OPEN) over TLS
  T-->>B: счета или ошибка проверки
  B->>D: сохранить шифротекст AES-256-GCM
  B-->>F: { connected, connectedAt }

API

  • GET /api/v1/tbank-connection возвращает { connected: false, connectedAt: null } или статус подключенного аккаунта.
  • PUT /api/v1/tbank-connection принимает { token }, проверяет его через GetAccounts и создает или заменяет подключение.
  • DELETE /api/v1/tbank-connection идемпотентен и возвращает 204.
  • connectedAt - метка времени RFC 3339 в UTC. Ответы и ошибки API никогда не содержат токен.

INVALID_TBANK_TOKEN означает, что T-Bank отклонил аутентификацию или права доступа. TBANK_UNAVAILABLE означает временную ошибку, превышение лимита, ожидание в очереди или другую ошибку внешнего сервиса.

Граница финансового кэша

Каждый успешный PUT заново шифрует token с новым AES-GCM nonce. Backend вычисляет из сохранённого шифротекста непрозрачную внутреннюю generation и разрешает повторно использовать Portfolio Snapshot и Ledger Page Cache только для текущей generation. Generation не хранится отдельным полем, не входит в API, logs или errors. Поэтому сохранённый или поздно завершившийся ответ предыдущего подключения не обслуживает запрос после создания, замены или удаления connection, включая замену тем же plaintext token.

После успешного PUT или DELETE frontend сначала коммитит подтверждённый статус connection, затем сбрасывает все generated GET query в /api/v1/brokerage-accounts, /api/v1/stocks и /api/v1/bonds subtrees. Активные выборки запрашиваются заново, а неактивные загружаются при следующем использовании; данные предыдущей границы не остаются Client Cached Snapshot. Неуспешная mutation не меняет status, backend generation или financial cache. Обычная ошибка фонового refetch сохраняет Client Cached Snapshot текущей generation. Logout остаётся отдельной границей Session и полностью очищает status connection и остальные session-scoped query.

Конфигурация и ограничения

  • TOKEN_ENCRYPTION_KEY - закодированный в base64 32-байтный ключ AES-256-GCM; обязателен при запуске.
  • TBANK_GRPC_ENDPOINT по умолчанию имеет значение invest-public-api.tbank.ru:443.
  • TBANK_RATE_LIMIT_PER_SECOND задаёт максимальное число T-Bank RPC в секунду на экземпляр backend; значение по умолчанию -- 5.
  • TBANK_CA_CERT_PATH - необязательный путь к корневому CA-сертификату PEM для сетей с TLS-инспекцией; проверка TLS остается включенной.

FIFO-ограничитель на экземпляр запускает не более 5 запросов в секунду и принимает не более 50 ожидающих вызовов. Для UNAVAILABLE, DEADLINE_EXCEEDED и RESOURCE_EXHAUSTED выполняется одна повторная попытка через секунду. Deadline каждой попытки - 15 секунд.

Портфель с большим числом ранее не кэшированных инструментов создаёт отдельные metadata lookup. Если в такой ситуации очередь переполняется и позиции получают FIGI вместо names, увеличьте TBANK_RATE_LIMIT_PER_SECOND в соответствии с разрешённой upstream-квотой; для локального портфеля из множества позиций использовалось значение 50.

Ограничения

Подключение используется поставленными сценариями Brokerage Accounts, Portfolio, Account Ledger, Future Cash Events, страницы акции и облигации; frontend не обращается к T-Bank напрямую. Token encryption key не ротируется, rate limit остаётся per-instance, а обновление connection не сериализуется между распределёнными экземплярами backend. Интеграция использует protobuf-контракт T-Bank Invest API. Автоматическое обновление внешнего протокола не предусмотрено; совместимость новой версии проверяется при отдельном обновлении интеграции.