internal Trade FindRepoTrade(MLPRepoInfo repoInfo)
 {
     if (repoInfo.DealId > 0)
     {
         var allTrades = Env.Current.Trade.GetTradesByPropertyLike(sMurexTradeIdProperty, repoInfo.DealId.ToString());
         foreach (var trade in allTrades)
         {
             if (trade.GetProperty(sMurexTradeIdProperty) == repoInfo.DealId.ToString() && trade.Status != "Canceled")
             {
                 return trade;
             }
         }
     }
     return null;
 }
        public IList<Trade> Import(Stream stream, Market market, IList<Exception> exceps)
        {
            mRepoTemplate = Env.Current.StaticData.GetTemplate(Template.Shared, "Repo", sMLPRepoTemplate);
            mMarket = new Market()
            {
                Setup = Env.Current.MarketData.GetPricingSetup("Symmetry"),
                Time = DateTime.Now
            };
            if (mRepoTemplate == null)
            {
                throw new Exception("Unable to find repo template for booking: " + sMLPRepoTemplate);
            }
            var trades = new List<Trade>();
            try
            {
                var dict = new Dictionary<long, MLPRepoInfo>();
                using (var parser = new TextFieldParser(stream))
                {
                    parser.SetDelimiters(Separator.ToString());
                    var headers = new Dictionary<string, int>();
                    var titles = parser.ReadFields();
                    var idx = 0;
                    if (titles == null)
                    {
                        exceps.Add(new Exception("Header line not found"));
                        return trades;
                    }
                    foreach (var s in titles) headers[s] = idx++;

                    while (!parser.EndOfData)
                    {
                        try
                        {
                            var items = parser.ReadFields();
                            string skipReason = null;
                            MLPRepoInfo repoInfo = new MLPRepoInfo(items, headers, out skipReason);
                            if (!repoInfo.IsValid)
                            {
                                exceps.Add(new Exception("Not a valid Repo trade: " + repoInfo.DealId));
                                continue;
                            }
                            if (repoInfo.Skip)
                            {
                                Logger.Warn("Repo " + repoInfo.DealId + " is skipped. " + skipReason);
                                continue;
                            }
                            var repoTrade = GetOrCreateRepo(repoInfo, exceps);
                            if (repoTrade != null)
                            {
                                trades.Add(repoTrade);
                            }
                        }
                        catch (Exception ex)
                        {
                            exceps.Add(ex);
                        }
                    }
                }
            }
            catch (Exception ex)
            {
                exceps.Add(ex);
            }
            return trades;
        }
        internal Trade GetOrCreateRepo(MLPRepoInfo repoInfo, IList<Exception> exceps)
        {
            try
            {
                var trade = FindRepoTrade(repoInfo);
                var templateProvider = mRepoTemplate.Provider as RepoTemplateProvider;
                String dealStatus = repoInfo.DealStatus ?? "";

                if (trade == null)
                {
                    trade = new Trade();
                    mRepoTemplate.Apply(trade, SimpleDate.Today, mMarket);
                    templateProvider.FillTrade(trade, mMarket);
                    trade.Status = "New";
                    trade.Action = "Create";
                }
                else if(dealStatus.Equals("Cancel", StringComparison.InvariantCultureIgnoreCase))
                {
                    trade.Action = "Cancel";
                    Logger.Info(String.Format("Cancelling trade MX ID {0} Orchestrade ID {1}",
                        repoInfo.DealId, trade.Id)
                    );
                }
                else
                {
                    trade.Action = "UpdateRef";
                }

                //Only set trade properties for non-Cancelled trades
                if (!trade.Action.Equals("Cancel", StringComparison.InvariantCultureIgnoreCase))
                {
                    var book = Env.Current.StaticData.GetPartyByCode(repoInfo.BookName);
                    if (book == null)
                    {
                        throw new Exception(String.Format("Unable to find book {0} to book repo MXID {1}!", repoInfo.BookName, repoInfo.DealId));
                    }
                    var portfolio = book.GetProperty("Portfolio");
                    if (portfolio != repoInfo.Portfolio)
                    {
                        throw new Exception(String.Format("Portfolio name mismatch: {0} vs {1} on repo MX ID {2}!", repoInfo.Portfolio, portfolio, repoInfo.DealId));
                    }
                    trade.BookId = book.Id;
                    trade.TradingDay = repoInfo.TradeDate;
                    trade.TradeTime = repoInfo.InsertGMT;
                    //                trade.SettlementDate = repoInfo.SettlementDate;
                    trade.SettleCurrency = repoInfo.CurrencyOfTrade;

                    var repo = trade.Product as Repo;
                    var product = Env.Current.Trade.GetProductByCode(repoInfo.SecurityType, repoInfo.Security);
                    if (product == null)
                    {
                        throw new Exception(String.Format("Unable to find product with {0} = {1} to book MX ID {2}", repoInfo.SecurityType, repoInfo.Security, repoInfo.DealId));
                    }
                    var templateFields = templateProvider.Fields(trade).ToDictionary(f => f.FieldName, f => f);
                    RepoTemplateProvider.SetSecurity(trade, mMarket, repo, product);
                    repo.Collaterals[0].PriceType = QuotationType.CleanPrice;
                    repo.Collaterals[0].SettleCurrency = product.Currency;

                    var allValues = new Dictionary<string, string>();
                    var shownFields = new List<TemplateField>();

                    // note: load open repos as overnights (open repos keep reappearing on MLP's report evey day until they are terminated)
                    templateProvider.SetFieldValue(trade, templateFields["Currency"], repoInfo.CurrencyOfTrade, shownFields, mMarket, SimpleDate.Today, allValues);
                    templateProvider.SetFieldValue(trade, templateFields["Nominal"], repoInfo.CurrentFace, shownFields, mMarket, SimpleDate.Today, allValues);
                    templateProvider.SetFieldValue(trade, templateFields["RepoType"], (repoInfo.IsReverse ? RepoType.ReverseRepo : RepoType.Repo), shownFields, mMarket, SimpleDate.Today, allValues);
                    templateProvider.SetFieldValue(trade, templateFields["Duration"], /*(repoInfo.OpenRepo ? RepoDuration.Overnight : */RepoDuration.Term, shownFields, mMarket, SimpleDate.Today, allValues);
                    templateProvider.SetFieldValue(trade, templateFields["Trade Price"], repoInfo.StartCleanPrice * 0.01, shownFields, mMarket, SimpleDate.Today, allValues);
                    templateProvider.SetFieldValue(trade, templateFields["Haircut"], (100 - repoInfo.Haircut) * 0.01, shownFields, mMarket, SimpleDate.Today, allValues);
                    templateProvider.SetFieldValue(trade, templateFields["HairCutType"], "DirtyPrice", shownFields, mMarket, SimpleDate.Today, allValues);
                    templateProvider.SetFieldValue(trade, templateFields["Rate"], repoInfo.RepoRate * 0.01, shownFields, mMarket, SimpleDate.Today, allValues);
                    templateProvider.SetFieldValue(trade, templateFields["Currency"], repoInfo.CurrencyOfTrade, shownFields, mMarket, SimpleDate.Today, allValues);
                    templateProvider.SetFieldValue(trade, templateFields["Is Fixed"], "true"/*(repoInfo.VariableRate ? "false" : "true")*/, shownFields, mMarket, SimpleDate.Today, allValues);
                    if (!repoInfo.OpenRepo)
                    {
                        templateProvider.SetFieldValue(trade, templateFields["StartDate"], repoInfo.StartDate.ToDateTime(), shownFields, mMarket, SimpleDate.Today, allValues);
                        templateProvider.SetFieldValue(trade, templateFields["EndDate"], repoInfo.EndDate.ToDateTime(), shownFields, mMarket, SimpleDate.Today, allValues);
                    }
                    else
                    {
                        // open repos are split into daily repos on MLP reports but there is no link to the original repo, so we have to guess the effective dates
                        var calendar = CalendarHelper.Get("WE"); // MLP repo follow NY calendar
                        var startDate = _effectiveTime.Date; // default T0 open repo allocation
                        if (repoInfo.StartDate.ToDateTime() > startDate) // sometimes we get a forward open repo
                        {
                            startDate = repoInfo.StartDate.ToDateTime();
                        }
                        var endDate = new SimpleDate(startDate).NextBusinessDay(calendar).ToDateTime();
                        templateProvider.SetFieldValue(trade, templateFields["StartDate"], startDate, shownFields, mMarket, SimpleDate.Today, allValues);
                        templateProvider.SetFieldValue(trade, templateFields["EndDate"], endDate, shownFields, mMarket, SimpleDate.Today, allValues);
                    }
                    repo.Cash.Leg.PaymentMarketPlaces = "WE";

                    templateProvider.FillTrade(trade, mMarket);
                    TradeEnrichHelper.Enrich(trade, "Repo");

                    trade.Source = "SymmetryMLPRepoImport";
                    trade.SetProperty(sMurexTradeIdProperty, repoInfo.DealId.ToString());
                    trade.SetProperty("TemplateName", sMLPRepoTemplate);

                    Logger.Info("Creating trade MX ID " + repoInfo.DealId);
                }

                //Env.Current.Trade.SaveTrade(trade); - will be saved by OT
                return trade;
            }
            catch (Exception ex)
            {
                exceps.Add(ex);
                return null;
            }
        }