Files

15 KiB
Raw Blame History

MODIFIED Requirements

Requirement: Нормализованный состав Portfolio

Система MUST возвращать только обычные Portfolio Position с ненулевым количеством и доступные Cash Balance с ненулевой суммой. Cash Balance MUST быть отдельным от Portfolio Position элементом и агрегироваться до одного значения на валюту. Portfolio Position с типом CURRENCY MUST означать позицию по торгуемому валютному Instrument и MUST NOT смешиваться с Cash Balance. Порядок Portfolio Position и Cash Balance MUST соответствовать upstream-порядку; система MUST NOT сортировать или объединять Portfolio Position с одинаковым FIGI. Виртуальные позиции и заблокированные денежные остатки MUST NOT входить в Portfolio.

Каждая Portfolio Position MUST содержать нормализованный тип STOCK, BOND, FUND, CURRENCY, FUTURE, OPTION, STRUCTURED_NOTE, DIGITAL_FINANCIAL_ASSET либо OTHER, строковое quantity, nullable currentValue, nullable averagePurchasePrice, nullable absoluteReturn, nullable isin, nullable ticker и nullable logoName — имя файла логотипа бренда инструмента. Имя файла логотипа MUST заполняться из metadata инструмента, когда upstream предоставляет бренд с непустым именем файла логотипа; во всех остальных случаях оно MUST быть null. Логотип является presentation metadata: он не влияет на количество, стоимость, агрегаты, успешность или свежесть Portfolio Snapshot. Система MUST искать metadata по instrument UID при его наличии, затем по FIGI. Отображаемый идентификатор MUST предпочитать name, затем ticker, а при недоступности metadata использовать FIGI, не скрывая финансовые значения.

Scenario: Позиция с неизвестным upstream-типом

  • WHEN upstream возвращает обычную ненулевую позицию с нераспознанным типом инструмента
  • THEN система возвращает её в исходном порядке с типом OTHER

Scenario: Позиция валютного инструмента не является денежным остатком

  • WHEN upstream возвращает ненулевую Portfolio Position валютного инструмента и ненулевой Cash Balance той же валюты
  • THEN система возвращает Portfolio Position с типом CURRENCY отдельно от Cash Balance и не объединяет их между собой

Scenario: Позиция без metadata инструмента

  • WHEN lookup metadata по FIGI не дал ticker или name либо временно недоступен
  • THEN система возвращает позицию с FIGI как fallback-идентификатором и всеми доступными финансовыми значениями

Scenario: Имя инструмента доступно

  • WHEN metadata инструмента по FIGI содержит непустое name
  • THEN система возвращает name как отображаемый идентификатор позиции вместо FIGI или ticker

Scenario: FIGI не разрешается, но доступен instrument UID

  • WHEN FIGI позиции не даёт metadata, а её instrument UID возвращает непустое name
  • THEN система возвращает name, полученное по instrument UID

Scenario: ISIN инструмента доступен

  • WHEN metadata инструмента позиции содержит непустой isin
  • THEN система возвращает его в поле isin позиции

Scenario: ISIN инструмента отсутствует

  • WHEN у инструмента позиции нет ISIN либо metadata недоступна
  • THEN система возвращает позицию с isin: null, не скрывая финансовые значения

Scenario: Тикер инструмента доступен

  • WHEN metadata инструмента позиции содержит непустой ticker
  • THEN система возвращает его в поле ticker позиции

Scenario: Тикер инструмента отсутствует

  • WHEN у инструмента позиции нет ticker либо metadata недоступна
  • THEN система возвращает позицию с ticker: null, не скрывая финансовые значения

Scenario: Имя файла логотипа бренда доступно

  • WHEN metadata инструмента позиции содержит бренд с непустым именем файла логотипа
  • THEN система возвращает его в поле logoName позиции

Scenario: Имя файла логотипа бренда отсутствует

  • WHEN у инструмента позиции нет бренда, имя файла логотипа пустое либо metadata недоступна
  • THEN система возвращает позицию с logoName: null, не скрывая финансовые значения

Scenario: Денежные остатки в одной валюте

  • WHEN upstream возвращает несколько ненулевых доступных денежных остатков одной валюты
  • THEN система возвращает один Cash Balance с их точной суммой

Scenario: Штатный пустой Portfolio

  • WHEN у доступного Brokerage Account нет ненулевых обычных позиций и доступных денежных остатков
  • THEN система отвечает 200 с пустыми positions, cashBalances и totalsByCurrency

Requirement: Представление карточек позиций на клиенте

Клиент MUST отображать STOCK и BOND отдельными секциями. Внутри каждой секции MUST сохраняться upstream-порядок позиций. Позиции иных типов MUST оставаться доступными в отдельной общей секции.

