PoliticalWorldAPI Actions, Conditions and Effects
✅ Runtime verified — executed branches WBML-0005 PoliticalWorldAPI 1.14.0
PoliticalWorldAPI exposes a creator-facing action system so addons can define reusable political actions with:
metadata+ optional condition+ handler/effectFor a beginner, the flow is:
register action→ ask whether it can run→ execute it→ condition decides whether handler is allowed→ handler/effects change stateWBML-0005 tested this stack as one subsystem instead of checking a single method in isolation.
ActionDefinition
Section titled “ActionDefinition”The inspected creator source contains fields conceptually equivalent to:
IdCategoryNameKeyDescriptionKeyDisplayNameDescriptionIconSortOrderKingdomCondition ConditionKingdomAction HandlerThe runtime package tested by WBML was API 1.14.0; the inspected source snapshot is older. Use the source for shape and the runtime evidence for the tested behavior.
Minimal action
Section titled “Minimal action”private const string AddonId = "Example.Actions";private const string ActionId = AddonId + ".increase_counter";
PoliticalWorldAPI.RegisterAction( AddonId, new PoliticalWorldAPI.ActionDefinition { Id = ActionId, Category = "example", DisplayName = "Increase counter", Condition = kingdom => kingdom != null, Handler = kingdom => { int current = PoliticalWorldAPI.GetKingdomInt( kingdom, AddonId, "counter", 0 );
PoliticalWorldAPI.SetKingdomInt( kingdom, AddonId, "counter", current + 1 ); } });Use an action ID owned by your addon namespace.
Validation behavior tested by WBML-0005
Section titled “Validation behavior tested by WBML-0005”The suite called the public validation path with deliberately bad definitions.
Runtime API 1.14.0 produced:
PW303 — action ID not owned by addon → invalidPW304 — Handler missing → invalidPW305 — no DisplayName/NameKey → warning, definition still validPractical lesson:
A readable label warning is not the same as a registration-blocking validation error.
Important runtime rule: same-ID registration replaces
Section titled “Important runtime rule: same-ID registration replaces”The first WBML-0005 harness assumed a second RegisterAction with the same ID would be rejected as a duplicate.
Runtime API 1.14.0 instead did this:
first definition registered→ second RegisterAction with same ID returned true→ GetAction exposed second definition→ previous metadata/condition were replacedThe Lab then registered the canonical definition again and verified it was restored.
Treat this as replacement/upsert behavior for the tested runtime.
Why a modder should care:
- reusing an ID can overwrite your previous handler;
- omitted fields in the replacement can disappear from the effective definition;
- accidental ID collisions inside your own addon can silently change behavior instead of producing the duplicate failure you expected.
Do not generalize the rule to future API versions without versioned evidence.
Query and metadata API
Section titled “Query and metadata API”WBML verified the tested action through:
GetAction(...)GetActionsByAddon(...)GetActionsByCategory(...)GetAddonContentSummary(...)The canonical test set returned three live actions in the owner/category queries before cleanup.
ActionInfo.Enabled also changed dynamically when the condition state changed.
Conditions: combinators
Section titled “Conditions: combinators”WBML-0005 verified these runtime semantics:
All(true, null, true) → trueAll(true, false, true) → falseAny(false, null, true) → trueAny(empty) → trueNot(false) → trueNot(null) → trueAny(empty) == true and Not(null) == true are worth documenting explicitly because they are easy to guess incorrectly.
When these semantics are important to your design, keep the API/runtime version in mind.
Conditions: political state
Section titled “Conditions: political state”The suite successfully evaluated helpers against the target kingdom’s live state:
GovernmentIs(current government)IdeologyIs(current ideology)CurrentIs(current current)PoliticalSystemIs(current system)StabilityAtLeast(current stability)StabilityAtMost(current stability)The exact IDs belong to the tested world and are not universal constants for every mod.
Conditions: addon-private state
Section titled “Conditions: addon-private state”WBML seeded its own private test state and verified:
AddonIntAtLeastAddonIntAtMostAddonBoolIsKingdomHasAddonTagThis is a useful pattern for building actions whose availability depends on your addon’s own progression or flags.
Conditions: party state
Section titled “Conditions: party state”The suite also verified executed branches of:
PartySupportAtLeastHasRulingPartyHasActivePartyIdeologyA methodology lesson came from this phase: PartyInfo was re-read immediately before support boundary checks. Do not assume an earlier info snapshot is still current if the simulation may have changed political values.
CanExecuteAction, ExecuteAction, TryExecuteAction
Section titled “CanExecuteAction, ExecuteAction, TryExecuteAction”WBML verified both disabled and enabled paths.
Disabled condition
Section titled “Disabled condition”CanExecuteAction → falseExecuteAction → falsehandler calls → 0TryExecuteAction → Success=falseCode → action-condition-failedEnabled condition
Section titled “Enabled condition”CanExecuteAction → trueExecuteAction → truehandler side effect occurredTryExecuteAction → Success=trueCode → oksecond side effect occurredError results
Section titled “Error results”The tested operation-result codes were:
missing action → action-not-foundnull kingdom → invalid-kingdomdisabled → action-condition-failedsuccess → okThese codes are runtime evidence for API 1.14.0, not a promise that every future API will never add or rename operation codes.
Effects.Sequence
Section titled “Effects.Sequence”WBML composed multiple effects, including a null entry, then executed them through an action handler.
The tested sequence:
SetAddonInt(counter, 10)nullChangeAddonInt(counter, +7)SetAddonBool(flag, true)AddAddonTag(tag)produced:
counter = 17flag = truetag presentThis verified the integration path used in the suite.
Effect helpers verified in WBML-0005
Section titled “Effect helpers verified in WBML-0005”Executed and passed:
SetAddonIntChangeAddonIntSetAddonBoolAddAddonTagRemoveAddonTagChangeStabilitySetStabilitySetPartyRadicalismThe stability probe changed the value by only ±1 and restored it immediately.
The party radicalism probe also changed by ±1 and restored the original value.
Party support: do not treat it as a simple setter in every state
Section titled “Party support: do not treat it as a simple setter in every state”This is the most important safety warning from WBML-0005.
An earlier run tested support when the target kingdom had only one active party. Requesting a lower support value caused the runtime path to normalize the lone active party to:
100Trying to restore the old lower value through the same setter also produced 100.
The final fix4 suite therefore does not perform the exact support-mutation assertion unless a kingdom with at least two active parties is available.
Final status:
👁 Observed: single-active-party support path normalized the lone party to 100🧪 Not verified: exact support mutation/restoration with >=2 active partiesDo not write:
SetPartySupport always assigns exactly the requested percentageOur evidence does not support that statement.
Unregister behavior
Section titled “Unregister behavior”WBML-0005 verified:
UnregisterAction(existing) → trueGetAction(after removal) → nullCanExecuteAction → falseExecuteAction → falsesecond UnregisterAction → falseTryExecuteAction → action-not-foundThe live owner query reached count=0 after cleanup.
Diagnostics bookkeeping caveat
Section titled “Diagnostics bookkeeping caveat”Immediately after the live action query returned zero, the diagnostics report still displayed:
Registered actions: 2following repeated same-ID replacement history.
Status:
👁 Observed bookkeeping mismatchDo not reinterpret that diagnostics count as proof that two live actions still existed; GetActionsByAddon returned zero.
This mismatch deserves a dedicated diagnostics suite later.
Final WBML-0005 result
Section titled “Final WBML-0005 result”PASS=90FAIL=0SKIP=3FINAL GATES: A=PASS B=PASS C=PASS D=PASSSUITE RESULT: PARTIAL PASSThe three SKIPs were all the intentionally unexecuted exact party-support mutation/restoration branch for a world with only one active party.
Every executed assertion passed.
Beginner checklist
Section titled “Beginner checklist”Before registering an action:
- register your addon;
- use an action ID inside your addon namespace;
- provide a handler;
- give the action readable text;
- decide whether a condition is actually needed;
- do not assume same-ID registration will fail;
- check execution/operation results when failure matters;
- re-query live political state for condition decisions;
- restore any temporary test mutation safely;
- be especially careful with party support in single-party states.