"""The sample demonstrates DOM data receiving via instrument subscription"""

import logging
import threading

import win32com.client

import CELEnvironment

#region Settings

# Replace it with enabled symbol
SYMBOL = "DD"

# Logging settings: specify log level and log format here.
# Set log level to DEBUG to see more internal messages.
# See more information about logging lib usage: https://docs.python.org/3/howto/logging-cookbook.html
CELEnvironment.LOG_LEVEL = logging.INFO
# CELEnvironment.LOG_FORMAT = ...

# CELEnvironment.SinkInternal uses own LOG_LEVEL (which is inherited from the global one) and own LOG_FORMAT.
# You can redefine them as follows:
# CELEnvironment.SinkInternal.LOG_LEVEL = logging.DEBUG
# CELEnvironment.SinkInternal.LOG_FORMAT = ...

LOG = CELEnvironment.GetLogger()

#endregion


class DOMReceiving(CELEnvironment.CELSinkBase):
    def __init__(self):
        self.eventDone = threading.Event()

    def Init(self, celEnvironment):
        self.celEnvironment = celEnvironment

    def Start(self):
        LOG.info("Request DOM for %s", SYMBOL)
        self.celEnvironment.cqgCEL.NewInstrument(SYMBOL)

        self.eventDone.wait(10)

    def OnDataError(self, cqgError, errorDescription):
        if cqgError is not None:
            error = win32com.client.Dispatch(cqgError)
            LOG.error("OnDataError: Code: %d Description: %s", error.Code, error.Description)

        self.eventDone.set()

    def OnInstrumentResolved(self, symbol, cqgInstrument, cqgError):
        if cqgError is not None:
            error = win32com.client.Dispatch(cqgError)
            LOG.error("OnInstrumentResolved error: Error code: %d Description: %s", error.Code, error.Description)
            self.eventDone.set()
            return

        instrument = win32com.client.Dispatch(cqgInstrument)
        LOG.info("OnInstrumentResolved: Symbol: %s Instrument full name: %s", symbol, instrument.FullName)
        LOG.info("Set data subscription level for DOM data receiving")
        instrument.DataSubscriptionLevel = win32com.client.constants.dsQuotesAndDOM
        LOG.info("Set limit to DOM depth")
        instrument.DOMBookLimit = 10

    def OnInstrumentDOMChanged(self, cqgInstrument, prevAsks, prevBids):
        instrument = win32com.client.Dispatch(cqgInstrument)
        for ask in instrument.DOMAsks:
            if ask.IsValid:
                LOG.info("     ASK Price: %f VolumeFractional %s", ask.Price, ask.VolumeFractional)
        for bid in instrument.DOMBids:
            if bid.IsValid:
                LOG.info("     BID Price: %f VolumeFractional %s", bid.Price, bid.VolumeFractional)


# If CQGCEL.APIConfiguration must be customized then do it in this function
def CustomAPIConfiguration(APIConfiguration):
    APIConfiguration.NewInstrumentMode = False
    APIConfiguration.DOMUpdatesMode = win32com.client.constants.domUMSnapshot
    APIConfiguration.DOMUpdatesPeriod = 1000


if __name__ == "__main__":
    CELEnvironment.Start(DOMReceiving, CustomAPIConfiguration)
