#!/usr/bin/env python3
"""PGS15 Audit Rapport Template v2.0 — DOCX Generator"""
from docx import Document
from docx.shared import Pt, Cm, RGBColor
from docx.enum.text import WD_ALIGN_PARAGRAPH
from docx.enum.table import WD_TABLE_ALIGNMENT
from docx.oxml.ns import nsdecls
from docx.oxml import parse_xml

doc = Document()

style = doc.styles['Normal']
style.font.name = 'Calibri'
style.font.size = Pt(11)
style.paragraph_format.space_after = Pt(6)
style.paragraph_format.line_spacing = 1.15

for level in range(1, 4):
    hs = doc.styles[f'Heading {level}']
    hs.font.name = 'Calibri'
    hs.font.color.rgb = RGBColor(0, 51, 102)
    hs.font.size = Pt([16, 13, 11][level-1])
    hs.font.bold = True
    hs.paragraph_format.space_before = Pt([18, 12, 8][level-1])

for section in doc.sections:
    section.top_margin = Cm(2.5)
    section.bottom_margin = Cm(2.5)
    section.left_margin = Cm(2.5)
    section.right_margin = Cm(2.5)

def add_para(text, bold=False, italic=False):
    p = doc.add_paragraph()
    run = p.add_run(text)
    run.font.size = Pt(11)
    run.font.bold = bold
    run.font.italic = italic
    return p

def add_table(headers, rows, col_widths=None):
    table = doc.add_table(rows=1+len(rows), cols=len(headers))
    table.style = 'Table Grid'
    table.alignment = WD_TABLE_ALIGNMENT.CENTER
    for i, h in enumerate(headers):
        cell = table.rows[0].cells[i]
        cell.text = h
        shading = parse_xml(f'<w:shd {nsdecls("w")} w:fill="003366"/>')
        cell.paragraphs[0].runs[0].font.color.rgb = RGBColor(255, 255, 255)
        cell.paragraphs[0].runs[0].font.bold = True
        cell.paragraphs[0].runs[0].font.size = Pt(10)
        cell._tc.get_or_add_tcPr().append(shading)
    for r_idx, row in enumerate(rows):
        for c_idx, val in enumerate(row):
            cell = table.rows[r_idx+1].cells[c_idx]
            cell.text = str(val)
            for p in cell.paragraphs:
                for run in p.runs:
                    run.font.size = Pt(10)
            if r_idx % 2 == 1:
                shading = parse_xml(f'<w:shd {nsdecls("w")} w:fill="F2F2F2"/>')
                cell._tc.get_or_add_tcPr().append(shading)
    if col_widths:
        for row in table.rows:
            for i, w in enumerate(col_widths):
                row.cells[i].width = Cm(w)
    return table

def add_field(label, width=12):
    p = doc.add_paragraph()
    run = p.add_run(f'{label}: ')
    run.font.bold = True
    run.font.size = Pt(11)
    run = p.add_run('_' * width)
    run.font.size = Pt(11)
    return p

# ===== TITLE PAGE =====
for _ in range(4):
    doc.add_paragraph()
p = doc.add_paragraph()
p.alignment = WD_ALIGN_PARAGRAPH.CENTER
run = p.add_run('PGS-15 Auditrapport')
run.font.size = Pt(28)
run.font.bold = True
run.font.color.rgb = RGBColor(0, 51, 102)
p = doc.add_paragraph()
p.alignment = WD_ALIGN_PARAGRAPH.CENTER
run = p.add_run('Opslag van Verpakte Gevaarlijke Stoffen')
run.font.size = Pt(18)
run.font.color.rgb = RGBColor(0, 51, 102)
doc.add_paragraph()
p = doc.add_paragraph()
p.alignment = WD_ALIGN_PARAGRAPH.CENTER
run = p.add_run('Versie 2.0 — April 2026\nBron: PGS 15:2025 versie 1.0 (januari 2025)')
run.font.size = Pt(12)
for _ in range(6):
    doc.add_paragraph()
p = doc.add_paragraph()
p.alignment = WD_ALIGN_PARAGRAPH.CENTER
run = p.add_run('Auditrapport — Vertrouwelijk')
run.font.size = Pt(14)
run.font.bold = True
run.font.color.rgb = RGBColor(180, 0, 0)
doc.add_page_break()

# ===== 1. ALGEMENE GEGEVENS =====
doc.add_heading('1. Algemene Gegevens', level=1)

add_field('Bedrijfsnaam')
add_field('Locatie/adres')
add_field('Auditdatum')
add_field('Auditor(s)')
add_field('Opdrachtgever')
add_field('Referentienummer audit')
add_field('Versie rapport')

