Last Updated May 8, 2026
Fragility is often misunderstood because it does not always announce itself through obvious weakness. In complex ecological, infrastructural, institutional, technological, and socio-economic systems, fragility frequently develops quietly. Systems continue to function, targets continue to be met, and visible order remains intact, even as buffers shrink, maintenance is deferred, thresholds approach, ecological support erodes, institutional standards drift, and organizations grow increasingly dependent on improvisation. By the time breakdown becomes unmistakable, the system may already have been fragile for a long time.
Fragility, in this sense, is not simply the presence of weakness. It is the hidden condition in which accumulated stress makes systems increasingly vulnerable to disruption, surprise, and disproportionate harm. A fragile system can appear strong because it is still performing. It can appear resilient because it is still coping. It can appear stable because decline has been normalized. The danger is that visible performance can survive long after resilience margin has begun to disappear.
Main Library
Publications
Article Map
Risk & Resilience
Foundation
Risk & Resilience
Previous Article
Complex Failure
Related Topic
Systems Thinking

This article builds on What Are Risk and Resilience in Sustainable Systems?, Risk, Uncertainty, and Complexity, Vulnerability, Exposure, and Sensitivity, Resilience, Robustness, and Antifragility, Adaptation, Recovery, and Transformation, and Why Complex Systems Fail by examining the slow buildup that often precedes visible failure.
The central argument is that fragility often grows beneath successful performance. Problems build through delay, normalization, compensation, erosion of standards, and repeated adaptation to strain. Organizations cope with shortages by working around them. Communities cope with environmental stress by absorbing more burden privately. Infrastructures cope with underinvestment through deferred repair. Ecosystems cope with disturbance until they approach thresholds beyond which recovery becomes much harder. Because these systems continue to operate for a time, stress is often mistaken for stability. What appears resilient may in fact be a system surviving on borrowed margin.
Why Fragility Is Hard to See
Fragility is hard to see because systems often continue working while they are becoming less able to tolerate disturbance. Visible failure is usually late in the sequence, not early. Before collapse, systems may appear normal precisely because people, institutions, ecosystems, and infrastructures are compensating for deterioration through extra effort, workarounds, lowered expectations, postponed maintenance, risk transfer, or silent acceptance of declining margins. The apparent continuity of output masks the declining quality of the conditions that make that output possible.
This is one of the central lessons of systems thinking and resilience engineering. A system can keep producing outputs while its capacity to absorb future disturbance is shrinking. A hospital can keep treating patients while staff exhaustion rises. A bridge can remain open while maintenance backlogs accumulate. A watershed can keep supplying water while ecological support systems weaken. A public institution can continue processing cases while expertise exits, trust erodes, and improvisation replaces capacity. The surface remains legible while the foundation deteriorates.
Donella Meadows described several system traps that illuminate this process, including eroding goals and drift in standards. When performance declines gradually, institutions may adapt by accepting the decline rather than reversing it. Goals are lowered to match deteriorating reality. What would once have counted as warning becomes normal. What would once have triggered corrective action becomes background noise. This makes fragility especially dangerous because the system’s interpretive frame deteriorates along with the system itself.
Complex systems therefore tend to hide fragility in plain sight. The problem is not merely that stress exists. It is that stress can be distributed, deferred, normalized, and displaced across time, people, places, and subsystems until no single warning seems decisive on its own. A maintenance backlog belongs to one department. Staff burnout belongs to another. Ecological degradation is treated as environmental background. Public distrust is treated as a communications problem. But together these pressures may reveal a system losing its ability to absorb disturbance.
The result is a dangerous illusion of continuity. A system appears functional because it has not yet failed visibly. But the absence of visible collapse is not the same as resilience. It may simply mean that hidden stress has not yet crossed the threshold where it becomes impossible to ignore.
What Fragility Means
Fragility, in the most useful sense for sustainable systems, refers to a condition in which a system is vulnerable to disproportionate harm from volatility, disruption, cumulative pressure, or changing conditions. A fragile system is not merely exposed to risk. It is shaped in such a way that stress produces damage more readily, recovery is harder, and hidden dependencies magnify consequences when assumptions fail.
Nassim Nicholas Taleb’s formulation is helpful here: fragility is harmed by disorder, uncertainty, and variation. A fragile object is damaged by volatility. A robust object resists damage. An antifragile system, under bounded and appropriate conditions, may even improve through stress. But for sustainable systems, fragility needs to be understood not only as a property of objects or portfolios, but as a structural condition that grows through accumulated stress and eroded margin.
Fragility has multiple dimensions. It may be material, as in infrastructure that lacks redundancy, spare capacity, maintenance, or safe margins. It may be ecological, as in watersheds, soils, forests, wetlands, reefs, or climate-regulating systems whose buffering capacity has been depleted. It may be institutional, as in governance systems that cannot detect weak signals, coordinate across sectors, act before crisis becomes acute, or correct their own drift. It may be social, as in communities whose ability to cope has been eroded by poverty, exclusion, poor health, precarious work, displacement, or insecure livelihoods. It may also be cognitive, where organizations cling to outdated models of normality that no longer match system conditions.
Seen this way, fragility is not just the presence of risk. It is the pattern through which stress becomes dangerous because protective capacity, interpretive clarity, adaptive room, and social legitimacy have been worn down over time. A fragile system may still look orderly. It may still meet performance targets. It may still report continuity. But it has lost margin.
This distinction matters because a system can be high-performing and fragile at the same time. A just-in-time supply chain may deliver efficiently under normal conditions while being highly vulnerable to disruption. A centralized digital platform may serve millions of users while becoming a single point of institutional failure. A city may grow rapidly while building exposure in floodplains, heat islands, and under-serviced settlements. A farm region may produce high yields while degrading soil, water, biodiversity, and livelihood diversity.
Fragility is therefore a warning against mistaking present output for durable capacity. It asks not only whether the system works today, but how much stress it can absorb tomorrow without transferring harm to people, ecosystems, or future generations.
How Stress Accumulates
Stress accumulates when systems repeatedly absorb pressure without altering the deeper conditions generating it. This may occur through deferred repair, resource depletion, staff overload, habitat loss, groundwater decline, narrowing supply routes, weakened public trust, concentration of dependence, underfunded public services, or incremental exposure to changing climate conditions. None of these developments may appear catastrophic in isolation. Their danger lies in cumulative effect. Each small compromise removes a little margin, and the system’s apparent ability to cope becomes the reason further pressure is tolerated.
Indicators often fail to capture this buildup because they track outputs more readily than margins. A power system may still deliver electricity while operating closer to critical thresholds. A hospital may still provide care while depending on exhausted staff and improvised routines. A watershed may still provide water while aquifers decline and ecological resilience weakens. A public agency may still meet statutory requirements while hollowing out expertise, institutional memory, and public trust. Output persists, so the stress remains politically and administratively easy to ignore.
This is one of the most dangerous features of hidden stress: it can be treated as evidence of resilience. When people keep coping, institutions may conclude that the system is still safe. When infrastructure keeps functioning, maintenance can be delayed again. When ecosystems continue providing services, extraction can continue. When communities absorb burden privately, public institutions may fail to see the depth of strain. The system’s coping capacity becomes a resource that is consumed rather than restored.
Meadows emphasized that resilience depends on feedback, information, and the relationship between the rate of change and the system’s rate of response. If stress accumulates faster than the system can detect, interpret, and respond to it, fragility grows even before visible failure occurs. A system may have warning signals, but if those signals are delayed, fragmented, normalized, or politically inconvenient, they may not change behavior.
Hidden stress accumulation is therefore not accidental. It is often structurally produced by systems that reward short-term throughput, cost minimization, visible order, or surface stability while neglecting the invisible capacities that sustain long-term function. Sustainable resilience requires changing what is measured, what is rewarded, and what institutions treat as evidence of health.
Normalization and Drift
One of the most important mechanisms by which fragility deepens is drift. Sidney Dekker’s account of drifting into failure argues that disasters are often preceded by gradual movement toward the edges of safe performance as organizations adapt to scarcity, pressure, competition, uncertainty, and conflicting goals. This movement is not necessarily reckless or irrational. It often emerges from ordinary attempts to succeed under constraint. But because the movement is gradual and locally reasonable, the growing distance from safer operating conditions may not be recognized until the system crosses a critical line.
Drift matters because it shows how fragility can deepen through success, not only through obvious malfunction. People solve immediate problems, deadlines are met, services continue, and organizations remain operational. Yet each workaround may also entrench dependence on strained routines, unacknowledged trade-offs, or informal compensations. What begins as flexibility can become silent structural exposure.
Hollnagel’s resilience engineering makes a related point: the same adaptive adjustments that allow systems to function under variable conditions can also become pathways to failure under different circumstances. A hospital that survives through constant staff improvisation may be praised for dedication while the underlying staffing model becomes unsustainable. A city agency that handles repeated infrastructure failures through emergency response may appear capable while routine maintenance deteriorates. A community that repeatedly recovers from climate shocks through unpaid care, debt, and informal networks may appear resilient while its social margin collapses.
Normalization deepens the problem. Warning signs gradually become ordinary. Reduced staffing becomes the new baseline. Delayed maintenance becomes expected. Lower service quality becomes acceptable. Ecological degradation becomes background. Public distrust becomes a communications challenge rather than a legitimacy warning. Drift is dangerous because it changes not only the system’s condition, but also its sense of what counts as safe, adequate, or urgent.
Fragility is therefore often the result of adaptation without reflection. Systems adjust to stress, but the adjustments mask the need for more fundamental repair, redesign, or transformation. A serious resilience practice must ask where adaptation is preserving function and where it is hiding deterioration.
Erosion of Buffers and Standards
Fragility also accumulates when buffers, slack, and standards erode. Buffers include spare capacity, maintenance margins, ecological redundancy, fiscal reserves, institutional memory, social solidarity, inventory reserves, workforce depth, backup systems, and the practical room needed to respond when assumptions fail. Systems that repeatedly consume these capacities in the name of efficiency, austerity, throughput, or short-term performance may remain functional for a time, but they become more exposed to shocks that earlier would have been manageable.
Slack is often treated as waste because it does not always appear productive under normal conditions. But in resilience terms, slack is the space that allows systems to absorb variation. A staff reserve allows illness, turnover, or surge demand to be managed. A maintenance reserve allows repair before breakdown. A wetland absorbs floodwater. A diversified supply chain absorbs disruption. A trusted public institution absorbs uncertainty because people are more likely to cooperate when conditions change. These capacities may not maximize short-term efficiency, but they protect long-term viability.
Meadows’s discussion of eroding goals is especially relevant here. When decline is gradual, institutions may redefine what counts as acceptable rather than restoring prior standards. This is one reason fragility is politically and administratively dangerous: people become accustomed to diminished margin. They stop measuring against what the system needs for resilience and begin measuring against what the damaged system still happens to deliver.
In sustainable systems, erosion of buffers can occur simultaneously across domains. Ecological resilience declines while infrastructure ages. Public services lose capacity while social vulnerability rises. Maintenance is deferred while climate stress intensifies. Trust erodes while institutions need cooperation more than ever. Each form of erosion compounds the others. A system that has lost buffering capacity in many places may still look functional until one stressor arrives that activates all of those losses at once.
The erosion of standards is especially hard to reverse because it becomes embedded in expectations. Once people adapt to poor service, delayed repair, ecological degradation, and precarious coping, restoring better standards can be framed as unrealistic. But resilience depends on resisting that downward normalization. It requires institutions to remember what safe margins look like and to rebuild them before crisis makes the deficit undeniable.
Thresholds and Latent Instability
Hidden accumulation of stress matters because complex systems are often nonlinear. They do not always deteriorate in a smooth, proportional way. Instead, they may absorb strain for long periods and then change rapidly once thresholds are crossed. A system can appear stable while moving closer to a tipping point. Once the threshold is crossed, recovery may become slow, costly, politically difficult, or impossible.
This is one reason fragility cannot be measured only by present performance. A system may be productive, orderly, and apparently successful while very close to a threshold. The decisive issue is not only what it is doing now, but how much disturbance it can still absorb before qualitatively different behavior emerges. In ecological systems, that may involve collapse of regenerative functions, biodiversity loss, regime shifts, soil degradation, groundwater depletion, or loss of hydrological buffering. In institutions, it may involve loss of legitimacy, coordination, compliance, staff capacity, or public trust. In infrastructure, it may involve cascading service failure.
Latent instability exists even while the system appears operational. A bridge may remain open while structural risk rises. A public-health system may continue operating while staff burnout pushes it toward failure. A watershed may still produce water while nearing ecological transition. A social system may appear calm while households accumulate debt, insecurity, and suppressed need. Threshold risk is often invisible because ordinary performance metrics do not show how close the system is to a nonlinear change.
This is why resilience analysis must focus on margins, slow variables, and thresholds. It must ask whether buffers are growing or shrinking, whether deterioration is reversible or approaching a point of no return, and whether the system’s ability to respond is keeping pace with the rate of change. Fragility belongs to the domain of margins, not only events.
Threshold thinking also changes governance. Waiting for visible failure may mean waiting too long. Once a critical transition occurs, the cost of response may rise dramatically. Preventive action may appear expensive before crisis, but far cheaper than recovery after thresholds have been crossed. Sustainable systems therefore require institutions willing to act before failure becomes undeniable.
Fragility in Social and Institutional Systems
Social and institutional systems accumulate hidden stress in ways that are often harder to quantify than technical systems, but no less important. Households may sustain daily life through debt, informal care, exhaustion, and suppressed need. Public institutions may appear functional while staffing thins, expertise exits, morale declines, and trust erodes. Governance systems may preserve procedural continuity while losing the capacity to act adaptively across sectors or anticipate systemic risk. These are all forms of accumulated stress that remain partially invisible until crisis reveals them.
The social distribution of fragility matters. Hidden stress is often borne first by those with the least margin: low-income households, precarious workers, marginalized communities, informal settlements, degraded landscapes, underfunded public systems, and people whose labor or care is treated as inexhaustible. What looks like stability from above may depend on burdens being absorbed below. A system can maintain visible order by transferring stress to those least able to bear it, but that does not make the system resilient. It only delays recognition of failure.
This is why fragility is both a systems problem and a justice problem. A technically functioning system may still be socially fragile if its performance depends on unpaid care, exhausted workers, degraded ecosystems, or communities exposed to chronic harm. A city may continue growing while housing insecurity rises. A health system may maintain throughput while workers burn out. A food system may keep shelves stocked while farmers, laborers, soils, and watersheds absorb unsustainable stress.
Institutional fragility is especially dangerous because institutions are supposed to detect and respond to systemic risk. When they themselves are strained, fragmented, underfunded, or distrusted, they may lose the ability to interpret weak signals. Governance can become reactive rather than anticipatory. Public systems can become locked into crisis response. Standards can erode because institutions no longer have the capacity to enforce or restore them.
For sustainable systems, this is decisive. Fragility is not just what breaks. It is also what quietly bears too much before breaking becomes visible. A serious analysis of fragility must therefore ask who is carrying the system’s hidden stress, who benefits from that invisibility, and what forms of repair would restore margin fairly.
Why Visible Performance Can Mislead
Visible performance can mislead because systems are often judged by current outputs rather than by the condition of the capacities producing those outputs. A supply chain delivers goods, a grid delivers power, an agency meets deadlines, a hospital treats patients, a community remains inhabited, and observers infer that the system is stable. But current delivery says little by itself about reserve capacity, signal quality, maintenance, ecological margin, institutional learning, or social strain. Performance can remain acceptable long after resilience has begun to decline.
This is one reason hidden accumulation of stress is so dangerous for decision-makers. By the time failure becomes visible enough to command attention, there may be little room left for low-cost intervention. The system’s earlier flexibility created the illusion that stress was manageable, which in turn discouraged corrective action. Fragility grows not only because stress is present, but because coping conceals the need to change.
Conventional performance management often reinforces the problem. It measures throughput, speed, cost, output, utilization, and short-term compliance. These metrics may be important, but they do not necessarily reveal whether buffers are shrinking, standards are eroding, workarounds are increasing, trust is declining, or thresholds are approaching. A dashboard can look good while the system becomes fragile underneath.
A serious resilience perspective therefore asks different questions. Where are margins thinning? Which buffers are being consumed? What standards have quietly drifted downward? What workarounds have become routine? What forms of social, ecological, or institutional burden are making visible performance possible? Which signals are being normalized rather than investigated? What would fail first if external stress increased?
Those questions are less immediately flattering than output metrics, but they are more useful for preventing crisis. Visible performance matters, but it must be interpreted alongside hidden stress, margin, threshold proximity, and the distribution of burden. Otherwise, systems can be praised for functioning until the moment their concealed fragility becomes undeniable.
What Resilience Requires
If fragility often accumulates invisibly, then resilience must include capacities for detecting and reversing that accumulation before breakdown occurs. This requires better indicators, stronger feedback systems, maintenance of slack and redundancy, institutional memory, ecological restoration, social protection, and governance capable of acting on weak signals rather than waiting for visible crisis.
Resilience requires resisting the political temptation to confuse coping with safety. A system that is coping may still be deteriorating. A workforce that is improvising may still be overloaded. An ecosystem that is still producing may still be nearing a tipping point. A community that has not yet collapsed may still be living under unsustainable stress. Resilience begins when institutions stop treating continued operation as proof of health and start asking what hidden burdens are making that operation possible.
In practical terms, resilience requires margin restoration. That means rebuilding buffers, restoring maintenance capacity, diversifying dependencies, strengthening monitoring, preserving institutional knowledge, investing in public systems, protecting ecological support, and reducing the burden on vulnerable communities. It also requires institutional humility: complex systems cannot be fully controlled, and visible order should not be mistaken for durable stability.
It also requires better information. Indicators should track not only outputs but conditions: maintenance backlog, ecological buffer health, staff strain, public trust, threshold proximity, recovery capacity, social vulnerability, signal quality, and response time. Meadows stressed the power of information systems and feedback. Resilience depends on whether systems can detect degradation and respond before it becomes irreversible.
Finally, resilience requires justice. Hidden fragility is often distributed unevenly. Systems may preserve visible stability by transferring stress onto people with the least power to refuse it. Sustainable resilience must not simply keep systems running. It must reduce the hidden burdens that make systems appear stable while deepening injustice.
In sustainable systems, this means preserving and rebuilding the capacities that allow societies, infrastructures, ecosystems, and institutions to absorb disturbance without silently eating away their own future.
Mathematical Lens: Hidden Stress, Drift, Fragility, and Resilience Margin
Fragility can be represented as a relationship between visible performance, hidden stress, drift, latent instability, and resilience margin. Let \(P_r\) represent visible performance for system \(r\), \(H_r\) represent hidden stress, \(D_r\) represent institutional drift, \(L_r\) represent latent instability, \(M_r\) represent resilience margin, and \(J_r\) represent justice pressure.
A hidden stress index can be written as:
H_r = h_1S_r + h_2B_r + h_3R_r + h_4A_r + h_5E_r + h_6C_r + h_7T_r
\]
Interpretation: Hidden stress increases when accumulated pressure, buffer erosion, deferred repair, adaptation debt, ecological support erosion, social strain, and trust erosion build beneath visible performance.
A drift index can be represented as:
D_r = d_1I_r + d_2N_r + d_3G_r + d_4(1 – W_r)
\]
Interpretation: Drift rises when institutions move away from safer standards, warning signs become normalized, goals erode, and monitoring capacity weakens.
Latent instability can be represented as:
L_r = \ell_1Q_r + \ell_2H_r + \ell_3D_r + \ell_4K_r
\]
Interpretation: Latent instability rises as systems approach thresholds, hidden stress accumulates, drift deepens, and system criticality increases.
Resilience margin can be represented as:
M_r = m_1(1 – B_r) + m_2W_r + m_3C^{response}_r + m_4(1 – Q_r)
\]
Interpretation: Resilience margin is stronger when buffers are preserved, monitoring is strong, response capacity exists, and systems remain farther from thresholds.
A fragility score can be written as:
F_r = \left(f_1H_r + f_2D_r + f_3L_r + f_4\max(0, P_r – (1 – H_r))\right)(1 + \kappa K_r)
\]
Interpretation: Fragility rises when hidden stress, drift, latent instability, and misleading visible performance combine in a critical system.
A justice-weighted fragility score can be written as:
F^{J}_r = F_r(1 + \theta J_r)
\]
Interpretation: Fragility becomes more serious when hidden stress is borne disproportionately by vulnerable groups, underfunded institutions, exhausted workers, or degraded ecosystems.
A resilience gap can then be written as:
\Delta_r = \max(0, F^{J}_r – M_r)
\]
Interpretation: A resilience gap appears when justice-weighted fragility exceeds the system’s remaining margin.
| Term | Meaning | Interpretive role |
|---|---|---|
| \(P_r\) | Visible performance | Represents current output, continuity, or apparent system success. |
| \(H_r\) | Hidden stress | Represents accumulated pressure beneath visible performance. |
| \(D_r\) | Drift | Represents normalization, eroding standards, and weakened interpretation of warning signs. |
| \(L_r\) | Latent instability | Represents threshold proximity and nonlinear risk beneath apparent stability. |
| \(M_r\) | Resilience margin | Represents remaining buffer, monitoring, response capacity, and distance from thresholds. |
| \(F^{J}_r\) | Justice-weighted fragility | Represents fragility adjusted for unequal burden and social vulnerability. |
| \(\Delta_r\) | Resilience gap | Identifies where fragility exceeds the system’s remaining margin. |
This mathematical lens is not meant to reduce fragility to a single number. It clarifies the relationships that a good diagnostic framework should examine: visible performance, hidden stress, drift, threshold proximity, resilience margin, and the unequal distribution of burden.
Advanced Python Workflow: Fragility and Hidden Stress Diagnostics
The following Python workflow models fragility as a relationship among visible performance, hidden stress accumulation, buffer erosion, deferred maintenance, institutional drift, normalized signals, standard erosion, threshold proximity, adaptation debt, ecological support erosion, social strain, trust erosion, monitoring capacity, response capacity, justice pressure, and system criticality.
"""
Advanced fragility and hidden stress accumulation diagnostics.
This workflow models:
- visible performance versus hidden stress
- buffer erosion and deferred maintenance
- institutional drift and normalization of weak signals
- standard erosion and threshold proximity
- adaptation debt
- ecological support erosion
- social strain and trust erosion
- monitoring and response capacity
- resilience margin
- justice-weighted fragility
- scenario-based stress reduction and margin restoration
- Monte Carlo uncertainty around fragility classification
"""
from __future__ import annotations
from dataclasses import dataclass
from pathlib import Path
from typing import Dict
import numpy as np
import pandas as pd
BASE_DIR = Path("articles/fragility-hidden-accumulation-stress")
DATA_FILE = BASE_DIR / "data" / "fragility_hidden_stress_panel.csv"
OUTPUT_DIR = BASE_DIR / "outputs"
@dataclass(frozen=True)
class Scenario:
name: str
stress_reduction: float
buffer_restoration: float
maintenance_reduction: float
drift_reduction: float
signal_denormalization: float
standards_restoration: float
threshold_reduction: float
adaptation_debt_reduction: float
ecological_restoration: float
social_strain_reduction: float
trust_repair: float
monitoring_gain: float
response_gain: float
SCENARIOS: Dict[str, Scenario] = {
"baseline": Scenario("baseline", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0),
"monitoring_and_signal_repair": Scenario("monitoring_and_signal_repair", 0.08, 0.08, 0.08, 0.14, 0.24, 0.14, 0.06, 0.10, 0.04, 0.08, 0.12, 0.24, 0.12),
"maintenance_and_buffer_restoration": Scenario("maintenance_and_buffer_restoration", 0.08, 0.24, 0.24, 0.08, 0.10, 0.12, 0.10, 0.10, 0.14, 0.08, 0.08, 0.10, 0.16),
"anti_drift_governance": Scenario("anti_drift_governance", 0.10, 0.14, 0.16, 0.24, 0.22, 0.24, 0.12, 0.20, 0.12, 0.14, 0.18, 0.20, 0.22),
"justice_centered_stress_relief": Scenario("justice_centered_stress_relief", 0.16, 0.14, 0.14, 0.16, 0.18, 0.16, 0.12, 0.18, 0.16, 0.24, 0.24, 0.18, 0.22),
"resilience_margin_rebuild": Scenario("resilience_margin_rebuild", 0.20, 0.26, 0.26, 0.24, 0.24, 0.24, 0.20, 0.24, 0.24, 0.24, 0.24, 0.24, 0.26),
}
def load_data(path: Path) -> pd.DataFrame:
df = pd.read_csv(path)
required = {
"system_id",
"system_name",
"domain",
"region",
"stress_type",
"visible_performance",
"stress_accumulation",
"buffer_erosion",
"deferred_maintenance",
"institutional_drift",
"signal_normalization",
"standard_erosion",
"threshold_proximity",
"adaptation_debt",
"ecological_support_erosion",
"social_strain",
"trust_erosion",
"monitoring_capacity",
"response_capacity",
"justice_pressure",
"system_criticality",
}
missing = required.difference(df.columns)
if missing:
raise ValueError(f"Missing required columns: {sorted(missing)}")
numeric_cols = [
col for col in df.columns
if col not in {"system_id", "system_name", "domain", "region", "stress_type"}
]
for col in numeric_cols:
if ((df[col] < 0) | (df[col] > 1)).any():
raise ValueError(f"{col} must be scaled between 0 and 1.")
return df
def score_systems(df: pd.DataFrame) -> pd.DataFrame:
scored = df.copy()
scored["hidden_stress_index"] = (
0.20 * scored["stress_accumulation"]
+ 0.16 * scored["buffer_erosion"]
+ 0.14 * scored["deferred_maintenance"]
+ 0.13 * scored["adaptation_debt"]
+ 0.12 * scored["ecological_support_erosion"]
+ 0.13 * scored["social_strain"]
+ 0.12 * scored["trust_erosion"]
)
scored["drift_index"] = (
0.34 * scored["institutional_drift"]
+ 0.30 * scored["signal_normalization"]
+ 0.22 * scored["standard_erosion"]
+ 0.14 * (1 - scored["monitoring_capacity"])
)
scored["latent_instability"] = (
0.38 * scored["threshold_proximity"]
+ 0.26 * scored["hidden_stress_index"]
+ 0.20 * scored["drift_index"]
+ 0.16 * scored["system_criticality"]
)
scored["resilience_margin"] = (
0.34 * (1 - scored["buffer_erosion"])
+ 0.24 * scored["monitoring_capacity"]
+ 0.24 * scored["response_capacity"]
+ 0.18 * (1 - scored["threshold_proximity"])
)
scored["performance_misalignment"] = np.maximum(
0,
scored["visible_performance"] - (1 - scored["hidden_stress_index"]),
)
scored["fragility_score"] = (
0.32 * scored["hidden_stress_index"]
+ 0.24 * scored["drift_index"]
+ 0.24 * scored["latent_instability"]
+ 0.20 * scored["performance_misalignment"]
) * (1 + 0.25 * scored["system_criticality"])
scored["justice_weighted_fragility"] = (
scored["fragility_score"] * (1 + 0.35 * scored["justice_pressure"])
)
scored["resilience_gap"] = np.maximum(
0,
scored["justice_weighted_fragility"] - scored["resilience_margin"],
)
scored["diagnostic_priority"] = np.select(
[
scored["threshold_proximity"] > 0.75,
scored["drift_index"] > 0.65,
scored["hidden_stress_index"] > 0.70,
scored["justice_pressure"] > 0.70,
scored["performance_misalignment"] > 0.25,
],
[
"threshold_avoidance_priority",
"anti_drift_governance_priority",
"hidden_stress_relief_priority",
"justice_centered_margin_repair",
"performance_metric_redesign",
],
default="monitor_and_rebuild_margin",
)
return scored.sort_values(
["resilience_gap", "justice_weighted_fragility", "latent_instability"],
ascending=False,
).reset_index(drop=True)
def apply_scenario(df: pd.DataFrame, scenario: Scenario) -> pd.DataFrame:
scenario_df = df.copy()
scenario_df["stress_accumulation"] = (
scenario_df["stress_accumulation"] * (1 - scenario.stress_reduction)
).clip(0, 1)
scenario_df["buffer_erosion"] = (
scenario_df["buffer_erosion"] * (1 - scenario.buffer_restoration)
).clip(0, 1)
scenario_df["deferred_maintenance"] = (
scenario_df["deferred_maintenance"] * (1 - scenario.maintenance_reduction)
).clip(0, 1)
scenario_df["institutional_drift"] = (
scenario_df["institutional_drift"] * (1 - scenario.drift_reduction)
).clip(0, 1)
scenario_df["signal_normalization"] = (
scenario_df["signal_normalization"] * (1 - scenario.signal_denormalization)
).clip(0, 1)
scenario_df["standard_erosion"] = (
scenario_df["standard_erosion"] * (1 - scenario.standards_restoration)
).clip(0, 1)
scenario_df["threshold_proximity"] = (
scenario_df["threshold_proximity"] * (1 - scenario.threshold_reduction)
).clip(0, 1)
scenario_df["adaptation_debt"] = (
scenario_df["adaptation_debt"] * (1 - scenario.adaptation_debt_reduction)
).clip(0, 1)
scenario_df["ecological_support_erosion"] = (
scenario_df["ecological_support_erosion"] * (1 - scenario.ecological_restoration)
).clip(0, 1)
scenario_df["social_strain"] = (
scenario_df["social_strain"] * (1 - scenario.social_strain_reduction)
).clip(0, 1)
scenario_df["trust_erosion"] = (
scenario_df["trust_erosion"] * (1 - scenario.trust_repair)
).clip(0, 1)
scenario_df["monitoring_capacity"] = (
scenario_df["monitoring_capacity"] + scenario.monitoring_gain
).clip(0, 1)
scenario_df["response_capacity"] = (
scenario_df["response_capacity"] + scenario.response_gain
).clip(0, 1)
rescored = score_systems(scenario_df)
rescored["scenario"] = scenario.name
return rescored
def run_scenarios(df: pd.DataFrame) -> pd.DataFrame:
return pd.concat(
[apply_scenario(df, scenario) for scenario in SCENARIOS.values()],
ignore_index=True,
)
def monte_carlo_uncertainty(
df: pd.DataFrame,
draws: int = 2000,
seed: int = 42,
) -> pd.DataFrame:
rng = np.random.default_rng(seed)
records = []
numeric_cols = [
"visible_performance",
"stress_accumulation",
"buffer_erosion",
"deferred_maintenance",
"institutional_drift",
"signal_normalization",
"standard_erosion",
"threshold_proximity",
"adaptation_debt",
"ecological_support_erosion",
"social_strain",
"trust_erosion",
"monitoring_capacity",
"response_capacity",
"justice_pressure",
"system_criticality",
]
for draw in range(draws):
sampled = df.copy()
noise = rng.normal(loc=0.0, scale=0.04, size=(len(df), len(numeric_cols)))
sampled[numeric_cols] = np.clip(sampled[numeric_cols].to_numpy() + noise, 0, 1)
scored = score_systems(sampled)
scored["draw"] = draw
records.append(
scored[
[
"system_id",
"system_name",
"draw",
"hidden_stress_index",
"drift_index",
"latent_instability",
"resilience_margin",
"justice_weighted_fragility",
"resilience_gap",
]
]
)
mc = pd.concat(records, ignore_index=True)
return (
mc.groupby(["system_id", "system_name"])
.agg(
hidden_stress_p50=("hidden_stress_index", "median"),
drift_p50=("drift_index", "median"),
instability_p50=("latent_instability", "median"),
margin_p50=("resilience_margin", "median"),
fragility_p50=("justice_weighted_fragility", "median"),
fragility_p95=("justice_weighted_fragility", lambda x: np.quantile(x, 0.95)),
resilience_gap_p50=("resilience_gap", "median"),
)
.reset_index()
.sort_values("resilience_gap_p50", ascending=False)
)
def build_domain_summary(scored: pd.DataFrame) -> pd.DataFrame:
return (
scored.groupby("domain")
.agg(
systems=("system_id", "count"),
mean_visible_performance=("visible_performance", "mean"),
mean_hidden_stress=("hidden_stress_index", "mean"),
mean_drift=("drift_index", "mean"),
mean_latent_instability=("latent_instability", "mean"),
mean_resilience_margin=("resilience_margin", "mean"),
mean_justice_weighted_fragility=("justice_weighted_fragility", "mean"),
mean_resilience_gap=("resilience_gap", "mean"),
)
.reset_index()
.sort_values("mean_resilience_gap", ascending=False)
)
def main() -> None:
OUTPUT_DIR.mkdir(parents=True, exist_ok=True)
raw = load_data(DATA_FILE)
scored = score_systems(raw)
scenarios = run_scenarios(raw)
uncertainty = monte_carlo_uncertainty(raw)
domain_summary = build_domain_summary(scored)
scored.to_csv(OUTPUT_DIR / "fragility_hidden_stress_scores.csv", index=False)
scenarios.to_csv(OUTPUT_DIR / "fragility_hidden_stress_scenarios.csv", index=False)
uncertainty.to_csv(OUTPUT_DIR / "fragility_hidden_stress_uncertainty.csv", index=False)
domain_summary.to_csv(OUTPUT_DIR / "fragility_hidden_stress_domain_summary.csv", index=False)
print(scored.round(3).to_string(index=False))
print(domain_summary.round(3).to_string(index=False))
if __name__ == "__main__":
main()
This workflow operationalizes the article’s core claim: fragility often grows beneath visible performance. It separates hidden stress, institutional drift, latent instability, resilience margin, justice-weighted fragility, and resilience gaps. The scenario structure allows users to test different interventions: monitoring and signal repair, maintenance and buffer restoration, anti-drift governance, justice-centered stress relief, and broad resilience-margin rebuilding.
Advanced R Workflow: Hidden Fragility Dashboarding
The following R workflow creates dashboard-ready outputs for comparing visible performance, hidden stress, drift, latent instability, resilience margin, justice-weighted fragility, resilience gaps, scenarios, domain summaries, and long-format dashboard data.
library(readr)
library(dplyr)
library(tidyr)
base_dir <- "articles/fragility-hidden-accumulation-stress"
data_file <- file.path(base_dir, "data", "fragility_hidden_stress_panel.csv")
output_dir <- file.path(base_dir, "outputs")
dir.create(output_dir, recursive = TRUE, showWarnings = FALSE)
systems <- read_csv(data_file, show_col_types = FALSE)
score_systems <- function(df) {
df %>%
mutate(
hidden_stress_index =
0.20 * stress_accumulation +
0.16 * buffer_erosion +
0.14 * deferred_maintenance +
0.13 * adaptation_debt +
0.12 * ecological_support_erosion +
0.13 * social_strain +
0.12 * trust_erosion,
drift_index =
0.34 * institutional_drift +
0.30 * signal_normalization +
0.22 * standard_erosion +
0.14 * (1 - monitoring_capacity),
latent_instability =
0.38 * threshold_proximity +
0.26 * hidden_stress_index +
0.20 * drift_index +
0.16 * system_criticality,
resilience_margin =
0.34 * (1 - buffer_erosion) +
0.24 * monitoring_capacity +
0.24 * response_capacity +
0.18 * (1 - threshold_proximity),
performance_misalignment =
pmax(0, visible_performance - (1 - hidden_stress_index)),
fragility_score =
(
0.32 * hidden_stress_index +
0.24 * drift_index +
0.24 * latent_instability +
0.20 * performance_misalignment
) *
(1 + 0.25 * system_criticality),
justice_weighted_fragility =
fragility_score * (1 + 0.35 * justice_pressure),
resilience_gap =
pmax(0, justice_weighted_fragility - resilience_margin),
diagnostic_priority = case_when(
threshold_proximity > 0.75 ~
"threshold_avoidance_priority",
drift_index > 0.65 ~
"anti_drift_governance_priority",
hidden_stress_index > 0.70 ~
"hidden_stress_relief_priority",
justice_pressure > 0.70 ~
"justice_centered_margin_repair",
performance_misalignment > 0.25 ~
"performance_metric_redesign",
TRUE ~
"monitor_and_rebuild_margin"
)
) %>%
arrange(desc(resilience_gap), desc(justice_weighted_fragility), desc(latent_instability))
}
scored <- score_systems(systems)
scenario_parameters <- tibble::tibble(
scenario = c(
"baseline",
"monitoring_and_signal_repair",
"maintenance_and_buffer_restoration",
"anti_drift_governance",
"justice_centered_stress_relief",
"resilience_margin_rebuild"
),
stress_reduction = c(0.00, 0.08, 0.08, 0.10, 0.16, 0.20),
buffer_restoration = c(0.00, 0.08, 0.24, 0.14, 0.14, 0.26),
maintenance_reduction = c(0.00, 0.08, 0.24, 0.16, 0.14, 0.26),
drift_reduction = c(0.00, 0.14, 0.08, 0.24, 0.16, 0.24),
signal_denormalization = c(0.00, 0.24, 0.10, 0.22, 0.18, 0.24),
standards_restoration = c(0.00, 0.14, 0.12, 0.24, 0.16, 0.24),
threshold_reduction = c(0.00, 0.06, 0.10, 0.12, 0.12, 0.20),
adaptation_debt_reduction = c(0.00, 0.10, 0.10, 0.20, 0.18, 0.24),
ecological_restoration = c(0.00, 0.04, 0.14, 0.12, 0.16, 0.24),
social_strain_reduction = c(0.00, 0.08, 0.08, 0.14, 0.24, 0.24),
trust_repair = c(0.00, 0.12, 0.08, 0.18, 0.24, 0.24),
monitoring_gain = c(0.00, 0.24, 0.10, 0.20, 0.18, 0.24),
response_gain = c(0.00, 0.12, 0.16, 0.22, 0.22, 0.26)
)
scenario_scores <- systems %>%
tidyr::crossing(scenario_parameters) %>%
mutate(
stress_accumulation = pmax(0, stress_accumulation * (1 - stress_reduction)),
buffer_erosion = pmax(0, buffer_erosion * (1 - buffer_restoration)),
deferred_maintenance = pmax(0, deferred_maintenance * (1 - maintenance_reduction)),
institutional_drift = pmax(0, institutional_drift * (1 - drift_reduction)),
signal_normalization = pmax(0, signal_normalization * (1 - signal_denormalization)),
standard_erosion = pmax(0, standard_erosion * (1 - standards_restoration)),
threshold_proximity = pmax(0, threshold_proximity * (1 - threshold_reduction)),
adaptation_debt = pmax(0, adaptation_debt * (1 - adaptation_debt_reduction)),
ecological_support_erosion = pmax(0, ecological_support_erosion * (1 - ecological_restoration)),
social_strain = pmax(0, social_strain * (1 - social_strain_reduction)),
trust_erosion = pmax(0, trust_erosion * (1 - trust_repair)),
monitoring_capacity = pmin(1, monitoring_capacity + monitoring_gain),
response_capacity = pmin(1, response_capacity + response_gain)
) %>%
group_by(scenario) %>%
group_modify(~ score_systems(.x)) %>%
ungroup()
scenario_summary <- scenario_scores %>%
group_by(scenario) %>%
summarise(
mean_hidden_stress = mean(hidden_stress_index),
mean_drift = mean(drift_index),
mean_latent_instability = mean(latent_instability),
mean_resilience_margin = mean(resilience_margin),
mean_fragility = mean(justice_weighted_fragility),
mean_resilience_gap = mean(resilience_gap),
.groups = "drop"
) %>%
arrange(mean_resilience_gap)
domain_summary <- scored %>%
group_by(domain) %>%
summarise(
systems = n(),
mean_visible_performance = mean(visible_performance),
mean_hidden_stress = mean(hidden_stress_index),
mean_drift = mean(drift_index),
mean_latent_instability = mean(latent_instability),
mean_resilience_margin = mean(resilience_margin),
mean_fragility = mean(justice_weighted_fragility),
mean_resilience_gap = mean(resilience_gap),
.groups = "drop"
) %>%
arrange(desc(mean_resilience_gap))
dashboard_long <- scored %>%
select(
system_id,
system_name,
domain,
region,
stress_type,
visible_performance,
hidden_stress_index,
drift_index,
latent_instability,
resilience_margin,
justice_weighted_fragility,
resilience_gap
) %>%
pivot_longer(
cols = c(
visible_performance,
hidden_stress_index,
drift_index,
latent_instability,
resilience_margin,
justice_weighted_fragility,
resilience_gap
),
names_to = "metric",
values_to = "value"
)
write_csv(scored, file.path(output_dir, "r_fragility_hidden_stress_scores.csv"))
write_csv(scenario_scores, file.path(output_dir, "r_fragility_hidden_stress_scenarios.csv"))
write_csv(scenario_summary, file.path(output_dir, "r_scenario_summary.csv"))
write_csv(domain_summary, file.path(output_dir, "r_domain_summary.csv"))
write_csv(dashboard_long, file.path(output_dir, "r_dashboard_long.csv"))
print(scored)
print(scenario_summary)
print(domain_summary)
The R workflow complements the Python workflow by producing dashboard-oriented outputs. It is especially useful for comparing domains, scenarios, hidden-stress metrics, resilience-margin restoration, and justice-weighted fragility across infrastructure, public-health, ecological, digital, food, energy, and regional systems. A production version could connect to maintenance backlogs, staff strain indicators, ecological monitoring data, public-trust surveys, service-quality records, threshold indicators, and community vulnerability datasets.
Engineering Extensions in the GitHub Repository
The accompanying repository extends the article beyond conceptual explanation into reproducible systems analysis. The article folder is designed around a synthetic system panel, advanced Python diagnostics, advanced R dashboarding, scenario outputs, uncertainty analysis, documentation, and extensible scoring logic.
The article body foregrounds Python and R because they are the most accessible languages for data analysis, scenario modeling, uncertainty analysis, and dashboard preparation. Additional languages can strengthen the repository where they serve a real analytical purpose. Go can support lightweight scoring services and APIs. Rust can support reliable command-line fragility scoring tools. SQL can support structured indicator records, scenario matrices, source provenance, and auditability. C and C++ can support compact numerical kernels and resilience-margin calculations. Fortran can support numerical threshold-proximity calculations and legacy scientific-computing workflows.
The deeper purpose of the repository is not to turn hidden fragility into false precision. It is to make assumptions visible. By separating visible performance, hidden stress, drift, latent instability, resilience margin, justice-weighted fragility, and resilience gaps, the workflow allows users to see how the final interpretation was produced. That transparency is essential in systems where apparent stability may conceal deteriorating conditions, normalized warning signs, and unevenly distributed stress.
GitHub Repository
Complete Code Repository
The full code directory for this article, including advanced Python diagnostics, advanced R dashboard workflow, synthetic hidden-fragility data, scenario outputs, uncertainty analysis, documentation, and systems-level extensions, is available on GitHub.
Common Misunderstandings
A common misunderstanding is that fragility must look weak. In complex systems, fragility often appears alongside visible strength, high output, or apparent stability. A system can keep performing while its margins quietly disappear.
Another misunderstanding is that coping proves resilience. Coping may be resilience, but it may also be hidden stress accumulation. If performance depends on exhaustion, deferred maintenance, degraded ecosystems, or vulnerable communities absorbing burden, the system may be fragile beneath the surface.
A third misunderstanding is that fragility begins at the moment of failure. Fragility usually begins earlier, as buffers erode, standards drift, thresholds approach, and warning signs become normalized.
A fourth misunderstanding is that visible performance metrics are enough. Output metrics can conceal loss of slack, institutional drift, social strain, ecological degradation, and threshold proximity.
A fifth misunderstanding is that restoring prior function always reduces fragility. Recovery can rebuild fragility if it restores the same exposure, same underinvestment, same social burden, and same ecological depletion.
A final misunderstanding is that hidden fragility is only a technical problem. It is also a justice problem. Systems often appear stable because vulnerable people, workers, ecosystems, or underfunded public institutions are carrying stress invisibly.
Conclusion
Fragility and the hidden accumulation of stress help explain why complex systems often fail after long periods of apparent normality. Systems continue functioning while margins erode, standards drift, signals are normalized, thresholds approach, and burden is transferred onto people, ecosystems, or infrastructures that can absorb it only temporarily. What appears sudden at the end is often the delayed expression of stress that has been accumulating for years.
To understand fragility is therefore to look beneath visible performance. It is to ask where stress is gathering, where thresholds are approaching, what workarounds have become normal, which buffers have been consumed, what standards have eroded, and whose burden is making the system appear stable. Sustainable resilience depends on that deeper mode of attention.
The computational workflows attached to this article extend that argument into practice. They separate visible performance, hidden stress, drift, latent instability, resilience margin, justice pressure, and resilience gaps. They show why some systems require monitoring and signal repair, some require maintenance and buffer restoration, some require anti-drift governance, some require justice-centered stress relief, and some require deeper rebuilding of resilience margin.
Systems do not become durable simply because they keep going. They become durable when they can detect, interpret, and reverse the quiet processes that would otherwise turn ordinary strain into eventual crisis.
Return to the Risk & Resilience knowledge series.
Related Reading
- Risk & Resilience
- What Are Risk and Resilience in Sustainable Systems?
- Risk, Uncertainty, and Complexity
- Vulnerability, Exposure, and Sensitivity
- Resilience, Robustness, and Antifragility
- Adaptation, Recovery, and Transformation
- Why Complex Systems Fail
- Systems Thinking
Further Reading
- Dekker, S. (2011) Drift into Failure: From Hunting Broken Components to Understanding Complex Systems. Farnham: Ashgate. Available at: https://safetydifferently.com/wp-content/uploads/2014/08/SDDriftPaper.pdf.
- Hollnagel, E. (n.d.) Resilience Engineering. Available at: https://erikhollnagel.com/ideas/resilience-engineering.html.
- Hollnagel, E., Pariès, J., Woods, D.D. and Wreathall, J. (eds.) (2011) Resilience Engineering in Practice: A Guidebook. Farnham: Ashgate. Available at: https://api.pageplace.de/preview/DT0400.9781317065296_A31717807/preview-9781317065296_A31717807.pdf.
- Meadows, D.H. (1998) Indicators and Information Systems for Sustainable Development. Available at: https://www.donellameadows.org/wp-content/userfiles/IndicatorsInformation.pdf.
- Meadows, D.H. (1999) Leverage Points: Places to Intervene in a System. Available at: https://donellameadows.org/wp-content/userfiles/Leverage_Points.pdf.
- Meadows, D.H. (2008) Thinking in Systems: A Primer. White River Junction, VT: Chelsea Green. Available at: https://research.fit.edu/media/site-specific/researchfitedu/coast-climate-adaptation-library/climate-communications/psychology-amp-behavior/Meadows-2008.-Thinking-in-Systems.pdf.
- Stockholm Resilience Centre (2015) Applying Resilience Thinking. Available at: https://www.stockholmresilience.org/download/18.10119fc11455d3c557d6928/1459560241272/SRC%2BApplying%2BResilience%2Bfinal.pdf.
- Stockholm Resilience Centre (n.d.) Planetary Boundaries. Available at: https://www.stockholmresilience.org/research/planetary-boundaries.html.
- Taleb, N.N. (2012) Antifragile: Things That Gain from Disorder. New York: Random House. Available at: https://www.penguinrandomhouse.com/books/176227/antifragile-by-nassim-nicholas-taleb/.
- Tang, K.B. and Karen, L. (2012) A New Heuristic Measure of Fragility and Tail Risks. IMF Working Paper. Available at: https://www.imf.org/external/pubs/ft/wp/2012/wp12216.pdf.
References
- Dekker, S. (2011) Drift into Failure: From Hunting Broken Components to Understanding Complex Systems. Farnham: Ashgate. Available at: https://safetydifferently.com/wp-content/uploads/2014/08/SDDriftPaper.pdf.
- Hollnagel, E. (n.d.) Resilience Engineering. Available at: https://erikhollnagel.com/ideas/resilience-engineering.html.
- Hollnagel, E., Pariès, J., Woods, D.D. and Wreathall, J. (eds.) (2011) Resilience Engineering in Practice: A Guidebook. Farnham: Ashgate. Available at: https://api.pageplace.de/preview/DT0400.9781317065296_A31717807/preview-9781317065296_A31717807.pdf.
- Meadows, D.H. (1998) Indicators and Information Systems for Sustainable Development. Available at: https://www.donellameadows.org/wp-content/userfiles/IndicatorsInformation.pdf.
- Meadows, D.H. (1999) Leverage Points: Places to Intervene in a System. Available at: https://donellameadows.org/wp-content/userfiles/Leverage_Points.pdf.
- Meadows, D.H. (2008) Thinking in Systems: A Primer. White River Junction, VT: Chelsea Green. Available at: https://research.fit.edu/media/site-specific/researchfitedu/coast-climate-adaptation-library/climate-communications/psychology-amp-behavior/Meadows-2008.-Thinking-in-Systems.pdf.
- Stockholm Resilience Centre (2015) Applying Resilience Thinking. Available at: https://www.stockholmresilience.org/download/18.10119fc11455d3c557d6928/1459560241272/SRC%2BApplying%2BResilience%2Bfinal.pdf.
- Stockholm Resilience Centre (n.d.) Planetary Boundaries. Available at: https://www.stockholmresilience.org/research/planetary-boundaries.html.
- Taleb, N.N. (2012) Antifragile: Things That Gain from Disorder. New York: Random House. Available at: https://www.penguinrandomhouse.com/books/176227/antifragile-by-nassim-nicholas-taleb/.
- Tang, K.B. and Karen, L. (2012) A New Heuristic Measure of Fragility and Tail Risks. IMF Working Paper. Available at: https://www.imf.org/external/pubs/ft/wp/2012/wp12216.pdf.
