- Create code-first route tree in src/app/routing/routeTree.tsx - Replace ProtectedRoute with beforeLoad auth guards - Add useSearchParamsCompat for URLSearchParams access - Update App.tsx, layouts, and all page/widget imports - Add frontend tooling: biome, prettier, env config - Update all tests for TanStack Router compatibility - Remove react-router-dom dependency, @tanstack/router-plugin - Consolidate biome config at root level
392 lines
8.1 KiB
TypeScript
392 lines
8.1 KiB
TypeScript
export interface ApiResponseMeta {
|
|
cachedAt: string | null
|
|
fromCache: boolean
|
|
}
|
|
|
|
export interface ApiEnvelope<T> {
|
|
data: T
|
|
meta: ApiResponseMeta
|
|
}
|
|
|
|
export interface StockMarketData {
|
|
price: number | null
|
|
change: number | null
|
|
changePercent: number | null
|
|
open: number | null
|
|
high: number | null
|
|
low: number | null
|
|
volume: number
|
|
value: number
|
|
issueCapitalization: number | null
|
|
updatedAt: string
|
|
}
|
|
|
|
export interface ShareResponse {
|
|
secid: string
|
|
isin: string
|
|
name: string
|
|
shortName: string
|
|
latName: string | null
|
|
listLevel: number
|
|
issueSize: number
|
|
faceValue: number
|
|
faceUnit: string
|
|
type: string
|
|
marketData: StockMarketData
|
|
}
|
|
|
|
export interface DividendItem {
|
|
registryCloseDate: string
|
|
value: number
|
|
currency: string
|
|
}
|
|
|
|
export interface ShareHistoryItem {
|
|
date: string
|
|
open: number
|
|
high: number
|
|
low: number
|
|
close: number
|
|
volume: number
|
|
value: number
|
|
}
|
|
|
|
export interface BondMarketData {
|
|
price: number | null
|
|
yieldToMaturity: number | null
|
|
duration: number | null
|
|
accruedInt: number | null
|
|
couponValue: number | null
|
|
couponPercent: number | null
|
|
nextCouponDate: string | null
|
|
open: number
|
|
high: number | null
|
|
low: number | null
|
|
volume: number
|
|
updatedAt: string
|
|
}
|
|
|
|
export interface BondResponse {
|
|
secid: string
|
|
isin: string
|
|
name: string
|
|
shortName: string
|
|
latName: string | null
|
|
listLevel: number
|
|
issueSize: number
|
|
faceValue: number
|
|
faceUnit: string
|
|
matDate: string
|
|
couponValue: number
|
|
couponPercent: number | null
|
|
couponPeriod: number
|
|
nextCoupon: string | null
|
|
accruedInt: number
|
|
bondType: string
|
|
bondSubType: string
|
|
offerDate: string | null
|
|
buybackDate: string | null
|
|
marketData: BondMarketData
|
|
}
|
|
|
|
export interface BondHistoryItem {
|
|
date: string
|
|
closePrice: number
|
|
yieldClose: number | null
|
|
duration: number | null
|
|
}
|
|
|
|
export interface CandleItem {
|
|
open: number
|
|
high: number
|
|
low: number
|
|
close: number
|
|
volume: number
|
|
value: number
|
|
begin: string
|
|
end: string
|
|
}
|
|
|
|
export interface SearchResultItem {
|
|
secid: string
|
|
isin: string
|
|
shortName: string
|
|
type: 'share' | 'bond'
|
|
listLevel: number
|
|
currency: string | null
|
|
price: number | null
|
|
}
|
|
|
|
export interface HealthResponse {
|
|
status: string
|
|
timestamp: string
|
|
uptime: number
|
|
}
|
|
|
|
export interface UserResponse {
|
|
id: number
|
|
email: string
|
|
name: string | null
|
|
role: string
|
|
}
|
|
|
|
export interface AuthResponse {
|
|
user: UserResponse
|
|
accessToken: string
|
|
}
|
|
|
|
export interface Portfolio {
|
|
id: number
|
|
name: string
|
|
description: string | null
|
|
currency: string
|
|
createdAt: string
|
|
updatedAt: string
|
|
totalValue: number
|
|
positionCount: number
|
|
shareCount: number
|
|
bondCount: number
|
|
}
|
|
|
|
export interface PositionWithPrice {
|
|
id: number
|
|
portfolioId: number
|
|
secid: string
|
|
shortName: string | null
|
|
type: 'share' | 'bond'
|
|
quantity: number
|
|
notes: string | null
|
|
tags: string[] | null
|
|
currentPrice: number | null
|
|
buyPrice: number | null
|
|
buyDate: string | null
|
|
totalCost: number | null
|
|
currentValue: number | null
|
|
pnl: number | null
|
|
pnlPercent: number | null
|
|
dividendIncome: number | null
|
|
totalReturn: number | null
|
|
totalReturnPercent: number | null
|
|
weightPercent: number
|
|
change?: number | null
|
|
changePercent?: number | null
|
|
yieldToMaturity?: number | null
|
|
duration?: number | null
|
|
couponValue?: number | null
|
|
couponPercent?: number | null
|
|
nextCouponDate?: string | null
|
|
matDate?: string | null
|
|
accruedInt?: number | null
|
|
bid?: number | null
|
|
offer?: number | null
|
|
couponPeriod?: number | null
|
|
bondType?: string | null
|
|
offerDate?: string | null
|
|
}
|
|
|
|
export interface PortfolioDetail extends Portfolio {
|
|
positions: PositionWithPrice[]
|
|
totalValue: number
|
|
analytics: PortfolioSummary
|
|
}
|
|
|
|
export interface Position {
|
|
id: number
|
|
secid: string
|
|
quantity: number
|
|
notes: string | null
|
|
tags: string[] | null
|
|
portfolioId: number
|
|
createdAt: string
|
|
updatedAt: string
|
|
}
|
|
|
|
export interface PortfolioSummary {
|
|
totalInvested: number
|
|
totalValue: number
|
|
totalPnl: number
|
|
totalPnlPercent: number | null
|
|
totalDividends: number
|
|
totalReturn: number
|
|
totalReturnPercent: number | null
|
|
positionCount: number
|
|
weightedYield: number | null
|
|
}
|
|
|
|
export interface AnalyticsResponse {
|
|
positions: PositionWithPrice[]
|
|
summary: PortfolioSummary
|
|
}
|
|
|
|
export interface ScreenerItem {
|
|
secid: string
|
|
shortName: string
|
|
isin: string
|
|
type: 'share' | 'bond'
|
|
price: number | null
|
|
change: number | null
|
|
changePercent: number | null
|
|
volume: number
|
|
listLevel: number
|
|
capitalization: number | null
|
|
yieldToMaturity: number | null
|
|
duration: number | null
|
|
couponValue: number | null
|
|
couponPercent: number | null
|
|
accruedInt: number | null
|
|
matDate: string | null
|
|
bondType: string | null
|
|
}
|
|
|
|
export interface ScreenerResult {
|
|
items: ScreenerItem[]
|
|
total: number
|
|
page: number
|
|
pageSize: number
|
|
totalPages: number
|
|
}
|
|
|
|
export interface BrokerMoney {
|
|
currency: string
|
|
units: string
|
|
nano: number
|
|
value: number
|
|
}
|
|
|
|
export interface BrokerAccount {
|
|
id: string
|
|
type: 'brokerage' | 'iis'
|
|
name: string
|
|
status: string
|
|
openedAt: string | null
|
|
accessLevel: string | null
|
|
}
|
|
|
|
export interface BrokerPosition {
|
|
figi: string | null
|
|
instrumentUid: string | null
|
|
positionUid: string | null
|
|
ticker: string | null
|
|
classCode: string | null
|
|
instrumentType: string | null
|
|
name: string | null
|
|
quantity: number | null
|
|
blockedLots: number | null
|
|
currentPrice: BrokerMoney | null
|
|
currentValue: BrokerMoney | null
|
|
averagePositionPrice: BrokerMoney | null
|
|
expectedYieldPercent: number | null
|
|
dailyYield: BrokerMoney | null
|
|
}
|
|
|
|
export interface BrokerPortfolio {
|
|
account: BrokerAccount
|
|
positionCounts: {
|
|
shares: number
|
|
bonds: number
|
|
etf: number
|
|
other: number
|
|
}
|
|
totals: {
|
|
shares: BrokerMoney | null
|
|
bonds: BrokerMoney | null
|
|
etf: BrokerMoney | null
|
|
currencies: BrokerMoney | null
|
|
futures: BrokerMoney | null
|
|
options: BrokerMoney | null
|
|
structuredProducts: BrokerMoney | null
|
|
dfa: BrokerMoney | null
|
|
portfolio: BrokerMoney | null
|
|
}
|
|
yields: {
|
|
expectedPercent: number | null
|
|
daily: BrokerMoney | null
|
|
dailyPercent: number | null
|
|
}
|
|
cash: BrokerMoney[]
|
|
blockedCash: BrokerMoney[]
|
|
asOf: string
|
|
}
|
|
|
|
export type BrokerOperationCategory = 'trade' | 'income' | 'tax' | 'fee' | 'transfer' | 'other'
|
|
|
|
export interface BrokerOperation {
|
|
cursor: string | null
|
|
accountId: string
|
|
id: string | null
|
|
parentOperationId: string | null
|
|
date: string | null
|
|
type: string
|
|
category: BrokerOperationCategory
|
|
description: string | null
|
|
name: string | null
|
|
state: string | null
|
|
instrumentUid: string | null
|
|
figi: string | null
|
|
ticker: string | null
|
|
classCode: string | null
|
|
instrumentType: string | null
|
|
payment: BrokerMoney | null
|
|
price: BrokerMoney | null
|
|
commission: BrokerMoney | null
|
|
yield: BrokerMoney | null
|
|
accruedInt: BrokerMoney | null
|
|
quantity: number | null
|
|
quantityDone: number | null
|
|
}
|
|
|
|
export interface BrokerOperationsPage {
|
|
accountId: string
|
|
items: BrokerOperation[]
|
|
nextCursor: string | null
|
|
hasNext: boolean
|
|
asOf: string
|
|
}
|
|
|
|
export interface BrokerPositionsPage {
|
|
accountId: string
|
|
items: BrokerPosition[]
|
|
nextCursor: string | null
|
|
hasNext: boolean
|
|
asOf: string
|
|
}
|
|
|
|
export interface BrokerPortfolioEvent {
|
|
id: string
|
|
type: 'dividend' | 'coupon' | 'maturity' | 'offer'
|
|
source: 'forecast' | 'actual'
|
|
category: 'cashflow' | 'corporate'
|
|
eventDate: string
|
|
paymentDate: string | null
|
|
ticker: string | null
|
|
name: string | null
|
|
instrumentUid: string | null
|
|
instrumentType: 'share' | 'bond' | 'other'
|
|
quantitySnapshot: number | null
|
|
payoutPerUnit: number | null
|
|
estimatedAmount: number | null
|
|
actualAmount: number | null
|
|
currency: string | null
|
|
estimateMode: 'current_position' | null
|
|
}
|
|
|
|
export interface BrokerEventsSummary {
|
|
eventCount: number
|
|
nearestEventDate: string | null
|
|
totalEstimatedCashflow: number
|
|
actualCashflow: number
|
|
forecastEstimatedCashflow: number
|
|
dividendsTotal: number
|
|
couponsTotal: number
|
|
principalRepaymentTotal: number
|
|
actualDividendsTotal: number
|
|
actualCouponsTotal: number
|
|
actualPrincipalRepaymentTotal: number
|
|
}
|
|
|
|
export interface BrokerEventsData {
|
|
items: BrokerPortfolioEvent[]
|
|
summary: BrokerEventsSummary
|
|
asOf: string
|
|
}
|