46 lines
1.5 KiB
Python
46 lines
1.5 KiB
Python
from __future__ import annotations
|
|
|
|
from ast import literal_eval
|
|
from typing import Dict
|
|
import logging
|
|
|
|
from models import OrderbookLevel
|
|
|
|
|
|
class OrderbookParser:
|
|
"""Parser for orderbook side text into structured levels.
|
|
|
|
Maintains a price cache for memory efficiency and provides a method to
|
|
parse a side into a dictionary of price -> OrderbookLevel.
|
|
"""
|
|
|
|
def __init__(self, price_cache: dict[float, float] | None = None, debug: bool = False) -> None:
|
|
self._price_cache: dict[float, float] = price_cache or {}
|
|
self._debug = debug
|
|
|
|
def parse_side(self, text: str, side_dict: Dict[float, OrderbookLevel]) -> None:
|
|
"""Parse orderbook side data from text and populate the provided dictionary."""
|
|
if not text or text.strip() == "":
|
|
return
|
|
try:
|
|
arr = literal_eval(text)
|
|
for p, s, lc, oc in arr:
|
|
price = float(p)
|
|
size = float(s)
|
|
price = self._price_cache.get(price, price)
|
|
if size > 0:
|
|
side_dict[price] = OrderbookLevel(
|
|
price=price,
|
|
size=size,
|
|
liquidation_count=int(lc),
|
|
order_count=int(oc),
|
|
)
|
|
except Exception as e:
|
|
if self._debug:
|
|
logging.exception("Error parsing orderbook data")
|
|
logging.debug(f"Text sample: {text[:100]}...")
|
|
else:
|
|
logging.error(f"Failed to parse orderbook data: {type(e).__name__}")
|
|
|
|
|