Карточки секций STOCK и BOND MUST отображаться по одной в ряду при любой ширине экрана. Карточка акции или облигации MUST показывать визуальный логотип бренда инструмента рядом с отображаемым идентификатором позиции; при отсутствии имени файла логотипа либо неудачной загрузке изображения вместо логотипа MUST отображаться первая буква отображаемого идентификатора позиции. Абсолютный доход в карточке акции или облигации MUST отображаться значением с явным знаком (+ для положительного, - для отрицательного, без знака при нуле) с цветовой индикацией знака и без текстовой подписи доходности.

Карточка STOCK MUST показывать только ticker под отображаемым идентификатором позиции, если тикер доступен; при ticker: null она MUST сохранять текущее отображение isin как fallback. Карточки BOND и общей секции иных типов MUST сохранять отображение isin. Карточки общей секции иных типов MUST сохранять прежнее поведение: компактная плитка в адаптивном grid (одна колонка на узком экране, несколько колонок на широком), абсолютный доход с текстовой подписью доходности и цветовой индикацией знака, без визуального логотипа. Плитки всех секций MUST показывать отображаемый идентификатор позиции, количество, currentValue как главную метрику, absoluteReturn, averagePurchasePrice и долю позиции среди позиций той же валюты. Отсутствующие метрики MUST быть скрыты, а не отображаться заглушкой. При форматировании денежных значений в русской локали клиент MUST отображать RUB как символ ₽; другие валюты MUST сохранять понятное обозначение.

Scenario: Отдельные акции и облигации

  • WHEN Portfolio содержит позиции STOCK и BOND
  • THEN клиент отображает их в отдельных секциях «Акции» и «Облигации» без изменения порядка в каждой секции

Scenario: Портфель отображается на мобильном устройстве

  • WHEN User открывает загруженный Portfolio на узком экране
  • THEN клиент сохраняет читаемое одноколоночное отображение агрегатов, позиций и Cash Balance

Scenario: Карточка акции с доступным тикером

  • WHEN позиция STOCK имеет непустой ticker и ISIN
  • THEN клиент показывает под отображаемым идентификатором только тикер и не показывает ISIN

Scenario: Карточка акции без тикера

  • WHEN позиция STOCK имеет ticker: null и непустой ISIN
  • THEN клиент показывает ISIN под отображаемым идентификатором

Scenario: Карточка облигации сохраняет ISIN

  • WHEN позиция BOND имеет доступные ticker и ISIN
  • THEN клиент показывает ISIN и не заменяет его тикером

Scenario: Карточка позиции отображает доступные метрики

  • WHEN позиция, не относящаяся к STOCK, имеет значение текущей стоимости, абсолютного дохода, средней цены покупки и ISIN
  • THEN клиент показывает идентификатор, количество, текущую стоимость, абсолютный доход, среднюю цену покупки, долю позиции среди позиций той же валюты и ISIN

Scenario: Отсутствующие метрики скрыты

  • WHEN у позиции отсутствует значение текущей стоимости, средней цены покупки или дохода
  • THEN клиент скрывает соответствующую метрику вместо отображения заглушки

Scenario: Доход окрашен по знаку

  • WHEN у позиции абсолютный доход положительный или отрицательный
  • THEN клиент отображает его зелёным для положительного и красным для отрицательного, без цвета при его отсутствии

Scenario: Доля позиции в валюте

  • WHEN позиция имеет вычислимую текущую стоимость в валюте
  • THEN клиент отображает её долю среди всех позиций той же валюты, не включая Cash Balance

Scenario: Одноколоночные секции акций и облигаций

  • WHEN User открывает загруженный Portfolio с позициями STOCK или BOND на широком экране
  • THEN клиент отображает карточки соответствующей секции по одной в ряду

Scenario: Логотип акции или облигации отображается

  • WHEN позиция STOCK или BOND содержит непустое имя файла логотипа бренда и изображение успешно загружается
  • THEN клиент показывает изображение логотипа рядом с отображаемым идентификатором позиции

Scenario: Фолбэк без логотипа у акции или облигации

  • WHEN у позиции STOCK или BOND имя файла логотипа отсутствует либо изображение не загружается
  • THEN вместо логотипа клиент показывает первую букву отображаемого идентификатора позиции

Scenario: Доходность акции или облигации со знаком без подписи

  • WHEN карточка акции или облигации показывает абсолютный доход
  • THEN клиент отображает значение с явным знаком + или - (без знака при нуле) и без текстовой подписи доходности

Scenario: Секция облигаций в едином стиле с акциями

  • WHEN User открывает загруженный Portfolio с позициями BOND
  • THEN клиент отображает облигации по одной карточке в ряду с визуальным логотипом бренда либо фолбэком первой буквы и абсолютным доходом с явным знаком без текстовой подписи

Scenario: Секция иных типов сохраняет прежний вид

  • WHEN User открывает загруженный Portfolio с позициями иных типов (не STOCK и не BOND)
  • THEN клиент отображает их компактными плитками в адаптивном grid с текстовой подписью доходности и без визуального логотипа