Skip to content

Watchlists

Track symbols in the right sidebar. Click a symbol to load it on the chart. Add via + button, remove via X, reorder by drag and drop. Multiple watchlists with configurable names.

Configuration

typescript
new ChartSpire({
  watchListEnabled: true,
  watchListAmount: 5,
  watchListLimit: 50,
  watchListHttp: false,
  watchListHttpInterval: 5000,
  watchListHttpBatchSize: 10,
  watchListHttpRetryEnabled: true,
  watchListHttpMaxRetries: 3,
  watchListUseExternalStorage: false,
  enabledSymbolTypes: [SYMBOL_TYPE.STOCKS, SYMBOL_TYPE.CRYPTO],
  // ...
})
OptionTypeDefaultDescription
watchListEnabledbooleanfalseEnable watchlist panel
watchListAmountnumber5Number of watchlists
watchListLimitnumber50Max symbols per watchlist
watchListHttpbooleanfalseUse HTTP polling instead of WebSocket for prices
watchListHttpIntervalnumber5000Poll interval (ms, min: 1000)
watchListHttpBatchSizenumber10Symbols per batch when polling
watchListHttpRetryEnabledbooleantrueRetry on failure
watchListHttpMaxRetriesnumber3Max retries
watchListUseExternalStoragebooleanfalseUse callbacks instead of localStorage

Price Data

WebSocket (default): Uses subscribeSymbol/unsubscribeSymbol for real-time prices.

HTTP polling: Set watchListHttp: true. DataFeed must implement getPrice(symbol, type) returning Promise<number | null>. Polls at watchListHttpInterval (min 1000ms).

Symbol Type Filtering

enabledSymbolTypes restricts which symbol types appear in watchlists and search. Omit or use [] for all types.

typescript
enabledSymbolTypes: [SYMBOL_TYPE.STOCKS, SYMBOL_TYPE.CRYPTO]

External storage warning: With enabledSymbolTypes and external storage, the frontend only loads and sends enabled types. If the backend overwrites the full watchlist on save, symbols of other types will be lost. Backend should merge by watchlist name instead of full replace.

External Storage

External storage persists watchlist data to your backend instead of localStorage. Set callbacks before creating the chart:

typescript
import ChartSpire, { setWatchListChangeCallback, setGetWatchListsCallback } from '@chartspire/chartspire'

setWatchListChangeCallback((watchlist) => {
  fetch('/api/watchlist', {
    method: 'POST',
    headers: { 'Content-Type': 'application/json' },
    body: JSON.stringify(watchlist)
  })
})

setGetWatchListsCallback(async () => {
  const res = await fetch('/api/watchlist')
  return res.ok ? await res.json() : null
})

new ChartSpire({
  watchListEnabled: true,
  watchListUseExternalStorage: true,
  // ...
})

Data Structure

SymbolInfoMap = Record<string, Symbol[]> — watchlist name → array of symbols.

typescript
{
  "WatchList 1": [
    { symbol: "AAPL", type: "stocks", name: "Apple Inc", exchange: "NASDAQ" },
    { symbol: "MSFT", type: "stocks", name: "Microsoft", exchange: "NASDAQ" }
  ],
  "WatchList 2": [
    { symbol: "BTCUSDT", type: "crypto", name: "Bitcoin/USDT", exchange: "binance" }
  ]
}

Symbol type uses SYMBOL_TYPE values: 'stocks', 'crypto', 'forex', 'futures', etc.

Limits

  • Max symbols per watchlist: watchListLimit (default 50)
  • No duplicate symbols in the same watchlist
  • localStorage: ~5MB per domain (when not using external storage)