feat: instrument analysis

This commit is contained in:
OpenSquared
2026-08-01 07:57:44 +02:00
parent 3fb61f1690
commit 7e640a09d0
3 changed files with 81 additions and 45 deletions

View File

@@ -41,18 +41,26 @@ export type SaxoLinkKind = keyof typeof SAXO_LINK_KIND_META
// injected by the caller so this can drive any backing store (instruments_watchlist's
// saxo_option_symbol/saxo_quote_symbol columns via Config.tsx, or instruments.json's
// saxo_quote_symbol field via InstrumentDashboard.tsx) without knowing which one it is.
export default function SaxoLinkPicker({ ticker, kind, saxoSymbol, onSave, isPending }: {
export default function SaxoLinkPicker({ ticker, kind, saxoSymbol, onSave, isPending, assetTypes }: {
ticker: string
kind: SaxoLinkKind
saxoSymbol: string | null
onSave: (symbol: string | null) => void
isPending: boolean
// Overrides SAXO_LINK_KIND_META[kind]'s default asset types — e.g. an FX instrument's
// "Quote" link should only ever search FxSpot, not the default's ContractFutures/
// CfdOnFutures/StockIndex too (those exist for commodities/indices priced via futures on
// Saxo, but searching "EURUSD" under the unfiltered default surfaces CME EURUSD futures
// contracts alongside the actual spot rate — a different product, not what a currency
// pair's price should ever be linked to).
assetTypes?: string
}) {
const [editing, setEditing] = useState(false)
const [value, setValue] = useState(saxoSymbol ?? '')
const [showDropdown, setShowDropdown] = useState(false)
const meta = SAXO_LINK_KIND_META[kind]
const { data: catalogMatches } = useSaxoCatalog(meta.assetTypes, value.length >= 2 ? value : undefined)
const effectiveAssetTypes = assetTypes ?? meta.assetTypes
const { data: catalogMatches } = useSaxoCatalog(effectiveAssetTypes, value.length >= 2 ? value : undefined)
const save = (sym?: string) => {
const resolved = (sym ?? value).trim().toUpperCase() || null

View File

@@ -2045,7 +2045,9 @@ export default function InstrumentDashboard({ instrumentIdProp, isVisible }: { i
{selected && (
<SaxoLinkPicker ticker={selected.id} kind="quote" saxoSymbol={selected.saxo_quote_symbol ?? null}
isPending={setSaxoLink.isPending} onSave={handleSaxoLinkSave} />
isPending={setSaxoLink.isPending} onSave={handleSaxoLinkSave}
assetTypes={selected.category === 'fx' ? 'FxSpot' : undefined}
/>
)}
{displayPrice !== undefined && (