doc.add_heading('1.1 Contactpersonen', level=2)
add_table(
    ['Functie', 'Naam', 'Telefoon', 'E-mail'],
    [
        ['Contactpersoon bedrijf', '', '', ''],
        ['Veiligheidsadviseur', '', '', ''],
        ['BG/ARBO-deskundige', '', '', ''],
    ],
    [4, 4, 4, 4]
)
doc.add_paragraph()

doc.add_heading('1.2 Scope van de audit', level=2)
add_para('Omschrijving van de geauditeerde activiteiten en opslagvoorzieningen:')
p = doc.add_paragraph('_' * 80)
doc.add_paragraph()

doc.add_heading('1.3 Documenten ontvangen', level=2)
add_table(
    ['Document', 'Datum ontvangen', 'Versie/Status'],
    [
        ['Omgevingsvergunning', '', ''],
        ['Stoffenlijst / M116-informatie', '', ''],
        ['Plattegrond NEN 1414-1', '', ''],
        ['UPD brandbeveiliging', '', ''],
        ['Intern noodplan (M113)', '', ''],
        ['Inspectierapporten VBB', '', ''],
        ['Certificaten vakbekwaamheid', '', ''],
        ['SDS kritische stoffen', '', ''],
        ['Eerdere auditrapporten', '', ''],
        ['M118 Wijze beschikbaarstelling', '', ''],
    ],
    [6, 3, 3]
)
doc.add_paragraph()
doc.add_page_break()

# ===== 2. INVENTARISATIE =====
doc.add_heading('2. Inventarisatie Gevaarlijke Stoffen', level=1)

doc.add_heading('2.1 Overzicht opgeslagen stoffen', level=2)
add_table(
    ['Stofnaam', 'UN-nr', 'ADR-klasse', 'VG', 'Hoeveelheid', 'Opslaglocatie', 'Veiligheidsniveau'],
    [
        ['', '', '', '', '', '', ''],
        ['', '', '', '', '', '', ''],
        ['', '', '', '', '', '', ''],
        ['', '', '', '', '', '', ''],
        ['', '', '', '', '', '', ''],
    ],
    [3.5, 1.5, 1.5, 0.8, 1.5, 2.5, 2.5]
)
doc.add_paragraph()

doc.add_heading('2.2 Ondergrenzenberekening', level=2)
add_table(
    ['ADR-klasse', 'VG', 'Ondergrens (kg/l)', 'Opgeslagen (kg/l)', 'qx/Qx', 'Totaal Σ'],
    [
        ['', '', '', '', '', ''],
        ['', '', '', '', '', ''],
        ['', '', '', '', '', ''],
    ],
    [2.5, 1, 2, 2, 1.5, 1.5]
)
doc.add_paragraph()
add_para('Σ qx/Qx = _____ (≥1 = PGS 15 van toepassing)')

doc.add_heading('2.3 Veiligheidsniveaus (Tabel 6, M3)', level=2)
add_table(
    ['Opslagvoorziening', 'Stofklasse', 'Hoeveelheid', 'Veiligheidsniveau', 'Vereiste WBDBO', 'Type opslag'],
    [
        ['', '', '', 'Basis / A / B / C', '', 'Binnen/Buiten/Kast'],
        ['', '', '', '', '', ''],
        ['', '', '', '', '', ''],
    ],
    [3.5, 2, 2, 2.5, 2, 2]
)
doc.add_paragraph()
doc.add_page_break()

# ===== 3. BEVINDINGEN =====
doc.add_heading('3. Bevindingen', level=1)

doc.add_heading('3.1 Samenvatting', level=2)
add_table(
    ['Sectie', 'Aantal conform', 'Aantal afwijking', 'Aantal kritiek', 'N.v.t.'],
    [
        ['1. Werkingssfeer', '', '', '', ''],
        ['2. Ondergrenzen', '', '', '', ''],
        ['3. Werkvoorraad', '', '', '', ''],
        ['4. Opslagvoorzieningen & Veiligheidsniveaus', '', '', '', ''],
        ['5. Zonnepanelen', '', '', '', ''],
        ['6. Productopvang', '', '', '', ''],
        ['7. Compartimentering', '', '', '', ''],
        ['8. Vakbekwaamheid', '', '', '', ''],
        ['9. Informatievoorziening (M116/M117)', '', '', '', ''],
        ['10. Noodplan', '', '', '', ''],
        ['11. Veiligheidssignalering', '', '', '', ''],
        ['12. Brandbeveiliging & VBB', '', '', '', ''],
        ['13. Gasflessen', '', '', '', ''],
        ['14. Verdiepingsopslag', '', '', '', ''],
        ['15. Tijdelijke opslag', '', '', '', ''],
        ['16. Specifieke stofgroepen', '', '', '', ''],
        ['17. Onderhoud & keuring', '', '', '', ''],
        ['TOTAAL', '', '', '', ''],
    ],
    [5, 2, 2, 2, 1]
)
doc.add_paragraph()

