using Qdp.ComputeService.Data.CommonModels.MarketInfos; using Qdp.ComputeService.Data.CommonModels.MarketInfos.CurveDefinitions; using Qdp.Foundation.Implementations; using Qdp.Pricing.Base.Enums; using Qdp.Pricing.Base.Implementations; using Qdp.Pricing.Base.Interfaces; using Qdp.Pricing.Base.Utilities; using Qdp.Pricing.Ecosystem.Market; using Qdp.Pricing.Ecosystem.Utilities; using Qdp.Pricing.Library.Common.Market; using Qdp.Pricing.Library.Common.MathMethods.VolTermStructure; using YLErp.DBModels; namespace YLErp.QdpModule { public class PrebuiltQdpMarketProxy : IQdpMarketProxy { public PrebuiltQdpMarketProxy() { _prebuiltQdpMarkets = new Dictionary(); } public void SaveVolSurface(VolSurfaceWrap wrap) { if (wrap is null) { throw new ArgumentNullException(nameof(wrap)); } if (string.IsNullOrEmpty(wrap.ValueDate)) { throw new ArgumentNullException("ValueDate"); } if (!_prebuiltQdpMarkets.ContainsKey(wrap.ValueDate)) { CreateMarket(wrap.ValueDate); } lock (_prebuiltQdpMarkets[wrap.ValueDate]) { _prebuiltQdpMarkets[wrap.ValueDate].VolSurfaces[wrap.VolSurfaceName] = wrap.VolSurface; } } public virtual void RemoveVolSurface(string valueDate, string volSurfaceName) { if (_prebuiltQdpMarkets.ContainsKey(valueDate)) { lock (_prebuiltQdpMarkets[valueDate]) { var volSurfaceKey = volSurfaceName.GenerateVolSurfaceKey(); if (_prebuiltQdpMarkets[valueDate].VolSurfaces.ContainsKey(volSurfaceKey)) { _prebuiltQdpMarkets[valueDate].VolSurfaces.Remove(volSurfaceKey); } } } } public virtual bool SaveSkewMapBaseVolSurface(string valueDate, string underlyingTicker, SkewMapBaseVolSurface baseVolSurface) { if (!_prebuiltQdpMarkets.ContainsKey(valueDate)) { CreateMarket(valueDate); } lock (_prebuiltQdpMarkets[valueDate]) { var volSurfaceName = underlyingTicker.GenerateVolSurfaceKey(); _prebuiltQdpMarkets[valueDate].SkewMapBaseVolSurfaces[volSurfaceName] = baseVolSurface; } return true; } public virtual SkewMapBaseVolSurface GetSkewMapBaseVolSurface(string valueDate, string underlyingTicker) { if (_prebuiltQdpMarkets.ContainsKey(valueDate)) { var volSurfaceName = underlyingTicker.GenerateVolSurfaceKey(); if (_prebuiltQdpMarkets[valueDate].SkewMapBaseVolSurfaces.ContainsKey(volSurfaceName)) { return _prebuiltQdpMarkets[valueDate].SkewMapBaseVolSurfaces[volSurfaceName]; } } return null; } public virtual bool SaveCorrelationSurface(string valueDate, string[] underlyingTickers, double correlation) { var date = valueDate.ToDate(); var marketName = date.ToString(); var corrName = underlyingTickers.Length > 1 ? (underlyingTickers[0] + "_" + underlyingTickers[1]) : underlyingTickers[0]; var corrSurface = new CorrSurfMktData(corrName, correlation); if (_prebuiltQdpMarkets.ContainsKey(valueDate)) { lock (_prebuiltQdpMarkets[valueDate]) { _prebuiltQdpMarkets[valueDate].CorrSurfaces[corrName] = corrSurface.ToImpliedVolSurface(date); } return true; } else { return false; } } public virtual bool CreateMarket(string valueDate) { if (!_prebuiltQdpMarkets.ContainsKey(valueDate)) { lock (this) { if (!_prebuiltQdpMarkets.ContainsKey(valueDate)) { try { _prebuiltQdpMarkets[valueDate] = new PrebuiltQdpMarket(valueDate, valueDate.ToDate()); AddYieldCurve(MarketProxy.ConstantZeroCurve, valueDate, BLL.Calculation.CalculatorHelper.CreateConstantRiskFreeCurve(MarketProxy.ConstantZeroCurve, 0.0)); } catch (Exception) { } } } } return true; } public virtual QdpMarket GetQdpMarket(string valueDate) { return _prebuiltQdpMarkets.ContainsKey(valueDate) ? _prebuiltQdpMarkets[valueDate] : null; } public virtual bool LoadMarket(MarketInfo marketInfo) { return true; } public virtual void AddStockPrice(string ticker, string valueDate, double price) { if (!_prebuiltQdpMarkets.ContainsKey(valueDate)) { CreateMarket(valueDate); } lock (_prebuiltQdpMarkets[valueDate]) { _prebuiltQdpMarkets[valueDate].StockPrices[ticker] = price; } } public void AddYieldCurve(string curveName, DateTime valueDate, InstrumentCurveDefinition definition) { AddYieldCurve(curveName, valueDate.ToString("yyyy-MM-dd"), definition); } public virtual void AddYieldCurve(string curveName, string valueDate, InstrumentCurveDefinition definition) { var date = valueDate.ToDate(); if (!_prebuiltQdpMarkets.ContainsKey(valueDate)) { CreateMarket(valueDate); } lock (_prebuiltQdpMarkets[valueDate]) { _prebuiltQdpMarkets[valueDate].YieldCurves[curveName] = BuildYieldCurve(date, definition); } } public virtual void RemoveYieldCurve(string curveName, string valueDate) { if (_prebuiltQdpMarkets.ContainsKey(valueDate) && _prebuiltQdpMarkets[valueDate].YieldCurves.ContainsKey(curveName)) { lock (_prebuiltQdpMarkets[valueDate]) { _prebuiltQdpMarkets[valueDate].YieldCurves.Remove(curveName); } } } public virtual double GetVol(string valueDate, string underlyingTicker, double strike, string maturityDate, double spot) { var date = valueDate.ToDate(); var marketName = date.ToString(); var volSurfaceName = underlyingTicker.GenerateVolSurfaceKey(); if (_prebuiltQdpMarkets.ContainsKey(valueDate) && _prebuiltQdpMarkets[valueDate].VolSurfaces.ContainsKey(volSurfaceName)) { return _prebuiltQdpMarkets[valueDate].VolSurfaces[volSurfaceName].GetValue(maturityDate.ToDate(), strike, spot); } else { return double.NaN; } } public static YieldCurve BuildYieldCurve(Date curveDate, InstrumentCurveDefinition curveDefinition) { YieldCurve instrumentCurve = null; try { if (curveDefinition.RateDefinitions.All( x => x.InstrumentType.ToInstrumentType() == InstrumentType.Dummy || x.InstrumentType.ToInstrumentType() == InstrumentType.None)) { if (curveDefinition.RateDefinitions.All(x => x.IsTerm())) { instrumentCurve = new YieldCurve( curveDefinition.Name, curveDate, curveDefinition.RateDefinitions.Select(x => Tuple.Create((ITerm)new Term(x.Tenor), x.Rate)).ToArray(), curveDefinition.CurveConvention.BusinessDayConvention.ToBda(), curveDefinition.CurveConvention.DayCount.ToDayCountImpl(), curveDefinition.CurveConvention.Calendar.ToCalendarImpl(), curveDefinition.CurveConvention.Currency.ToCurrencyCode(), curveDefinition.CurveConvention.Compound.ToCompound(), curveDefinition.CurveConvention.Interpolation.ToInterpolation(), curveDefinition.Trait.ToYieldCurveTrait() ); } else { instrumentCurve = new YieldCurve( curveDefinition.Name, curveDate, curveDefinition.RateDefinitions.Select(x => Tuple.Create(new Date(DateTime.Parse(x.Tenor)), x.Rate)).ToArray(), curveDefinition.CurveConvention.BusinessDayConvention.ToBda(), curveDefinition.CurveConvention.DayCount.ToDayCountImpl(), curveDefinition.CurveConvention.Calendar.ToCalendarImpl(), curveDefinition.CurveConvention.Currency.ToCurrencyCode(), curveDefinition.CurveConvention.Compound.ToCompound(), curveDefinition.CurveConvention.Interpolation.ToInterpolation(), curveDefinition.Trait.ToYieldCurveTrait() ); } } } catch (Exception e) { LogFactory.GetLogger().Error("BuildYieldCurve:" + curveDefinition.Name, e); } return instrumentCurve; } public virtual void Clear() { _prebuiltQdpMarkets.Clear(); } private Dictionary _prebuiltQdpMarkets; } }