πŸ—³οΈ Voting Patterns Template

May 24, 2026 Β· View on GitHub

πŸ“Œ Template Instructions: Copy to analysis/daily/{date}/{article-type}-run{N}/intelligence/voting-patterns.md. Replace every [REQUIRED] marker with analysis derived from get_voting_records, analyze_voting_patterns, analyze_coalition_dynamics, and compare_political_groups. See methodologies/per-artifact-methodologies.md Β§voting-patterns.

🎯 Purpose: Group-by-group coalition arithmetic for the period. Answers "how did each political group behave, where did blocs cohere, where did they fracture, and which cross-group coalitions carried majorities?" Distinct from coalition-dynamics.md (alliance-pair focused) β€” this file is bloc-behaviour focused.


πŸ“‹ Document Metadata

FieldValue
Report ID[REQUIRED: VP-YYYY-MM-DD-runNN]
Analysis Period[REQUIRED: e.g. Q1 2026 (2026-01-01 to 2026-03-31)]
Roll-Call Votes Covered[REQUIRED: count]
Plenary Sessions Covered[REQUIRED: list of part-sessions]
Confidence[REQUIRED: 🟒 HIGH / 🟑 MEDIUM / πŸ”΄ LOW β€” explain in body if not HIGH]

1️⃣ Group Size & Theoretical Coalition Arithmetic

