Application¶
Service¶
wayfault.application.service ¶
The :class:WrongWayRiskService orchestration.
WrongWayRiskService ¶
Orchestrates the WWR estimation through the outbound ports.
The service contains no I/O and no numpy-free leakage of external concerns: everything outside the domain is reached through the request's ports.
estimate ¶
Run the full WWR pipeline and return a :class:WWRResult.
Source code in src/wayfault/application/service.py
DTOs¶
wayfault.application.dto ¶
Data-transfer objects for the WWR use case.
WWRRequest
dataclass
¶
WWRRequest(exposure: ExposureSource, credit: CreditCurveSource, model: DependenceModel, discount: ndarray | None = None, pfe_quantile: float = 0.95)
Inputs for a WWR estimation.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
exposure
|
ExposureSource
|
Port supplying the exposure cube. |
required |
credit
|
CreditCurveSource
|
Port supplying the credit curve. |
required |
model
|
DependenceModel
|
The dependence model to apply. |
required |
discount
|
ndarray | None
|
Optional discount factors on the grid (defaults to 1.0). |
None
|
pfe_quantile
|
float
|
Quantile used for the PFE profile. |
0.95
|
WWRResult
dataclass
¶
WWRResult(baseline_cva: float, wwr_cva: float, alpha: float, classification: WWRClass, tenors: ndarray, epe: ndarray, conditional_ee: ndarray, pfe: ndarray, eepe: float, ead: float, uplift_pct: float, ee_ratio: ndarray, ee_hazard_corr: float, model: str, params: dict[str, float] = dict())
Outputs of a WWR estimation.
Attributes:
| Name | Type | Description |
|---|---|---|
baseline_cva, wwr_cva, alpha |
The independent CVA, the WWR-adjusted CVA, and their ratio. |
|
classification |
WWRClass
|
WWR / RWR / NEUTRAL label. |
tenors |
ndarray
|
The tenor grid year-fractions (x-axis for the per-tenor profiles). |
epe, conditional_ee, pfe |
Per-tenor profiles (numpy arrays). |
|
eepe |
float
|
Effective EPE scalar. |
ead |
float
|
|
uplift_pct, ee_ratio, ee_hazard_corr |
Diagnostics. |
|
model, params |
Metadata about the dependence model used. |
to_dict ¶
Return a JSON-serialisable dictionary representation.
Source code in src/wayfault/application/dto.py
Inverse solvers¶
wayfault.application.inverse ¶
Inverse WWR solvers (prescriptive analytics).
Where the rest of the library answers "given this dependence, what is the WWR?", this module inverts the question:
- :func:
calibrate_to_alpha/ :func:calibrate_to_cva— find the dependence parameter that reproduces a target alpha multiplier or WWR-CVA (e.g. a desk/regulator target, or a historically observed CVA). - :func:
find_breakpoint— find the dependence level at which a chosen metric (alpha, WWR-CVA, EAD) crosses a threshold — a reverse-stress / capital breach diagnostic: "how much wrong-way correlation until we breach?".
All solvers root-find on the monotone metric-vs-parameter curve with a robust
bracketed bisection (deterministic, numpy-only). The caller supplies a
model_factory mapping a scalar parameter to a dependence model, so the same
solver works for the Hull-White b, the Gaussian rho, or a copula
theta.
SolveResult
dataclass
¶
SolveResult(param: float, achieved: float, target: float, iterations: int, converged: bool, result: WWRResult)
Outcome of an inverse solve.
Attributes:
| Name | Type | Description |
|---|---|---|
param |
float
|
The solved dependence parameter. |
achieved |
float
|
The metric value attained at |
target |
float
|
The requested target / threshold. |
iterations |
int
|
Number of bisection steps taken. |
converged |
bool
|
Whether the solver reached |
result |
WWRResult
|
The full :class: |
alpha_metric ¶
wwr_cva_metric ¶
ead_metric ¶
solve_for_target ¶
solve_for_target(exposure: ExposureSource, credit: CreditCurveSource, model_factory: ModelFactory, target: float, *, metric: Metric = alpha_metric, lo: float, hi: float, tol: float = 0.0001, max_iter: int = 60, discount: ndarray | None = None, pfe_quantile: float = 0.95) -> SolveResult
Find the parameter in [lo, hi] whose metric equals target.
The metric must be monotone in the parameter over the bracket (true for the
built-in models). Raises :class:ValidationError if [lo, hi] does not
bracket the target.
Source code in src/wayfault/application/inverse.py
calibrate_to_alpha ¶
calibrate_to_alpha(exposure: ExposureSource, credit: CreditCurveSource, model_factory: ModelFactory, target_alpha: float, *, lo: float, hi: float, tol: float = 0.0001, max_iter: int = 60, discount: ndarray | None = None, pfe_quantile: float = 0.95) -> SolveResult
Find the dependence parameter that reproduces target_alpha.
Source code in src/wayfault/application/inverse.py
calibrate_to_cva ¶
calibrate_to_cva(exposure: ExposureSource, credit: CreditCurveSource, model_factory: ModelFactory, target_cva: float, *, lo: float, hi: float, tol: float = 1e-08, max_iter: int = 80, discount: ndarray | None = None, pfe_quantile: float = 0.95) -> SolveResult
Find the dependence parameter that reproduces target_cva.
Source code in src/wayfault/application/inverse.py
find_breakpoint ¶
find_breakpoint(exposure: ExposureSource, credit: CreditCurveSource, model_factory: ModelFactory, threshold: float, *, metric: Metric = alpha_metric, lo: float, hi: float, tol: float = 0.0001, max_iter: int = 60, discount: ndarray | None = None, pfe_quantile: float = 0.95) -> SolveResult
Find the dependence level at which metric crosses threshold.
A reverse-stress diagnostic: the returned param is the breakpoint where
the chosen metric (default alpha) equals threshold.