doc.add_heading('3.2 Detail bevindingen', level=2)
add_para('Per bevinding: Situatie → Toetsing (M-nummer) → Afwijking → Risico → Classificatie → Aanbeveling')
doc.add_paragraph()

# Repeat block for multiple findings
for i in range(1, 11):
    p = doc.add_paragraph()
    run = p.add_run(f'Bevinding {i}')
    run.font.bold = True
    run.font.size = Pt(11)
    add_table(
        ['Veld', 'Inhoud'],
        [
            ['Sectie/Checklist-nr', ''],
            ['Situatie (aangetroffen)', ''],
            ['Toetsing (PGS 15:2025 maatregel)', ''],
            ['Afwijking', ''],
            ['Risico', ''],
            ['Classificatie', 'CONFORM / AFWIJKING / KRITIEK / N.v.t.'],
            ['Aanbeveling', ''],
            ['Termijn herstel', ''],
            ['Verantwoordelijke', ''],
            ['Fotoverwijzing', ''],
        ],
        [4, 11]
    )
    doc.add_paragraph()

doc.add_page_break()

# ===== 4. FOTOGRAFISCH OVERZICHT =====
doc.add_heading('4. Fotografisch Overzicht', level=1)
add_table(
    ['Nr.', 'Omschrijving', 'Locatie', 'Classificatie', 'Foto bijgevoegd'],
    [
        ['1', '', '', '', 'Ja / Nee'],
        ['2', '', '', '', ''],
        ['3', '', '', '', ''],
        ['4', '', '', '', ''],
        ['5', '', '', '', ''],
        ['6', '', '', '', ''],
        ['7', '', '', '', ''],
        ['8', '', '', '', ''],
        ['9', '', '', '', ''],
        ['10', '', '', '', ''],
    ],
    [1, 5, 3, 2.5, 2]
)
doc.add_paragraph()
doc.add_page_break()

# ===== 5. CONCLUSIE =====
doc.add_heading('5. Conclusie & Aanbevelingen', level=1)

doc.add_heading('5.1 Algemeen oordeel', level=2)
add_para('Het algemene oordeel over de naleving van PGS 15:2025:')
p = doc.add_paragraph('_' * 80)
doc.add_paragraph()
add_para('□ Conform — De opslag voldoet aan PGS 15:2025')
add_para('□ Gedeeltelijk conform — Met opmerkingen/afwijkingen (zie §3)')
add_para('□ Niet conform — Kritieke afwijkingen die direct herstel vereisen')

doc.add_heading('5.2 Prioriteitenlijst actiepunten', level=2)
add_table(
    ['Prioriteit', 'Actiepunt', 'Maatregel PGS 15:2025', 'Termijn', 'Verantwoordelijke'],
    [
        ['1 (Kritiek)', '', '', '', ''],
        ['2 (Kritiek)', '', '', '', ''],
        ['3 (Afwijking)', '', '', '', ''],
        ['4 (Afwijking)', '', '', '', ''],
        ['5 (Aanbeveling)', '', '', '', ''],
    ],
    [2, 5, 3, 2, 2.5]
)
doc.add_paragraph()

doc.add_heading('5.3 Follow-up audit', level=2)
add_field('Geplande datum follow-up audit')
doc.add_paragraph()

doc.add_page_break()

# ===== 6. HANDTEKENINGEN =====
doc.add_heading('6. Handtekeningen', level=1)
add_table(
    ['Functie', 'Naam', 'Handtekening', 'Datum'],
    [
        ['Auditor', '', '', ''],
        ['Hoofd auditor (indien van toepassing)', '', '', ''],
        ['Contactpersoon bedrijf', '', '', ''],
    ],
    [4, 4, 4, 2.5]
)
doc.add_paragraph()

# ===== COLOFON =====
p = doc.add_paragraph()
run = p.add_run('Colofon')
run.font.size = Pt(10)
run.font.bold = True
add_para('Bron: PGS 15:2025 versie 1.0 (januari 2025), Publicatiereeks Gevaarlijke Stoffen.')
add_para('Vastgesteld door: Bestuurlijk Omgevingsberaar (BOb), 16 januari 2025.')
add_para('Dit rapport is bedoeld als documentatie van een PGS-15 audit en vervangt niet de originele PGS 15:2025-publicatie.', italic=True)
add_para('Versie 2.0 | Template samengesteld april 2026.', italic=True)

output_path = '/root/projects/jg/2026-pgs15-audit-toolkit/deliverables/docx/PGS15_Audit_Rapport_Template_v2.0.docx'
doc.save(output_path)
print(f"DOCX saved to: {output_path}")
