/// <summary>
        /// SaveBalanceSheet
        /// </summary>
        /// <param name="contract"></param>
        /// <param name="fmpSymbol"></param>
        /// <param name="xmlDocument"></param>
        /// <param name="date"></param>
        private void SaveBalanceSheet(Contract contract, string fmpSymbol, FundamentalsXmlDocument xmlDocument, string date)
        {
            if (DataContext.Instance.BalanceSheets.Any(i => i.Symbol == fmpSymbol && i.Date == date))
            {
                LogCurrent.Add($"Balance sheet for {contract.Company} ad date {date} already exists in database.");
                return;
            }

            if (xmlDocument.Equity == 0)
            {
                LogCurrent.Add($"No IB data for balance sheet for {contract.Company} for year {date}.");
                return;
            }

            var balanceSheet = new BalanceSheet()
            {
                Symbol = fmpSymbol,
                Date   = date,
                TotalStockholdersEquity = xmlDocument.Equity
            };

            try
            {
                DataContext.Instance.BalanceSheets.Add(balanceSheet);
                DataContext.Instance.SaveChanges();
                LogCurrent.Add($"OK! Balance sheet for {contract.Company} {date} saved in database.");
            }
            catch (Exception exception)
            {
                LogCurrent.Add(exception.ToString());
            }
        }
        /// <summary>
        /// SaveCashFlowStatement
        /// </summary>
        /// <param name="contract"></param>
        /// <param name="fmpSymbol"></param>
        /// <param name="xmlDocument"></param>
        /// <param name="date"></param>
        private void SaveCashFlowStatement(Contract contract, string fmpSymbol, FundamentalsXmlDocument xmlDocument, string date)
        {
            if (DataContext.Instance.CashFlowStatements.Any(i => i.Symbol == fmpSymbol && i.Date == date))
            {
                LogCurrent.Add($"Cash flow statement for {contract.Company} and date {date} already exists in database.");
                return;
            }

            if (xmlDocument.NetIncomeFromCashStatement == 0 && xmlDocument.OperatingCashFlow == 0 && xmlDocument.InvestmentsInPropertyPlantAndEquipment == 0)
            {
                LogCurrent.Add($"No IB data for cash flow statement for {contract.Company} for year {date}.");
                return;
            }

            var cashFlowStatement = new CashFlowStatement()
            {
                Symbol            = fmpSymbol,
                Date              = date,
                NetIncome         = xmlDocument.NetIncomeFromCashStatement,
                OperatingCashFlow = xmlDocument.OperatingCashFlow,
                InvestmentsInPropertyPlantAndEquipment = xmlDocument.InvestmentsInPropertyPlantAndEquipment
            };

            try
            {
                DataContext.Instance.CashFlowStatements.Add(cashFlowStatement);
                DataContext.Instance.SaveChanges();
                LogCurrent.Add($"OK! Cash flow statement for {contract.Company} {date} saved in database.");
            }
            catch (Exception exception)
            {
                LogCurrent.Add(exception.ToString());
            }
        }
        /// <summary>
        /// ResponseHandlerSymbolSamples
        /// </summary>
        /// <param name="obj"></param>
        private void ResponseHandlerSymbolSamples(IBSampleApp.messages.SymbolSamplesMessage obj)
        {
            BackgroundLog = Brushes.White;
            var message = string.Empty;

            LogCurrent.Add($"{obj.ContractDescriptions.Count()} symbols found for company {CurrentCompany}. {CompaniesList.Count()} companies more.");
            CompaniesList.Remove(CurrentCompany);
            var contracts = SymbolManager.FilterSymbols(CurrentCompany, obj, ExchangeIbSelected);

            LogCurrent.Add($"{contracts.Count()} symbols filtered out for company {CurrentCompany}");

            try
            {
                if (!contracts.Any())
                {
                    ProcessNotResolved();
                    ProcessDatabaseBatch();
                    return;
                }

                ProcessResolved(contracts);
                ProcessDatabaseBatch();
            }
            catch (Exception exception)
            {
                LogCurrent.Add(exception.ToString());
            }
        }
        /// <summary>
        /// SaveIncomeStatement
        /// </summary>
        /// <param name="contract"></param>
        /// <param name="fmpSymbol"></param>
        /// <param name="xmlDocument"></param>
        /// <param name="date"></param>
        private void SaveIncomeStatement(Contract contract, string fmpSymbol, FundamentalsXmlDocument xmlDocument, string date)
        {
            if (DataContext.Instance.IncomeStatements.Any(i => i.Symbol == fmpSymbol && i.Date == date))
            {
                LogCurrent.Add($"Income statement for {contract.Company} for year {date} already exists in database.");
                return;
            }

            if (xmlDocument.Revenue == 0 && xmlDocument.OperatingIncome == 0 && xmlDocument.Eps == 0 && xmlDocument.NetIncome == 0)
            {
                LogCurrent.Add($"No IB data for income statement for {contract.Company} for year {date}.");
                return;
            }

            var incomeStatement = new IncomeStatement()
            {
                Symbol          = fmpSymbol,
                Date            = date,
                Revenue         = xmlDocument.Revenue,
                OperatingIncome = xmlDocument.OperatingIncome,
                Epsdiluted      = xmlDocument.Eps,
                NetIncome       = xmlDocument.NetIncome
            };

            try
            {
                DataContext.Instance.IncomeStatements.Add(incomeStatement);
                DataContext.Instance.SaveChanges();
                LogCurrent.Add($"OK! Income statement for {contract.Company} {date} saved in database.");
            }
            catch (Exception exception)
            {
                LogCurrent.Add(exception.ToString());
            }
        }
 /// <summary>
 /// ProcessDatabaseBatch
 /// </summary>
 private void ProcessDatabaseBatch()
 {
     if (CompaniesProcessed.Count() > 0 && CompaniesProcessed.Count() % Convert.ToInt32(Configuration.Instance["BatchSizeDatabase"]) == 0 ||
         CompaniesList.Count() == 0)
     {
         DataContext.Instance.SaveChanges();
         LogCurrent.Add("OK! Current batch saved in database.");
     }
 }
        /// <summary>
        /// ImportContracts
        /// </summary>
        /// <param name="p"></param>
        private async Task CommandImportContractsAsync(object p)
        {
            if (String.IsNullOrWhiteSpace(ExchangeIbSelected))
            {
                LogCurrent.Add($"ERROR! Exchange must be selected.");
                return;
            }

            LogCurrent = LogSymbols;
            LogCurrent.Clear();
            BackgroundLog = Brushes.Gray;
            await Task.Run(() =>
            {
                try
                {
                    string[] companiesArray = null;
                    int delay = 0;
                    Dispatcher.Invoke(() =>
                    {
                        delay              = Convert.ToInt32(Configuration.Instance["DelayMathingSymbols"]);
                        companiesArray     = CompaniesForSymbolResolution.ToArray();
                        CompaniesList      = companiesArray.ToList();
                        SymbolProcessed    = new List <string>();
                        CompaniesProcessed = new List <string>();
                    });

                    foreach (var company in companiesArray)
                    {
                        CurrentCompany = company;
                        IbClient.Instance.LookForSymbols(CurrentCompany);
                        Thread.Sleep(delay);
                    }
                }
                catch (Exception exception)
                {
                    Dispatcher.Invoke(() => { LogCurrent.Add(exception.ToString()); });
                }
            });

            if (ConnectedToIb)
            {
                LogCurrent.Add($"OK! Import completed.");
                DataContext.Instance.SaveChanges();
                LogCurrent.Add("OK! All contracts saved in database.");
                IbClient.Instance.Disonnect();

                UpdateDbState();
                InventoryText = GenerateInventoryText();
                UpdateCompaniesForSymbolResolution(ExchangesFmpSelected);
            }
            else
            {
                LogCurrent.Add($"ERROR! Error while connection to IB server.");
            }
        }
        /// <summary>
        /// ImportFundamentals
        /// </summary>
        /// <param name="p"></param>
        private async Task CommandImportFundamentalsAsync(object p)
        {
            LogCurrent = LogFundamentals;
            LogCurrent.Clear();
            BackgroundLog = Brushes.Gray;

            await Task.Run(() =>
            {
                try
                {
                    List <Contract> contractsToProcess = new List <Contract>();
                    int delay = 0;
                    Dispatcher.Invoke(() =>
                    {
                        contractsToProcess = ContractsForIbFundamentalsQueries();
                        ContractList       = new List <Contract>(contractsToProcess);
                        ContractsProcessed = new List <Contract>();
                        delay = Convert.ToInt32(Configuration.Instance["DelayFundamentals"]);
                    });

                    foreach (var contract in contractsToProcess)
                    {
                        CurrentContract = contract;
                        IbClient.Instance.RequestFundamentals(contract);
                        Thread.Sleep(delay);
                    }
                }
                catch (Exception exception)
                {
                    Dispatcher.Invoke(() => { LogCurrent.Add(exception.ToString()); });
                }
            });

            if (ConnectedToIb)
            {
                LogCurrent.Add($"OK! Import completed.");
                IbClient.Instance.Disonnect();

                UpdateDbState();
                InventoryText = GenerateInventoryText();
                UpdateCompaniesForFundamenatals(SelectTop1000);
            }
            else
            {
                LogCurrent.Add($"ERROR! Error while connection to IB server.");
            }
        }
        /// <summary>
        /// ProcessNotResolved
        /// </summary>
        private void ProcessNotResolved()
        {
            if (!CompaniesProcessed.Any(s => s.ToUpper() == CurrentCompany.ToUpper()))
            {
                if (DataContext.Instance.NotResolved.Any(n => n.Company == CurrentCompany))
                {
                    LogCurrent.Add($"Company {CurrentCompany} exists already in database table NotResolved.");
                    return;
                }

                DataContext.Instance.NotResolved.Add(new NotResolved {
                    Company = CurrentCompany
                });
            }

            CompaniesProcessed.Add(CurrentCompany);
        }
        /// <summary>
        /// ProcessResolved
        /// </summary>
        /// <param name="contracts"></param>
        private void ProcessResolved(IList <Contract> contracts)
        {
            for (int i = 0; i < contracts.Count(); i++)
            {
                Contract contract = contracts[i];
                if (!SymbolProcessed.Any(s => s.ToUpper() == contract.Symbol.ToUpper()))
                {
                    if (DataContext.Instance.Contracts.Any(c => c.Symbol == contract.Symbol))
                    {
                        LogCurrent.Add($"Symbol {contract.Symbol} exists already in database table Contracts. Adding record in table NotUnique.");
                        DataContext.Instance.NotUnique.Add(new NotUnique {
                            Symbol = contract.Symbol, Company = contract.Company
                        });
                        continue;
                    }
                    DataContext.Instance.Contracts.Add(contract);
                    SymbolProcessed.Add(contract.Symbol);
                }
            }

            CompaniesProcessed.Add(CurrentCompany);
        }
        /// <summary>
        /// ResponseHandlerFundamentalData
        /// </summary>
        /// <param name="obj"></param>
        private void ResponseHandlerFundamentalData(IBSampleApp.messages.FundamentalsMessage obj)
        {
            BackgroundLog = Brushes.White;
            var message = string.Empty;

            LogCurrent.Add($"Processing {CurrentContract.Company} ... {ContractList.Count()} companies more.");
            ContractList.Remove(CurrentContract);

            string fmpSymbol = QueryFactory.SymbolByCompanyNameQuery.Run(CurrentContract.Company);

            if (string.IsNullOrWhiteSpace(fmpSymbol))
            {
                LogCurrent.Add($"ERROR! FMP symbol for {CurrentContract.Company} could not be found.");
                return;
            }

            foreach (string date in Dates)
            {
                FundamentalsXmlDocument xmlDocument = XmlFactory.Instance.CreateXml(obj, date);
                SaveIncomeStatement(CurrentContract, fmpSymbol, xmlDocument, date);
                SaveBalanceSheet(CurrentContract, fmpSymbol, xmlDocument, date);
                SaveCashFlowStatement(CurrentContract, fmpSymbol, xmlDocument, date);
            }
        }
 /// <summary>
 /// ResponseHandlerConnectionClosed
 /// </summary>
 private void ResponseHandlerConnectionClosed()
 {
     ConnectedToIb = false;
     LogCurrent.Add($"Connection to IB server closed.");
 }