GroupSeats% of 720Role
EPP[#][%][REQUIRED: one-line strategic role]
S&D[#][%][REQUIRED]
PfE[#][%][REQUIRED]
ECR[#][%][REQUIRED]
Renew[#][%][REQUIRED]
Greens/EFA[#][%][REQUIRED]
The Left[#][%][REQUIRED]
ESN[#][%][REQUIRED]
NI[#][%][REQUIRED]

Majority threshold: 361 votes (of 720). Simple majority of votes cast: varies by attendance.


2️⃣ Observed Coalition Patterns (Period)

%%{init: {"theme":"dark","themeVariables":{"primaryColor":"#1565C0","primaryTextColor":"#ffffff","primaryBorderColor":"#0A3F7F","lineColor":"#90CAF9","secondaryColor":"#2E7D32","secondaryTextColor":"#ffffff","tertiaryColor":"#FF9800","tertiaryTextColor":"#000000","mainBkg":"#1565C0","secondBkg":"#2E7D32","tertiaryBkg":"#FF9800","noteBkgColor":"#FFC107","noteTextColor":"#000000","errorBkgColor":"#D32F2F","fontFamily":"Inter, Helvetica, Arial, sans-serif"}}}%%
graph LR
    %% Palette note: this diagram uses political-group colours (EPP blue, S&D red, Renew orange, Greens green, ECR light-blue)
    %% which intentionally differ from the general Hack23 semantic palette defined in ai-driven-analysis-guide.md Β§Colour legend.
    %% Party colours take precedence over the semantic palette whenever a diagram depicts named political groups.
    EPP[EPP<br/>[#]] ---|[agreement %]| SD[S&D<br/>[#]]
    SD ---|[agreement %]| REN[Renew<br/>[#]]
    EPP ---|[agreement %]| REN
    EPP -.-|[agreement %]| ECR[ECR<br/>[#]]
    REN ---|[agreement %]| GRE[Greens/EFA<br/>[#]]

    style EPP fill:#1565C0,color:#ffffff
    style SD fill:#D32F2F,color:#ffffff
    style REN fill:#FF9800,color:#000000
    style GRE fill:#2E7D32,color:#ffffff
    style ECR fill:#0288D1,color:#ffffff
CoalitionGroupsTypical MajorityUse CasesCohesion (%)Evidence
Grand CentreEPP + S&D + Renew[# votes][REQUIRED: policy domains][%][REQUIRED: β‰₯1 RCV ID]
Progressive-CentristS&D + Renew + Greens/EFA + Left[# votes][REQUIRED][%][REQUIRED]
Conservative-RightEPP + ECR + selective PfE[# votes][REQUIRED][%][REQUIRED]
Opposition BlocsPfE + ECR + ESN[# votes][REQUIRED][%][REQUIRED]

3️⃣ Per-Group Behaviour

For each group: cohesion, defection highlights, sample votes.

EPP

  • Internal cohesion: [REQUIRED: % with evidence β€” e.g. 91% across 567 RCVs]
  • Dominant position: [REQUIRED: 1-2 sentences]
  • Notable defections: [REQUIRED: β‰₯1 named MEP + RCV ID, or note "none observed this period"]
  • Cross-group alliances: [REQUIRED: most frequent partners]

S&D

  • Internal cohesion: [REQUIRED]
  • Dominant position: [REQUIRED]
  • Notable defections: [REQUIRED]
  • Cross-group alliances: [REQUIRED]

Renew

  • Internal cohesion: [REQUIRED]
  • Dominant position: [REQUIRED]
  • Notable defections: [REQUIRED]
  • Cross-group alliances: [REQUIRED]

Greens/EFA

  • Internal cohesion: [REQUIRED]
  • Dominant position: [REQUIRED]
  • Notable defections: [REQUIRED]
  • Cross-group alliances: [REQUIRED]

ECR

  • Internal cohesion: [REQUIRED]
  • Dominant position: [REQUIRED]
  • Notable defections: [REQUIRED]
  • Cross-group alliances: [REQUIRED]

PfE

  • Internal cohesion: [REQUIRED]
  • Dominant position: [REQUIRED]
  • Notable defections: [REQUIRED]
  • Cross-group alliances: [REQUIRED]

The Left

  • Internal cohesion: [REQUIRED]
  • Dominant position: [REQUIRED]
  • Notable defections: [REQUIRED]
  • Cross-group alliances: [REQUIRED]

ESN / NI

  • Behaviour notes: [REQUIRED: aggregate position given fragmentation]

4️⃣ Bloc-Behaviour Index

BlocMembersVotes WonVotes LostWin RateTrend vs. Prior Period
Grand Centre[EPP+S&D+Renew][#][#][%][↑ / β†’ / ↓]
Progressive-Centrist[S&D+Renew+Greens+Left][#][#][%][↑ / β†’ / ↓]
National-Right[PfE+ECR+ESN][#][#][%][↑ / β†’ / ↓]
EPP-led right[EPP+ECRΒ±PfE][#][#][%][↑ / β†’ / ↓]

5️⃣ Stress Points & Outlier Votes

RCV IDTopicOutcomeWhy outlier?Coalition flipped?
[REQUIRED][REQUIRED][For/Against/Abstain counts][REQUIRED: β‰₯30 words][yes/no]
[REQUIRED][REQUIRED][...][REQUIRED][...]
[REQUIRED][REQUIRED][...][REQUIRED][...]

β‰₯3 outlier votes required.


6️⃣ Forward Implications

Upcoming VoteExpected CoalitionConfidenceWhat would flip it
[REQUIRED: plenary date + topic][REQUIRED][🟒/🟑/πŸ”΄][REQUIRED]
[REQUIRED][REQUIRED][🟒/🟑/πŸ”΄][REQUIRED]

β‰₯3 forward forecasts.


7️⃣ Voting Data Freshness

Required field β€” consumed by mcp-reliability-audit.md Β§"Data-source bridge" and by Stage-C completeness gate. Copy the value from VotingRecordsFallbackResult.freshnessLabel produced by getVotingRecordsWithFallback in src/mcp/ep-open-data-client.ts.

FieldValue
Data source[REQUIRED: "mcp" / "ep-open-data-portal" / "unavailable"]
Freshness label[REQUIRED: 🟒 MCP (...β†’...) / 🟑 EP Open Data Portal fallback (...β†’...) / πŸ”΄ voting data unavailable for window...]
EP MCP toolget_voting_records (dateFrom / dateTo)
Fallback used?[yes β€” queried EP Open Data Portal /api/v2/decision / no β€” MCP data sufficient / n/a β€” both sources empty]
Attribution[REQUIRED when fallback active: "European Parliament Open Data Portal β€” https://data.europarl.europa.eu β€” CC BY 4.0"]
Confidence adjustment[REQUIRED: explain whether 🟑 or πŸ”΄ widens WEP bands or degrades Admiralty grade per osint-tradecraft-standards.md Β§3]

When source = "unavailable": Do NOT substitute structural-proxy cohesion scores without an explicit πŸ”΄ LOW-confidence flag on every claim in Β§Β§2–4. Widen all WEP bands by ~10 pp. See analysis/methodologies/osint-tradecraft-standards.md Β§3.1 and .github/prompts/07-mcp-reference.md Β§11 item #6.


8️⃣ Confidence Ledger

  • βœ… Roll-call IDs present: [count cited in this file]
  • ⚠️ Aggregate vs. per-MEP: [REQUIRED: note where EP roll-call delay limits claims to LOW]
  • πŸ”¬ Tools used: analyze_voting_patterns, analyze_coalition_dynamics, compare_political_groups, get_voting_records (per session), ep-get-voting-records (fallback, if active)

9️⃣ EP MCP Tool Inputs

EP MCP toolUsed for which sectionNotes
get_voting_recordsΒ§1 RCV-evidence column (every claim cites RCV ID)Aggregate margins; flag LOW if <4 weeks.
ep-get-voting-records (fallback)Β§1 RCV-evidence column when MCP returns emptyEP Open Data Portal /api/v2/decision; activate via getVotingRecordsWithFallback; CC BY 4.0 attribution required.
analyze_voting_patternsΒ§2 Per-MEP behaviour rubricWhen per-MEP feed available; aggregate otherwise.
analyze_coalition_dynamicsΒ§3 Group-cohesion proxyTwo-window deltas.
compare_political_groupsΒ§4 Seat-share normalisationConfirms majority arithmetic.
track_legislationΒ§5 Procedure contextCOD/CNS/APP per RCV.
get_meeting_decisionsΒ§6 Adopted-decision ↔ RCV cross-checkVerifies passage.
get_adopted_textsΒ§8 Outcome confirmationAdopted-text reflects RCV result.
correlate_intelligenceΒ§9 Anomaly alertsDefection / abstention spikes.
detect_voting_anomaliesΒ§9 Outlier RCVsConfigurable sensitivity threshold.

πŸ”Ÿ Worked Pass-1 β†’ Pass-2 Example (Strasbourg-I 2025 voting digest)

❌ Pass-1 (thin, 22 words):

"Several important votes happened. AI Act passed. CRA implementation was approved. Coalitions held. Some defections noted but minor."

βœ… Pass-2 (compliant, 110 words, sourced):

Top 5 RCVs (Strasbourg-I 2025-10-21/24): (1) 2024/0123(COD) Critical Raw Materials Act final 412/189/68 β€” passage margin 178; (2) 2024/0145(COD) AI-Office implementing-act amendment 392/214/41 β€” Renew lost 11 of 84 (Strack-Zimmermann + 10) per analyze_voting_patterns; (3) 2025/2014(RSP) Ukraine-aid 50bn extension 487/126/52 β€” broadest cross-party majority of session; (4) 2024/0099(COD) CRA implementation amendment 367/241/45 β€” closest passage of session; (5) 2025/2901(RSP) Iran-MEK delisting 287/198/153 β€” high abstention signal (153 = 22 %). PfE+ESN+ECR cohesion on RCVs (1)+(4): 84 % per analyze_coalition_dynamics β€” right-flank consolidation continues.


1️⃣1️⃣ Worked Top-5 RCV Table

#Procedure code + short titleDateForAgainstAbstainMarginAnchor group split
12024/0123(COD) Critical Raw Materials Act β€” final2025-10-2241218968+178EPP 184/188 (98 %); S&D 134/136 (99 %); Renew 79/84 (94 %); ECR 41/78 (53 %); PfE 0/84; Greens/EFA 47/53 (89 %)
22024/0145(COD) AI-Office IA amendment2025-10-2239221441+178EPP 184/188 (98 %); S&D 132/136 (97 %); Renew 73/84 (87 %, 11 defectors); ECR 22/78 (28 %); PfE 0/84
32025/2014(RSP) Ukraine-aid 50 bn extension2025-10-2348712652+361EPP 188/188; S&D 136/136; Renew 84/84; ECR 56/78; PfE 18/84; ESN 0/30
42024/0099(COD) CRA implementation amendment2025-10-2336724145+126EPP 181/188; S&D 121/136 (15 dissenters); Renew 81/84; Greens/EFA 12/53 (24 % only); ECR 39/78
52025/2901(RSP) Iran-MEK delisting2025-10-24287198153+89EPP 117/188; S&D 91/136; Renew 51/84; high abstention reflects free-vote on terrorism listing

1️⃣2️⃣ Per-Group Behaviour Rubric (4 EP voting behaviours)

BehaviourDefinitionWorked observation (Strasbourg-I 2025)Score 1-5
Discipline% of group voting with whip on top-5 RCVsEPP 98 %, S&D 97 %, Renew 89 %, Greens/EFA 87 %, ECR 65 %, PfE 92 %, ESN 88 %4 (Grand Coalition); 3 (right-flank)
Defectionnamed MEPs voting against own group β‰₯1 of top-5Strack-Zimmermann + 10 Renew on RCV 2; 15 S&D dissenters on RCV 42 (low β€” Grand Coalition); 4 (S&D fissure on CRA)
Abstentionabstention rate on contested RCVsRCV 5 (Iran-MEK) 22 % abstention β€” high signal5 on RCV 5; 1-2 elsewhere
No-show% of MEPs absent (not voting / not authorised substitute)Top-5 average 8 % (515-pp turnout / 720 seats); rises to 14 % on Thursday RCV 52 (Tue/Wed); 4 (Thu)

1️⃣3️⃣ Anti-patterns β€” REJECT on Pass-2 Review

#Banned patternWhy it fails
1RCV cited without procedure code (e.g. "the AI Act vote")Unindexed; reviewer cannot trace.
2Per-MEP defection claim while EP roll-call publication delay >4 weeksTradecraft violation.
3Top-5 RCV table without abstain columnAbstain is a signal, not noise.
4Group behaviour score without RCV citationScore is judgment-only.
5"Coalition held" verdict on a vote where one anchor group ≀80 % cohesionDefinition mismatch.
6Defection narrative without naming defectors (where public-record permits)Hides the political signal.
7Margin column missing or computed from only For-Against (ignores Abstain)Margin = For - Against; absent column = unverifiable.

1️⃣4️⃣ Cross-References β€” Controlling Methodology


1️⃣5️⃣ Stage-C Completeness Signals

scripts/validate-analysis-completeness.js checks for this artifact:

CheckThresholdSource
Line floorper article-type (breaking 150, week-in-review 150, month-in-review 180, motions 200)reference-quality-thresholds.json
Required H2 substrings"Top RCVs" / "Roll-Call" / "Behaviour" / "Anomalies"structural contract
Mermaid blockβ‰₯1 (xychart of For/Against/Abstain across top-5 preferred)visual contract
Tradecraft markersAdmiralty per RCV; LOW flag for <4-week-old votes; abstain column populatedosint-tradecraft-standards.md
Source diversityβ‰₯3 EP MCP tools (must include get_voting_records or ep-get-voting-records fallback)per-artifact rule
Top-5 coverage5 distinct RCVs cited with procedure codestemplate logic
Voting data freshnessΒ§7 "Voting Data Freshness" table present and source field populatedD-02 fallback compliance

Document Control: /analysis/daily/{date}/{type}-run{N}/intelligence/voting-patterns.md Β· Template v1.2 Β· Depth floor: per article-type minimum defined in ../methodologies/reference-quality-thresholds.json (authoritative β€” e.g. breaking 150, week-in-review 150, month-in-review 180, motions 200).