#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
HQ_10 Compliance Auditor - Governance Compliance Matrix
Project: 2026-voorjaarsconventie-110an (Voorjaarsconventie April 2027)
Bron: uitsluitend Meta-Dossier working/meta-dossier_v1.json (incl. map-extracts)
Output: deliverables/docx/Governance_Compliance_Matrix_v1.0.xlsx
"""
from openpyxl import Workbook
from openpyxl.styles import Font, PatternFill, Alignment, Border, Side
from openpyxl.utils import get_column_letter

OUT = "/root/projects/jg/2026-voorjaarsconventie-110an/deliverables/docx/Governance_Compliance_Matrix_v1.0.xlsx"

NAVY="00338D"; BLUE="1F5FA8"; GOLD="F2A900"; BAND="F5F8FC"; LIGHT="EAF0F8"; GREY_F="EEEEEE"
GREEN_F,GREEN_T="D9EAD3","006600"
AMBER_F,AMBER_T="FFF2CC","9C6500"
RED_F,RED_T="F4CCCC","9C0006"

thin=Side(style="thin",color="B7C4D6")
border=Border(left=thin,right=thin,top=thin,bottom=thin)
hdr_font=Font(name="Calibri",bold=True,color="FFFFFF",size=10)
hdr_fill=PatternFill("solid",fgColor=NAVY)
cell_font=Font(name="Calibri",size=10)
bold_font=Font(name="Calibri",size=10,bold=True)
wrap=Alignment(wrap_text=True,vertical="top")
center=Alignment(wrap_text=True,vertical="top",horizontal="center")
STATUS_STYLE={"Compliant":(GREEN_F,GREEN_T),"Gap":(AMBER_F,AMBER_T),"Action Required":(RED_F,RED_T)}

ROWS=[
# ===== 1. LCI Constitution & By-Laws / Conventie Handboek LCI =====
("LCI Constitution & By-Laws (via Conventie Handboek LCI vs 06)","Chapter XVII - District Convention",
 "Jaarlijkse districtsconventie met formele stemmingen over personen en zaken volgens LCI Constitution & By-Laws en het LCI Conventie Handboek.",
 "Voorjaarsconventie april 2027 wordt ingericht als formele districtsconventie met stemmingen, conform Handboek Lions Conventies vs 06 (29-07-2024).",
 "Action Required",
 "De actuele tekst van LCI Constitution & By-Laws Chapter XVII is niet in het meta-dossier opgenomen. Verifieer procedures vóór vaststelling van de agenda tegen de actuele LCI-tekst (LCI-portal).",
 "District Governor 2026-2027 / Cabinet Secretary","Uiterlijk 31-12-2026"),

("Conventie Handboek LCI vs 06 (29-07-2024)","H3.1 De voorjaarsconventie",
 "Tijdens de voorjaarsconventie deelt de zittende gouverneur de voortgang op het werkplan en worden de inkomende 2e VDG, 1e VDG en DG benoemd; de inkomende DG presenteert het werkplan en de begroting voor het volgende Lionsjaar (start 1 juli).",
 "Conventie april 2027 valt in FY 2026-2027: benoeming inkomende functionarissen FY 2027-2028 en presentatie van werkplan en begroting 2027-2028 moeten worden geagendeerd.",
 "Action Required",
 "Agendapunten 'presentatie werkplan & begroting inkomende DG' en 'benoeming inkomende 2e VDG / 1e VDG / DG' opnemen in de concepagenda; werkplan 2027-2028 (draft) tijdig opvragen.",
 "District Governor 2026-2027 / Districtssecretaris","Concepagenda (± nov-dec 2026)"),

("Conventie Handboek LCI vs 06 (29-07-2024)","Vergaderstukken / uitnodiging",
 "Agenda en vergaderstukken zijn uiterlijk 1 maand (30 dagen) vóór de conventie voor leden benaderbaar via site, uitnodiging en ownCloud; tijdige beschikbaarstelling is een statutaire verplichting. Uitnodiging bevat directe links naar aanmeldformulier en agenda/stukken.",
 "Uitnodiging, agenda en alle vergaderstukken moeten uiterlijk 30 dagen vóór de conventie (± begin maart 2027) digitaal beschikbaar zijn.",
 "Action Required",
 "Publicatieplanning met QC-moment opnemen in het projectplan; publicatiekalender koppelen aan de exacte conventiedatum zodra vastgesteld.",
 "Districtssecretaris (Cabinet Secretary)","Uiterlijk 30 dagen vóór conventie (± begin maart 2027)"),

("Conventie Handboek LCI vs 06 (29-07-2024)","Registratie",
 "De secretaris zit duidelijk zichtbaar bij de entree van de locatie, noteert de aanwezigen en deelt badges uit met naam en clubnaam, alsmede de stembiljetten/stemkaarten.",
 "Registratiebureau bij de entree met badge-uitgifte, uitreiking stemkaarten en stembiljetten, en aparte telling van stemgerechtigden en niet-stemgerechtigden (gekoppeld aan HR Art. 3).",
 "Action Required",
 "Registratieprocedure en -bureau organiseren: bezetting, badges, stemkaarten, stembiljetten, tellijsten; registratie start minimaal 1 uur vóór opening.",
 "Districtssecretaris / Registratiebureau","Procedure gereed ± februari 2027"),

("Conventie Handboek LCI vs 06 (29-07-2024)","Agenda - vaste agendapunten",
 "Welkom, roll-call (wie aanwezig/afgemeld; hoeveel stemmen vertegenwoordigd) en rondvraag zijn vaste agendapunten. Na een stemming op personen een apart agendapunt om de telling van stembiljetten mogelijk te maken. Raadpleeg vergaderstukken van eerdere conventies.",
 "Vaste agendapunten en tellijst-momenten opnemen in de agenda van april 2027; vergaderstukken Najaarsconventie 17-10-2024 als referentie gebruiken.",
 "Compliant",
 "Vaste agendapunten en verwijzing naar het verslag van de Najaarsconventie 2024 zijn verwerkt in Procedure_Voorjaarsconventie_2027_v1.0.docx; hertoetsen bij agenda-vaststelling.",
 "Districtssecretaris","Doorlopend / bij agenda-vaststelling"),

("Conventie Handboek LCI vs 06 (29-07-2024)","Voorjaarsconventie - verplichte onderwerpen",
 "Voor de voorjaarsconventie agendeer je het herdenken van de overledenen, de presentatie van het werkplan, de begroting en de verkiezing/benoeming van de 2e, 1e en Districtsgouverneur.",
 "Herdenkingsmoment, werkplan- en begrotingspresentatie en het verkiezings-/benoemingsblok moeten in april 2027 worden opgenomen.",
 "Action Required",
 "Herdenkingsmoment en verkiezingsblok in de concepagenda opnemen; namen overledenen uiterlijk 6 weken vóór conventie verzamelen via zonevoorzitters.",
 "District Governor / Districtssecretaris","Concepagenda; namen ± 6 weken vóór conventie"),

("Conventie Handboek LCI vs 06 (29-07-2024)","Locatie - richtlijnen",
 "Bezoek de locatie vooraf; stem met de uitbater af over exacte locatie, parkeren, gelijktijdige gezelschappen, routing en opbouw; zorg voor een afgesloten deel van de locatie zodat de vergadering ongestoord kan plaatsvinden; test de geluidsinstallatie minimaal de dag tevoren.",
 "Locatiebezoek en -afstemming moeten worden uitgevoerd; afgesloten zaal en werkende geluidsinstallatie zijn randvoorwaarden voor het formele vergaderdeel.",
 "Action Required",
 "Locatieteam wijzen; locatiebezoek en afspraken met uitbater documenteren; AV-check met testmoment dag tevoren opnemen in de checklist conventiedag.",
 "Commissaris Voorjaarsconventie / Organiserend comité","Locatiebezoek uiterlijk Q4-2026; AV-test dag vóór conventie"),

("Conventie Handboek LCI vs 06 (29-07-2024)","Vlaggenceremonie",
 "Bij de voorjaarsconventie hoort een vlaggenceremonie: eerst de VS-vlag, daarna de vlaggen van buitenlandse gasten in volgorde van belangrijkheid van de gast, dan de Nederlandse vlag; met bijbehorende volksliederen (bij NL het hele eerste couplet van het Wilhelmus).",
 "Vlaggenceremonie voorbereiden indien internationale gasten (bevriende gouverneurs) worden uitgenodigd; spreektijd en voertaal vooraf afspreken.",
 "Gap",
 "Beslissing nemen over uitnodiging internationale gasten; indien ja: vlaggen, muziek en protocol regelen en in het programma opnemen.",
 "District Governor / Protocolcommissie","Beslissing ± 6 maanden vóór conventie (oktober 2026)"),

("Conventie Handboek LCI vs 06 (29-07-2024)","Organiserend comité / host clubs",
 "De keuze van de stad wordt door de districtsgouverneur gemaakt evenals het werven en besturen van het organiserend comité; meestal bieden meerdere lokale Lionsclubs een programma aan tijdens en na de conventie; de DG is de linking pin samen met de (ambtelijk) secretaris. De dag wordt afgesloten met een gezamenlijke borrel.",
 "DG 2026-2027 wijst de gaststad aan en werft het organiserend comité met lokale clubs (host clubs); omrand programma (rondleiding, sprekers, afsluitende borrel) door host clubs laten verzorgen.",
 "Action Required",
 "Gaststad en host clubs bevestigen; organiserend comité formeren met mandaat en budget; afspraken met host clubs vastleggen.",
 "District Governor 2026-2027 / Commissaris Voorjaarsconventie","Uiterlijk 31-12-2026"),

("Conventie Handboek LCI vs 06 (29-07-2024)","Notulering / verslag",
 "Het formele deel van de conventie wordt genotuleerd; van de conventie wordt een verslag opgemaakt (vgl. Verslag Districtsconventie 17-10-2024 als formaat: aanwezigen, besluiten, stemminguitslagen).",
 "Notulist aanwijzen; conventieverslag opmaken conform het formaat van het verslag Najaarsconventie 2024 en tijdig verspreiden.",
 "Action Required",
 "Notulist vastleggen in de organisatiestructuur; verslagsjabloon op basis van het verslag 2024 opstellen; verspreidingstermijn vaststellen (14 dagen na vergadering als richtsnoer uit HR Art. 21.4).",
 "Cabinet Secretary / Notulist","Verslag uiterlijk 14 dagen na conventie (± mei 2027)"),
]

# ===== 2. MD110 Huishoudelijk Reglement mei 2021 =====
ROWS += [
("MD 110 Huishoudelijk Reglement mei 2021","Sectie 1, Art. 2.1 - Oproeping",
 "De oproeping wordt door de gouverneursraad ten minste 30 dagen vooraf ter kennis gebracht aan clubs, clubs in oprichting, alle Lions en Leoclubs, met: datum, aanvangstijdstip en locatie; agenda met alle te behandelen onderwerpen; voorstellen/bijlagen; aanvangstijd registratie; good-standing vereiste; verplichting om zich uiterlijk 48 uur vóór aanvang aan te melden voor stemrecht.",
 "Oproeping moet uiterlijk ± begin maart 2027 verzonden zijn met alle voorgeschreven onderdelen; aanmeldsysteem moet de 48-uursgrens voor stemrechtregistratie afdwingen.",
 "Action Required",
 "Oproepingsbrief opstellen volgens checklist Art. 2.1; aanmeldformulier voorzien van deadline-automatiek (48 uur) en good-standing vermelding.",
 "Gouverneursraad / Districtssecretaris","Oproeping uiterlijk 30 dagen vóór conventie; systeem gereed ± januari 2027"),

("MD 110 Huishoudelijk Reglement mei 2021","Sectie 1, Art. 2.2 - Aanwijzing stemgerechtigde",
 "Clubs ontvangen direct na aanmelding van een clublid mededeling daarvan en moeten uiterlijk 24 uur vóór aanvang doorgeven wie namens de club stemgerechtigd is; bij geen of niet-tijdig bericht is de club niet stemgerechtigd.",
 "Aanmeldsysteem moet automatische bevestiging plus verzoek tot aanwijzing van de stemgerechtigde naar clubs sturen met 24-uursdeadline.",
 "Action Required",
 "Workflow in aanmeldsysteem inrichten (automatische clubnotificatie); handmatige fallback; communicatie naar clubsecretarissen via zonevoorzitters.",
 "Districtssecretaris / Informatiemanager (LionsBase)","Gereed uiterlijk 6 weken vóór conventie (februari 2027)"),

("MD 110 Huishoudelijk Reglement mei 2021","Sectie 1, Art. 2.3-2.4 - Spreekrecht",
 "Leden die niet door hun club als stemgerechtigde zijn aangewezen hebben toegang zonder spreekrecht; leden van MD-organen en MD-stichtingen hebben spreekrecht.",
 "Toegangs- en spreekrechtregeling meenemen in het registratieprotocol (badgecategorieën: stemgerechtigd / niet-stemgerechtigd / spreekrecht).",
 "Compliant",
 "Regeling is opgenomen in de registratieprocedure; badgecategorieën worden onderscheiden bij badge-ontwerp.",
 "Registratiebureau / Districtssecretaris","Badge-ontwerp ± januari 2027"),

("MD 110 Huishoudelijk Reglement mei 2021","Sectie 1, Art. 3 - Registratie en totaaltellingen",
 "Registratie vindt plaats vanaf ten minste 1 uur vóór opening tot de opening; elke stemgerechtigde ontvangt stemkaart en stembiljet(ten) voor elke geagendeerde stemming; de GR zorgt voor herstemmingsbiljetten; het registratiebureau levert na sluiting de totaaltellingen aan de conventievoorzitter (uit te brengen stemmen, stemgerechtigden, niet-stemgerechtigden, aanwezige clubs).",
 "Registratiebureau start 1 uur vóór opening, reikt stemkaarten en stembiljetten (incl. reserves voor herstemmingen) uit en levert de quorumtelling aan de voorzitter.",
 "Action Required",
 "Registratieprotocol opstellen met tijdschema, tellijsten en overdrachtsformat quorumtelling; reservebiljetten laten drukken.",
 "Voorzitter registratiebureau / Gouverneursraad","Protocol gereed ± februari 2027"),

("MD 110 Huishoudelijk Reglement mei 2021","Sectie 1, Art. 4 - Voorstellen GR en clubs",
 "De GR legt eigen voorstellen voor (ten minste alle statutair verplichte onderwerpen) en ziet toe op tijdige aanlevering door kandidaat-DG's en vorige DG's; elke club in good standing kan voorstellen indienen; alle voorstellen omvatten een schriftelijk conceptbesluit met toelichting.",
 "Voorstelprocedure met inlevertermijnen en format (conceptbesluit + toelichting) moet naar clubs worden gecommuniceerd; GR-voorstellen tijdig opstellen.",
 "Action Required",
 "Oproep aan clubs publiceren samen met de conventie-aankondiging; voorstelformulier (conceptbesluit + toelichting) beschikbaar stellen.",
 "Gouverneursraad / Districtssecretaris","Publicatie met aankondiging; deadline clubs = 20 dagen vóór conventie"),

("MD 110 Huishoudelijk Reglement mei 2021","Sectie 1, Art. 5 - Adviezen raad van advies",
 "De raad van advies kan over conventiestukken (werkplan, begroting, jaarrekening, onkostenvergoedingsregeling) advies uitbrengen; schriftelijke adviezen die tot 7 dagen vóór de conventie zijn uitgebracht, worden door de GR zo snel mogelijk verzonden; latere adviezen worden bij registratie uitgereikt.",
 "Adviesprocedure moet zijn geborgd: doorstuurmechanisme voor schriftelijke adviezen en uitreiking bij registratie.",
 "Action Required",
 "Afspraak maken met de raad van advies over termijn en logistiek; uitreiking late advieken opnemen in registratieprotocol.",
 "Gouverneursraad / Voorzitter raad van advies","Uiterlijk 7 dagen vóór conventie"),

("MD 110 Huishoudelijk Reglement mei 2021","Sectie 1, Art. 6 - Ontwerpresoluties en -moties",
 "Elke club in good standing kan ontwerpresoluties en -moties voorleggen; deze worden schriftelijk ingebracht en kunnen tevoren worden toegezonden of tijdens de vergadering worden ingediend.",
 "Procedure voor indiening en behandeling van resoluties/moties moet zijn ingericht (innamepunt, schriftelijke vorm).",
 "Action Required",
 "Innamepunt en formatspecificatie voor resoluties/moties communiceren; procedure in de werkinstructie opnemen.",
 "Districtssecretaris","Bij publicatie oproeping"),

("MD 110 Huishoudelijk Reglement mei 2021","Sectie 1, Art. 7 - Termijn voorstellen en agendavaststelling",
 "Voorstellen, amendementen, ontwerpresoluties en -moties die uiterlijk 20 dagen vóór de conventie door de GR zijn ontvangen, worden digitaal aan de clubs verzonden, aanvullend op de agenda geplaatnd en in stemming gebracht. Late indieners: plaatsing via stemming bij agendapunt 'Vaststelling van de agenda' (zonder discussie); staande de conventie: onmiddellijke stemming over behandeling.",
 "Deadline 20 dagen vóór conventie (± begin maart 2027) moet worden gecommuniceerd en afgedwongen; procedure late stukken moet de voorzitter beheersen.",
 "Action Required",
 "Datum 20-dagentermijn vaststellen zodra conventiedatum bekend; procedure late indiening opnemen in voorzittersinstructie (script agendapunt 'Vaststelling van de agenda').",
 "Districtssecretaris / Conventievoorzitter","Uiterlijk 20 dagen vóór conventie"),

("MD 110 Huishoudelijk Reglement mei 2021","Sectie 1, Art. 8-9 - Orde van de vergadering",
 "De orde van de vergadering wordt bepaald door de conventievoorzitter (toewijzen spreektijd, beëindigen discussie, overgang tot stemming, sluiting); na aanvang van een stemming over zaken wordt door niemand ter zake het woord gevoerd tot de uitslag is vastgesteld.",
 "Voorzitter (DG 2026-2027) moet over een vergaderscript en instructie beschikken; vergaderorde-procedures in het draaiboek opnemen.",
 "Action Required",
 "Voorzittersscript en vergaderregels opstellen (spreektimebeheer, stemmingdiscipline); timekeeper (Lion tamer / tail twister) aanwijzen.",
 "Conventievoorzitter (DG 2026-2027) / Districtssecretaris","Script gereed ± 6 weken vóór conventie"),

("MD 110 Huishoudelijk Reglement mei 2021","Sectie 1, Art. 10-14 - Verkiezing van personen",
 "Kandidaten voor verkiezing door de conventie dienen te zijn gekandideerd door de districtsconventie van hun district (enkele kandidaat per functie); schriftelijke kandidaatstelling uiterlijk 30 dagen vóór de conventie, rondgezonden aan de geadresseerden; kandidaten krijgen maximaal 5 minuten voor toelichting; bij meerdere kandidaten volgorde bij loting; herstemmingen volgens statuten; certificering door de GR bij internationale functies.",
 "Kandidaatstellingsprocedure en -termijn (30 dagen) moeten worden gecommuniceerd; verkiezingsprocedure met presentatie (5 min), loting en mogelijke herstemming moet in het draaiboek.",
 "Action Required",
 "Kandidaatstellingsroute en deadline vaststellen; verkiezingsdraaiboek opstellen incl. presentatie-, lotings- en herstemmingsprocedure.",
 "Gouverneursraad / Conventievoorzitter","Kandidaatstelling uiterlijk 30 dagen vóór conventie; draaiboek ± februari 2027"),

("MD 110 Huishoudelijk Reglement mei 2021","Sectie 1, Art. 15 - Stembureau",
 "De GR benoemt vóór de conventie de voorzitter en leden van het stembureau (zoveel leden dat de stemmen vlot kunnen plaatsvinden); leden worden gepositioneerd per blok stemgerechtigden; de voorzitter van het stembureau verifieert of bij schriftelijke stemming is voldaan aan de quorumbepalingen.",
 "Stembureau moet tijdig worden benoemd en gepositioneerd; quorumcontrole (>50% stemgerechtigden) is expliciete taak.",
 "Action Required",
 "Stembureauleden benoemen en instrueren (blokpositionering, tellijsten, quorumverificatie); opnemen in draaiboek.",
 "Gouverneursraad / Voorzitter stembureau","Benoeming uiterlijk 6 weken vóór conventie"),

("MD 110 Huishoudelijk Reglement mei 2021","Sectie 1, Art. 16-17 - Wijze van stemmen",
 "Over zaken wordt gestemd door opsteken van stemkaarten; precieze telling kan achterwege blijven als de meerderheid visueel duidelijk is; bij twijfel direct herstemming; acclamatie mogelijk tenzij bezwaar; stemmen over personen schriftelijk op gewaarmerkte stembiljetten (alleen één kruisje); verkeerd biljet, meerdere kruisjes of toevoegingen maken de stem ongeldig; herstemming op afzonderlijk biljet.",
 "Stemprocedure (kaarten voor zaken, biljetten voor personen, ongeldigverklaring) moet in het draaiboek en de instructie van stembureau en voorzitter zijn opgenomen.",
 "Action Required",
 "Procedurehandleiding stemmen opstellen (incl. lijst ongeldigverklaringen en herstemmingsbiljetten);; instrueren stembureau.",
 "Voorzitter stembureau / Conventievoorzitter","± februari 2027"),

("MD 110 Huishoudelijk Reglement mei 2021","Sectie 1, Art. 18 - Slotbepaling",
 "In alle gevallen waarin dit reglement niet voorziet, beslist de conventie op voorstel van de conventievoorzitter.",
 "Voorzitter moet op onvoorziene situaties kunnen inspelen; voorziening in voorzittersscript opnemen.",
 "Compliant",
 "Bepaling is opgenomen in de procedure (beslispunt voorzitter); bij draaiboekactualisatie explicititeren.",
 "Conventievoorzitter (DG 2026-2027)","Doorlopend"),

("MD 110 Huishoudelijk Reglement mei 2021 / MD 110 Statuten Art. 11","Stemrechtclubs (controleset)",
 "Stemrechten: 1 stem per 10 leden per club (minimaal 1, maximaal 5). Tellende lidmaatschapscategorieën (HR Art. 19): actief, buitengewoon, vrijgesteld, lid voor het leven, geaffilieerd; niet-tellend: erelid en geassocieerd lid. Buitengewone en geassocieerde leden kunnen de club niet als stemgerechtigde vertegenwoordigen.",
 "Stemrechtentabel per club moet vooraf worden opgesteld op basis van de ledenadministratie (per 1 juli 2026) met correcte categorie-weging, min 1 / max 5 stemmen.",
 "Action Required",
 "Stemrechtentabel laten opstellen door de Informatiemanager op basis van de MD-ledenadministratie; tabel laten verifieren door het registratiebureau vóór de oproeping.",
 "Informatiemanager (LionsBase) / Gouverneursraad","Tabel gereed vóór oproeping (± januari 2027)"),

("MD 110 Statuten (via controleset sources.md)","Quorum",
 "Quorum voor besluitvoting: meer dan 50% van de stemgerechtigden (verificatie door de voorzitter van het stembureau, HR Art. 15.4).",
 "Quorumberekening moet tijdens de conventie real-time mogelijk zijn op basis van de registratietelling (aanwezige stemgerechtigden vs. totaal toegewezen stemmen).",
 "Action Required",
 "Quorumformule en tellijsten opnemen in het registratieprotocol; drempelwaarde vooraf berekenen per stemrechtentabel.",
 "Voorzitter stembureau / Registratiebureau","Conventiedag; voorbereiding ± februari 2027"),
]

# ===== 3. District 110AN specifieke regels: roulatie, host club =====
ROWS += [
("Conventie Roulatieschema (GR, vastgesteld 06-05-2022)","Roulatieschema landelijke voorjaarsconventies",
 "De Gouverneursraad heeft op 6-5-2022 het roulatieschema voor de landelijke voorjaarsconventies vastgesteld: 2023-2024 110CO; 2024-2025 110BN; 2025-2026 110AN; 2026-2027 110AZ; 2027-2028 110CW; 2028-2029 110BZ. De locatie/gastdistrict van de voorjaarsconventie volgt dit schema.",
 "De voorjaarsconventie april 2027 valt in Lionsjaar 2026-2027. Volgens het roulatieschema is het gastdistrict voor 2026-2027: 110AZ (110AN was gastdistrict in 2025-2026). Dit raakt aan de opzet van dit project (110AN als organisator in april 2027).",
 "Gap",
 "KRITIEKE BEVINDING: verifieer het mandaat en de rol van 110AN in de voorjaarsconventie april 2027: (a) betreft het een districtsconventie van 110AN (eigen bijeenkomst van 110AN), of (b) de landelijke voorjaarsconventie die conform roulatie door 110AZ wordt gehost? Constateer besluit GR; bij afwijking van het schema: GR-besluit en eventuele schema-update documenteren.",
 "Gouverneursraad / District Governor 110AN 2026-2027","Uiterlijk 31-10-2026 (vóór locatie- en budgetvaststelling)"),

("Conventie Roulatieschema (GR, vastgesteld 06-05-2022)","Roulatie - locatiebepaling",
 "De locatie van de landelijke voorjaarsconventie wordt bepaald op basis van het roulatieschema (gastdistrict kiest stad en organiseert, veelal met meerdere lokale Lionsclubs).",
 "Locatiekeuze voor april 2027 moet conform het roulatieschema worden afgehandeld en formeel worden bevestigd door de GR.",
 "Action Required",
 "Locatiebesluit laten ratificeren door de Gouverneursraad; besluit en motivering vastleggen in de projectdocumentatie.",
 "Gouverneursraad / Organiserend comité","Uiterlijk 31-12-2026"),

("Verslag Najaarsconventie 110AN (17-10-2024)","Lessen geleerd vorige conventie",
 "Het verslag van de Districtsconventie/Leden Ontmoetingsavond van 17-10-2024 (Stadscaffee Laurens, Kerkrade) bevat het formaat en de ervaringen van de laatste 110AN-conventie en geldt als referentie voor agenda, verslagvorm en organisatie.",
 "Lessen en formaat van 17-10-2024 meenemen in de concepagenda, het verslagsjabloon en de organisatiechecklist van april 2027.",
 "Compliant",
 "Verslag 2024 is als bron in het meta-dossier opgenomen en verwerkt in de procedure; actualiseren zodra verslag Najaarsconventie 2026 beschikbaar is.",
 "Districtssecretaris","Doorlopend"),

("District 110AN - Club Health Assessment (sep. 2025)","Good standing clubs",
 "Stemrecht en voorstelrecht van clubs vereisen good standing (statuten MD/HR Art. 2.1); het Club Health Assessment District 110AN t/m september 2025 geeft inzicht in clubstatus en ledenaantallen.",
 "Good standing-status van alle 110AN-clubs moet vóór de oproeping zijn gecontroleerd; ledenaantallen (per 1 juli) bepalen de stemrechtentabel.",
 "Action Required",
 "Good-standing controle doorlopen met de Informatiemanager; clubs met achterstand tijdig attenderen (herstelmogelijkheid vóór registratie).",
 "District Governor / Informatiemanager","Vóór oproeping (± januari 2027)"),
]

# ===== 4. Werkplan AN 2026-2027 draft v1 =====
ROWS += [
("Werkplan AN 2026-2027 (draft v1)","Kabinet 2026-2027 - voorzitterschap",
 "De District Governor 2026-2027 is voorzitter van het district (collegiaal Dagelijks Bestuur; bij staking van stemmen telt de stem van de DG dubbel). Conform controleset: voorzitter van de conventie is de DG 2026-2027; secretaris is de Cabinet Secretary 2026-2027.",
 "DG 2026-2027 treedt op als conventievoorzitter; Cabinet Secretary als conventiesecretaris (registratie, notulen, stukken).",
 "Compliant",
 "Rolverdeling is vastgelegd in Werkplan 2026-2027 (draft) en overeenkomstig de controleset; namen na definitieve vaststelling van het werkplan actualiseren.",
 "District Governor 2026-2027 / Cabinet Secretary","Actualisatie bij werkplan-vaststelling"),

("Werkplan AN 2026-2027 (draft v1)","Kabinet 2026-2027 - commissaris Voorjaarsconventie",
 "Het kabinet 2026-2027 kent een commissaris Voorjaarsconventie; in de draft zijn meerdere functies nog niet ingevuld ([Naam], [Club]), waaronder 2e VDG, secretaris, penningmeester en diverse commissarissen.",
 "De commissaris Voorjaarsconventie is de operationele trekker van de conventieorganisatie; zijn/haar benoeming en mandaat zijn randvoorwaarde voor het project.",
 "Gap",
 "Commissaris Voorjaarsconventie (en ontbrekende kabinetsfuncties) tijdig definitief benoemen; mandaat, budget en rapportagelijn vastleggen.",
 "District Governor 2026-2027 (invullen) / Gouverneursraad","Uiterlijk 31-10-2026"),

("Werkplan AN 2026-2027 (draft v1)","Commissiestructuur / GAT / zonevoorzitters",
 "Het kabinet omvat Dagelijks Bestuur, Global Action Team (GLT/GST/GMT/GET), zonevoorzitters (1A-3B), commissarissen (o.a. Voorjaarsconventie, Lions Media, Informatiemanager/LionsBase) en stichtingsfunctionarissen (LCIF, Lions Helpen, Jeugduitwisseling, Fight for Sight, Duurzame Leefomgeving).",
 "De conventieorganisatie kan putten uit deze structuur: zonevoorzitters voor communicatie naar clubs, Lions Media voor promotie, Informatiemanager voor registratie/stemrechtentabel.",
 "Action Required",
 "Taaktoedeling conventie per kabinetsfunctie vastleggen in het organogram van het project; betrokkenheid bevestigen in de kickoff.",
 "Commissaris Voorjaarsconventie / Cabinet Secretary","Kickoff project (± oktober 2026)"),

("Werkplan AN 2026-2027 (draft v1)","Voornemen meerdaagse voorjaarsconventie",
 "Het werkplan 2026-2027 kondigt een meerdaagse voorjaarsconventie aan (naast andere programmapunten zoals afsluitende borrel voor alle Lions uit de omgeving).",
 "Een meerdaagse opzet vergt aanvullende logistiek (accommodatie, programma, vergunningen) en budget; toets aan de Handboek-eisen voor het formele vergaderdeel (afgesloten locatie, registratie).",
 "Action Required",
 "Programmavisie (1- vs. meerdaags) uitwerken incl. budgettoets aan de Districtbegroting; besluitvorming DB documenteren.",
 "Commissaris Voorjaarsconventie / Districtspenningmeester","Programmavisie uiterlijk 31-12-2026"),

("Districtbegroting 110 AN 2025-2026","Budgetkader conventie",
 "De Districtbegroting 110 AN biedt het financiële referentiekader (aantal leden in district ca. 1200) waarbinnen de conventie moet worden begroot; het eigen vermogen van het MD bedraagt minimaal EUR 175.000 en maximaal EUR 225.000 per 30 juni (HR Art. 25.3).",
 "Conventiebegroting 2026-2027 moet aansluiten op de districtsfinanciën en het werkplan; geen ongedekte verplichtingen aangaan.",
 "Action Required",
 "Conventiebegroting opstellen en laten vaststellen door het DB/GR; borg- en afrekenprocedure met host clubs/locatie contractueel vastleggen.",
 "Districtspenningmeester / Commissaris Voorjaarsconventie","Begroting uiterlijk 31-12-2026; afrekening ± juni 2027"),
]

# ===== 5. Overig: GR-werkwijze (HR Sectie 3) =====
ROWS += [
("MD 110 Huishoudelijk Reglement mei 2021","Sectie 3, Art. 21 - Werkmethode GR (borgerde besluitvorming)",
 "De GR vergadert zo dikwijls als nodig; van elke vergadering wordt door de secretaris een verslag en besluitenlijst opgesteld die binnen 14 dagen wordt toegezonden en in de eerstvolgende vergadering wordt vastgesteld; besluiten vereisen aanwezigheid van de meerderheid van de leden.",
 "Alle conventie-besluiten van de GR (oproeping, locatie, stembureau, voorstellen) moeten via deze route worden vastgesteld en gedocumenteerd.",
 "Action Required",
 "Besluitenlijst-aanpak opzetten voor conventiebeslissingen in de GR; besluiten binnen 14 dagen verzenden en agenderen voor vaststelling.",
 "Gouverneursraad / (Ambtelijk) secretaris GR","Doorlopend; eerste besluiten uiterlijk Q4-2026"),
]

# ===================== WORKBOOK =====================
wb = Workbook()

# ---------- Sheet 1: Compliance Matrix ----------
ws = wb.active
ws.title = "Compliance Matrix"
HEADERS = ["Nr","Regelbron","Artikel / Paragraaf","Eis","Toepassing op Conventie (april 2027)",
           "Status","Actie","Verantwoordelijke","Deadline"]
WIDTHS  = [5, 26, 24, 46, 46, 15, 46, 24, 24]

# Titelblok
ws.merge_cells("A1:I1")
c = ws["A1"]; c.value = "GOVERNANCE COMPLIANCE MATRIX - VOORJAARSCONVENTIE DISTRICT 110AN - APRIL 2027"
c.font = Font(name="Calibri", bold=True, size=13, color="FFFFFF"); c.fill = PatternFill("solid", fgColor=NAVY)
c.alignment = Alignment(horizontal="center", vertical="center"); ws.row_dimensions[1].height = 26

ws.merge_cells("A2:I2")
c = ws["A2"]; c.value = ("Toetsing van LCI / MD110 / District 110AN governance-regels op de conventie-organisatie  |  "
                         "Bron: Meta-Dossier v1 (22 bronnen)  |  Status: v1.0  |  Auditdatum: 26-08-2026  |  Auditor: HQ_10 Compliance Auditor")
c.font = Font(name="Calibri", italic=True, size=9, color=NAVY); c.fill = PatternFill("solid", fgColor=LIGHT)
c.alignment = Alignment(horizontal="center", vertical="center"); ws.row_dimensions[2].height = 18

HDR_ROW = 4
for i, h in enumerate(HEADERS, 1):
    cell = ws.cell(row=HDR_ROW, column=i, value=h)
    cell.font = hdr_font; cell.fill = hdr_fill; cell.alignment = center; cell.border = border
ws.row_dimensions[HDR_ROW].height = 30
for i, w in enumerate(WIDTHS, 1):
    ws.column_dimensions[get_column_letter(i)].width = w

for n, r in enumerate(ROWS, 1):
    bron, art, eis, toep, status, actie, verantw, deadline = r
    vals = [n, bron, art, eis, toep, status, actie, verantw, deadline]
    rowidx = HDR_ROW + n
    for col, v in enumerate(vals, 1):
        cell = ws.cell(row=rowidx, column=col, value=v)
        cell.font = cell_font; cell.border = border
        cell.alignment = center if col in (1, 6) else wrap
        if col == 1:
            cell.fill = PatternFill("solid", fgColor=GREY_F); cell.font = bold_font
        elif n % 2 == 0:
            cell.fill = PatternFill("solid", fgColor=BAND)
    # statuskleur
    sc = ws.cell(row=rowidx, column=6)
    fill_c, font_c = STATUS_STYLE[status]
    sc.fill = PatternFill("solid", fgColor=fill_c)
    sc.font = Font(name="Calibri", size=10, bold=True, color=font_c)

last = HDR_ROW + len(ROWS)
ws.auto_filter.ref = f"A{HDR_ROW}:I{last}"
ws.freeze_panes = f"A{HDR_ROW+1}"

# ---------- Sheet 2: Samenvatting ----------
ss = wb.create_sheet("Samenvatting")
ss.column_dimensions["A"].width = 42; ss.column_dimensions["B"].width = 60
ss.merge_cells("A1:B1")
c = ss["A1"]; c.value = "SAMENVATTING & CONTROLESET FEITEN"
c.font = Font(name="Calibri", bold=True, size=12, color="FFFFFF"); c.fill = PatternFill("solid", fgColor=NAVY)
c.alignment = Alignment(horizontal="center", vertical="center"); ss.row_dimensions[1].height = 22

comp  = sum(1 for r in ROWS if r[4] == "Compliant")
gap   = sum(1 for r in ROWS if r[4] == "Gap")
act   = sum(1 for r in ROWS if r[4] == "Action Required")

data = [
    ("Toetsingskader", ""),
    ("1. LCI Constitution & By-Laws / Conventie Handboek LCI (vs 06)", "10 regels"),
    ("2. MD110 Huishoudelijk Reglement mei 2021 (incl. quorum/stemrecht)", "15 regels"),
    ("3. District 110AN specifiek (roulatie, host club, good standing)", "4 regels"),
    ("4. Werkplan AN 2026-2027 draft (commissies, DG/VDG/cabinet, budget)", "5 regels"),
    ("5. GR-werkwijze (HR Sectie 3)", "1 regel"),
    ("", ""),
    ("Statusverdeling", ""),
    ("Compliant", f"{comp} regels"),
    ("Gap", f"{gap} regels"),
    ("Action Required", f"{act} regels"),
    ("Totaal", f"{len(ROWS)} regels"),
    ("", ""),
    ("Kritische bevindingen", ""),
    ("K1 - Roulatieschema", "Voorjaarsconventie FY 2026-2027 is volgens GR-roulatieschema (06-05-2022) toegewezen aan 110AZ; 110AN was gastdistrict 2025-2026. Mandaat/rol van 110AN in april 2027 vereist GR-verify vóór locatie- en budgetvaststelling (uiterlijk 31-10-2026)."),
    ("K2 - LCI Constitution Chapter XVII", "Actuele LCI-tekst ontbreekt in het meta-dossier; verify vóór agenda-vaststelling (uiterlijk 31-12-2026)."),
    ("K3 - Kabinetsbezetting", "Commissaris Voorjaarsconventie en diverse kabinetsfuncties in Werkplan 2026-2027 (draft) nog niet ingevuld ([Naam], [Club]); benoeming uiterlijk 31-10-2026."),
    ("", ""),
    ("Controleset feiten (bron: sources.md in meta-dossier - verbindend voor alle deliverables)", ""),
    ("District", "110AN"),
    ("Conventietype", "Voorjaarsconventie (District Convention)"),
    ("Datum", "April 2027 (exacte datum t.b.v. roulatie/oproepingstermijnen nog vast te stellen)"),
    ("Locatie", "Te bepalen op basis van roulatieschema"),
    ("Governance", "Huishoudelijk Reglement MD 110 mei 2021"),
    ("Stemrechten", "Per club: 1 stem per 10 leden (min 1, max 5)"),
    ("Quorum", "Meeste artikelen: >50% van de stemgerechtigden"),
    ("Voorzitter", "District Governor 2026-2027"),
    ("Secretaris", "Cabinet Secretary 2026-2027"),
    ("", ""),
    ("Status-legenda", ""),
    ("Compliant", "Regel is verwerkt in de bestaande projectdeliverables; hertoetsing bij actualisaties."),
    ("Gap", "Verplichting bestaat maar is (nog) niet gedekt door besluit of deliverable; besluitvorming vereist."),
    ("Action Required", "Concrete actie met eigenaar en deadline vereist vóór de conventie."),
    ("", ""),
    ("Brontoegang", "Uitsluitend Meta-Dossier v1 (26-08-2026, 22 bronnen, 43.159 tokens). LCI Constitution & By-Laws en MD110 Statuten zijn alleen indirect (via Conventie Handboek, HR en controleset) in het dossier opgenomen."),
]
r = 3
for k, v in data:
    ck = ss.cell(row=r, column=1, value=k); cv = ss.cell(row=r, column=2, value=v)
    ck.alignment = wrap; cv.alignment = wrap; ck.border = border; cv.border = border
    ck.font = cell_font; cv.font = cell_font
    if v == "" and k != "":
        ck.font = Font(name="Calibri", bold=True, size=10, color="FFFFFF")
        ck.fill = PatternFill("solid", fgColor=BLUE); cv.fill = PatternFill("solid", fgColor=BLUE)
    if k in ("Compliant",): ck.fill = PatternFill("solid", fgColor=GREEN_F); ck.font = bold_font
    if k in ("Gap",): ck.fill = PatternFill("solid", fgColor=AMBER_F); ck.font = bold_font
    if k in ("Action Required",): ck.fill = PatternFill("solid", fgColor=RED_F); ck.font = bold_font
    if k == "Totaal": ck.font = bold_font; cv.font = bold_font
    r += 1

# ---------- Sheet 3: Bronnen ----------
bs = wb.create_sheet("Bronnen")
bs.column_dimensions["A"].width = 6; bs.column_dimensions["B"].width = 52; bs.column_dimensions["C"].width = 12
bs.merge_cells("A1:C1")
c = bs["A1"]; c.value = "BRONNEN UIT META-DOSSIER V1 (gebruikt voor deze toetsing)"
c.font = Font(name="Calibri", bold=True, size=12, color="FFFFFF"); c.fill = PatternFill("solid", fgColor=NAVY)
c.alignment = Alignment(horizontal="center", vertical="center"); bs.row_dimensions[1].height = 22
hdrs = ["#", "Bron", "Tokens"]
for i, h in enumerate(hdrs, 1):
    cell = bs.cell(row=2, column=i, value=h); cell.font = hdr_font; cell.fill = hdr_fill; cell.alignment = center; cell.border = border
SOURCES = [
 ("Handboek Lions Conventies vs 06 (29-07-2024)", "11.230"),
 ("MD 110 - Huishoudelijk Reglement mei 2021", "5.584"),
 ("Werkplan AN 2025-2026", "7.290"),
 ("2024-2025 MD110 Werkplan Gouverneursraad", "8.941"),
 ("Lions 110AN Werkplan 2024-2025 v1.0", "3.821"),
 ("agenda-110AN-2026-2027.json", "1.921"),
 ("werkplan AN 2026-2027 draft v1", "2.082"),
 ("District 110AN (1) - Club Health Assessment sep 2025", "496"),
 ("Verslag Najaarsconventie 17-10-2024 110AN", "292"),
 ("Districtbegroting 110 AN 25-26", "196"),
 ("Conventie Roulatieschema (GR 06-05-2022)", "42"),
 ("sources.md (bronnenoverzicht + controleset)", "717"),
]
r = 3
for i, (s, t) in enumerate(SOURCES, 1):
    bs.cell(row=r, column=1, value=i).alignment = center
    bs.cell(row=r, column=2, value=s).alignment = wrap
    bs.cell(row=r, column=3, value=t).alignment = center
    for col in range(1, 4):
        cell = bs.cell(row=r, column=col); cell.border = border
        if cell.font.size != 10 or True: cell.font = cell_font
        if i % 2 == 0: cell.fill = PatternFill("solid", fgColor=BAND)
    r += 1
r += 1
bs.merge_cells(f"A{r}:C{r}")
c = bs[f"A{r}"]
c.value = "Volledige bronnenlijst (22 items incl. samenvattingen): zie working/meta-dossier_v1.json"
c.font = Font(name="Calibri", italic=True, size=9, color=NAVY); c.alignment = wrap

wb.save(OUT)
print("OK", OUT, "| regels:", len(ROWS), "| Compliant:", comp, "| Gap:", gap, "| Action Required:", act)
