Political World — hardening a public Event Bus
✅ Source verified 🧯 Failure containment
A naive mod Event Bus can be written in a few lines:
foreach (var callback in subscribers) callback(data);For a private project, that may be enough.
For a public addon framework, it creates several failure modes.
Political World’s Event Bus contains defenses for four of them.
Failure 1 — one callback throws
Section titled “Failure 1 — one callback throws”Naive result:
subscriber A throws→ dispatch stops→ B and C never run→ exception escapes into corePolitical World invokes every subscriber separately inside try/catch.
The failure is attributed to the addon through diagnostics and dispatch continues.
Failure 2 — callback mutates subscriptions
Section titled “Failure 2 — callback mutates subscriptions”Naive result:
foreach live List→ callback unsubscribes→ collection changes during iterationPolitical World creates a list snapshot before dispatch.
Changes affect future dispatches rather than corrupting the current loop.
Failure 3 — subscriber mutates shared event payload
Section titled “Failure 3 — subscriber mutates shared event payload”If every subscriber receives the exact same mutable payload object:
A changes data.NewValue→ B sees modified payloadPolitical World clones PoliticalEventData for each callback.
Important limitation: embedded Kingdom and Actor references still point to live WorldBox objects.
Failure 4 — callback causes an event recursion loop
Section titled “Failure 4 — callback causes an event recursion loop”Example:
government changed event→ addon writes government→ government changed event→ addon writes government→ ...Political World tracks nested event dispatch depth and stops after depth 16.
The exact number is an implementation detail of the inspected snapshot, but the general protection is the important part.
Additional defense — known event IDs
Section titled “Additional defense — known event IDs”A subscriber cannot silently subscribe to an arbitrary typo.
Unknown IDs are rejected and a diagnostic error is recorded.
What this does not solve
Section titled “What this does not solve”An event framework cannot automatically make arbitrary addon code safe.
A callback can still:
- do expensive work;
- mutate live game objects;
- create logical loops below the depth limit;
- hold references longer than intended;
- cause side effects unrelated to the event.
The Event Bus is failure containment, not a sandbox.
Documentation lesson
Section titled “Documentation lesson”When documenting an extension API, document not only:
“Call Subscribe.”
Also document:
- callback failure behavior;
- mutation behavior;
- ordering assumptions;
- recursion limits;
- ownership/registration rules;
- payload lifetime and mutability.
Those details determine whether multiple community addons can coexist.