15QuantLib::ext::shared_ptr<CurrencyHedgedEquityIndexDecomposition>
17 const QuantLib::ext::shared_ptr<CurveConfigurations>&
curveConfigs) {
18 QuantLib::ext::shared_ptr<CurrencyHedgedEquityIndexReferenceDatum> indexRefData;
19 QuantLib::ext::shared_ptr<EquityIndexReferenceDatum> underlyingRefData;
20 std::map<std::string, std::pair<double, std::string>> currencyWeightsAndFxIndexNames;
23 if (refDataMgr->hasData(
"CurrencyHedgedEquityIndex",
name))
24 indexRefData = QuantLib::ext::dynamic_pointer_cast<CurrencyHedgedEquityIndexReferenceDatum>(
25 refDataMgr->getData(
"CurrencyHedgedEquityIndex",
name));
27 if (indexRefData !=
nullptr && refDataMgr->hasData(
"EquityIndex", indexRefData->underlyingIndexName()))
28 underlyingRefData = QuantLib::ext::dynamic_pointer_cast<EquityIndexReferenceDatum>(
29 refDataMgr->getData(
"EquityIndex", indexRefData->underlyingIndexName()));
32 if (indexRefData ==
nullptr || underlyingRefData ==
nullptr) {
37 std::map<std::string, double> currencyWeights;
38 std::string indexCurrency;
39 std::string underlyingIndexCurrency;
40 std::string fxIndexName;
44 indexCurrency =
curveConfigs->equityCurveConfig(indexRefData->id())->currency();
46 WLOG(
"Can not find curveConfig for " << indexRefData->id() <<
" and can not determine the index currecy");
54 std::string underlyingIndexName = indexRefData->underlyingIndexName();
55 underlyingIndexCurrency =
56 curveConfigs->equityCurveConfig(indexRefData->underlyingIndexName())->currency();
58 auto fxIndexIt = indexRefData->fxIndexes().find(underlyingIndexCurrency);
59 if (fxIndexIt != indexRefData->fxIndexes().end()) {
60 fxIndexName = fxIndexIt->second;
62 fxIndexName =
"FX-GENERIC-" + indexCurrency +
"-" + underlyingIndexCurrency;
66 QuantLib::Date refDate =
69 std::map<std::string, double> underlyingIndexWeightsAtRebalancing;
71 if (indexRefData->currencyWeights().empty()) {
72 QuantLib::ext::shared_ptr<ReferenceDatum> undIndexRefDataAtRefDate;
74 undIndexRefDataAtRefDate = refDataMgr->getData(
"EquityIndex", underlyingIndexName, refDate);
78 if (undIndexRefDataAtRefDate) {
79 underlyingIndexWeightsAtRebalancing =
80 QuantLib::ext::dynamic_pointer_cast<EquityIndexReferenceDatum>(undIndexRefDataAtRefDate)->underlyings();
83 underlyingIndexWeightsAtRebalancing = indexRefData->currencyWeights();
86 if (underlyingIndexWeightsAtRebalancing.empty()) {
87 currencyWeights[underlyingIndexCurrency] = 1.0;
89 for (
const auto& [
name, weight] : underlyingIndexWeightsAtRebalancing) {
93 auto eqCcy = ecc->currency();
94 currencyWeights[eqCcy] += weight;
97 currencyWeights[underlyingIndexCurrency] += weight;
103 for (
const auto& [currency, weight] : currencyWeights) {
104 if (currency != indexCurrency) {
105 auto defaultIndexIt = indexRefData->fxIndexes().find(currency);
106 if (defaultIndexIt != indexRefData->fxIndexes().end()) {
107 currencyWeightsAndFxIndexNames[currency] = std::make_pair(weight, defaultIndexIt->second);
109 currencyWeightsAndFxIndexNames[currency] =
110 std::make_pair(weight,
"FX-GENERIC-" + indexCurrency +
"-" + currency);
114 return QuantLib::ext::make_shared<CurrencyHedgedEquityIndexDecomposition>(
name, indexRefData, underlyingRefData,
115 indexCurrency, underlyingIndexCurrency,
116 fxIndexName, currencyWeightsAndFxIndexNames);
120 const QuantLib::ext::shared_ptr<CurrencyHedgedEquityIndexReferenceDatum>& refData,
121 const QuantLib::Date& asof) {
123 if (hedgingDate == QuantLib::Date()) {
124 return QuantLib::Date();
126 return refData->hedgeCalendar().advance(hedgingDate, -refData->referenceDateOffset() * QuantLib::Days,
127 QuantLib::Preceding);
132 const QuantLib::ext::shared_ptr<CurrencyHedgedEquityIndexReferenceDatum>& refData,
133 const QuantLib::Date& asof) {
134 if (refData->rebalancingStrategy() ==
136 QuantLib::Date lastBusinessDayOfCurrentMonth = QuantLib::Date::endOfMonth(asof);
137 lastBusinessDayOfCurrentMonth =
138 refData->hedgeCalendar().adjust(lastBusinessDayOfCurrentMonth, QuantLib::Preceding);
139 if (asof == lastBusinessDayOfCurrentMonth) {
142 return refData->hedgeCalendar().advance(QuantLib::Date(1, asof.month(), asof.year()), -1 * QuantLib::Days,
143 QuantLib::Preceding);
146 return QuantLib::Date();
158 const double quantity,
const QuantLib::Date& asof,
const QuantLib::ext::shared_ptr<ore::data::Market>& todaysMarket,
const double shiftsize)
const {
160 std::map<std::string, double> fxRisks;
161 auto indexCurve = todaysMarket->equityCurve(
indexName());
164 double adjustmentFactor = 1.0;
167 adjustmentFactor = underlyingCurve->fixing(asof) / underlyingCurve->fixing(
rebalancingDate(asof));
171 double weight = weightAndIndex.first;
174 double forwardNotional =
175 quantity * adjustmentFactor * weight * indexCurve->fixing(refDate) / fxIndex->fixing(refDate);
176 fxRisks[ccy] = shiftsize * forwardNotional * fxIndex->fixing(asof);
183 const QuantLib::Date& asof,
184 const QuantLib::ext::shared_ptr<ore::data::Market>& todaysMarket)
const {
185 auto indexCurve = todaysMarket->equityCurve(
indexName());
190 double hedgedUnitPrice = (hedgedExposure / quantity);
192 double scaling = hedgedUnitPrice / indexCurve->fixing(asof);
194 double fxReturn = fxIndex->fixing(asof) / fxIndex->fixing(rebalanceDt);
196 double underlyingIndexReturn = underlyingCurve->equitySpot()->value() / underlyingCurve->fixing(rebalanceDt);
198 double unhedgedUnitPrice= indexCurve->fixing(rebalanceDt) * underlyingIndexReturn * fxReturn;
200 return scaling * quantity * unhedgedUnitPrice;
204 const QuantLib::Date& asof, std::map<std::string, RequiredFixings::FixingDates>& fixings)
const {
208 fixings[IndexNameTranslator::instance().oreName(
indexName())].addDate(rebalancingDt,
false);
209 fixings[IndexNameTranslator::instance().oreName(
indexName())].addDate(referenceDt,
false);
212 fixings[IndexNameTranslator::instance().oreName(
underlyingIndexName())].addDate(rebalancingDt,
false);
213 fixings[IndexNameTranslator::instance().oreName(
underlyingIndexName())].addDate(referenceDt,
false);
215 fixings[
fxIndexName()].addDate(referenceDt,
false);
216 fixings[
fxIndexName()].addDate(rebalancingDt,
false);
219 fixings[
name.second].addDate(referenceDt,
false);
220 fixings[
name.second].addDate(rebalancingDt,
false);
const std::string & underlyingIndexName() const
QuantLib::Date referenceDate(const QuantLib::Date &asof) const
double unhedgedSpotExposure(double hedgedExposure, const double quantity, const QuantLib::Date &asof, const QuantLib::ext::shared_ptr< ore::data::Market > &todaysMarket) const
const std::string & indexName() const
QuantLib::ext::shared_ptr< ore::data::CurrencyHedgedEquityIndexReferenceDatum > indexRefData() const
const std::map< std::string, std::pair< double, std::string > > & currencyWeightsAndFxIndexNames() const
std::string underlyingIndexCurrency_
std::map< std::string, double > fxSpotRiskFromForwards(const double quantity, const QuantLib::Date &asof, const QuantLib::ext::shared_ptr< ore::data::Market > &todaysMarket, const double shiftsize) const
const std::string & fxIndexName() const
QuantLib::Date rebalancingDate(const QuantLib::Date &asof) const
std::string indexCurrency_
QuantLib::ext::shared_ptr< ore::data::CurrencyHedgedEquityIndexReferenceDatum > indexRefData_
void addAdditionalFixingsForEquityIndexDecomposition(const QuantLib::Date &asof, std::map< std::string, RequiredFixings::FixingDates > &fixings) const
Helper function used for the index decompositon.
QuantLib::ext::shared_ptr< FxIndex > parseFxIndex(const string &s, const Handle< Quote > &fxSpot, const Handle< YieldTermStructure > &sourceYts, const Handle< YieldTermStructure > &targetYts, const bool useConventions)
Convert std::string to QuantExt::FxIndex.
translates between QuantLib::Index::name() and ORE names
#define WLOG(text)
Logging Macro (Level = Warning)
QuantLib::ext::shared_ptr< CurrencyHedgedEquityIndexDecomposition > loadCurrencyHedgedIndexDecomposition(const std::string &name, const QuantLib::ext::shared_ptr< ReferenceDataManager > &refDataMgr, const QuantLib::ext::shared_ptr< CurveConfigurations > &curveConfigs)
Serializable Credit Default Swap.
vector< string > curveConfigs