diff --git a/.gitignore b/.gitignore index be97e45..dab9540 100644 --- a/.gitignore +++ b/.gitignore @@ -6,8 +6,23 @@ __pycache__/ *.pyc *.pyo .env +.env.* *.db *.sqlite3 +*.sqlite3-journal .DS_Store media/ -.venv/ \ No newline at end of file +.venv/ + +# Claude Code / IDE +.claude/ +.vscode/ +.idea/ + +# Dev artifacts — test PDFs, backup files, accidental shell artifacts +test_*.pdf +test_*.json +nul + +# Local backup downloads — these should never be in git +backups/ diff --git a/CLAUDE.md b/CLAUDE.md index a4ba0f3..9b5f2cd 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -14,7 +14,7 @@ This is v5 — a fresh export from Flatlogic/AppWizzy, rebuilt from the v2 codeb ## Tech Stack - Django 5.2.7, Python 3.13, MySQL (production on Flatlogic Cloud Run) / SQLite (local dev) - Bootstrap 5.3.3 (CDN), Font Awesome 6.5.1 (CDN), Google Fonts (Inter + Poppins) -- xhtml2pdf for PDF generation (payslips, receipts) +- WeasyPrint for PDF generation (payroll report, payslips, receipts) — migrated from xhtml2pdf; browser-grade HTML/CSS rendering with flexbox, grid, @font-face, shadows, and proper CSS cascade - Gmail SMTP for automated document delivery - Hosted on Flatlogic/AppWizzy platform (Apache on Debian, e2-micro VM) @@ -25,12 +25,24 @@ core/ — Single main app: ALL business logic, models, views, forms, context_processors.py — Injects deployment_timestamp (cache-busting), Flatlogic branding vars forms.py — AttendanceLogForm, PayrollAdjustmentForm, ExpenseReceiptForm + formset models.py — All 10 database models - utils.py — render_to_pdf() helper (lazy xhtml2pdf import) - views.py — All 28 functions (~2635 lines, includes helpers) + utils.py — render_to_pdf() helper (lazy WeasyPrint import + Windows GTK3 DLL registration) + views.py — All view functions (~52 functions, ~3,800 lines) — dashboard, attendance, payroll, reports, worker/team/project CRUD + forms.py — All form classes + validators (WorkerForm, TeamForm, ProjectForm, AttendanceLogForm, PayrollAdjustmentForm, ExpenseReceiptForm, WorkerCertificate/WarningFormSet, 5MB file validator) + admin.py — Django admin registrations for all core models + WorkerCertificate/Warning inlines on Worker + templatetags/ — format_tags.py (money filter for ZAR formatting) management/commands/ — setup_groups, setup_test_data, import_production_data - templates/ — base.html + 7 page templates + 2 email + 2 PDF + login + templates/ + base.html — App shell (topbar + mobile menu + bottom tab bar) + core/ — Page templates: index, attendance_log, work_history, payroll_dashboard, + report, create_receipt, payslip, login, _report_config_modal (partial) + core/workers/ — 4 templates: list, detail, edit, batch_report + core/teams/ — 4 templates: list, detail, edit, batch_report + core/projects/— 4 templates: list, detail, edit, batch_report + core/pdf/ — 4 PDF templates: report_pdf, payslip_pdf, receipt_pdf, workers_report_pdf + core/email/ — 2 HTML email templates + admin/ — base_site.html override (adds admin CSS tweaks, e.g. taller M2M pickers) ai/ — Flatlogic AI proxy client (not used in app logic) -static/css/ — custom.css (CSS variables, component styles) +static/css/ — custom.css (CSS variables, component styles, tooltip overrides) staticfiles/ — Collected static assets (Bootstrap, admin) ``` @@ -44,6 +56,8 @@ staticfiles/ — Collected static assets (Bootstrap, admin) - **PayrollAdjustment** — bonuses, deductions, overtime, loans; linked to project (FK, optional), worker, and optionally to a Loan or WorkLog - **Loan** — worker loans AND advances with principal, remaining_balance, `loan_type` ('loan' or 'advance') - **ExpenseReceipt / ExpenseLineItem** — business expense records with VAT handling +- **WorkerCertificate** — per-worker certifications (Skills, PDP, First Aid, Medical, Work at Height) with `valid_until` expiry and optional document upload. Unique per (worker, cert_type). Has `is_expired` and `expires_soon` (≤30 days) properties. +- **WorkerWarning** — disciplinary records per worker with severity (verbal/written/final), reason, optional document. Ordered -date. ## Key Business Rules - All business logic lives in the `core/` app — do not create additional Django apps @@ -109,6 +123,10 @@ python manage.py check # System check - Pending Payments Table: Shows overdue badges (red) for workers with unpaid work from completed pay periods, and loan badges (yellow) for workers with active loans/advances. Filter bar has: team dropdown, "Overdue only" checkbox, and loan dropdown (All Workers / With loans only / Without loans). Overdue detection uses `get_pay_period()` cutoff logic. - Quick Adjust Button: Each pending payments row has an "Adjust" button (slider icon) that opens the Add Adjustment modal with that worker pre-checked and their most recent project pre-selected. The header "Add Adjustment" button resets the modal to a clean state. Uses `_quickAdjustOpen` flag to distinguish between the two open paths. - Worker Lookup Modal: Clicking any worker name on the payroll dashboard (or using the "Worker Lookup" button) opens a modal with a comprehensive report card — amount payable, outstanding loans, paid this month/year, loans this year, recent activity (last payslip, loan, repayment, advance), active loans table, current project + days on project, PPE sizing, drivers license, and notes. Uses `worker_lookup_ajax` AJAX endpoint. Worker dropdown in modal allows switching workers without closing. +- Team & Project Management UIs: Friendlier alternatives to `/admin/core/team/` and `/admin/core/project/`. Reachable via the "Resources" dropdown in the topbar (admin only). **Team pages**: `/teams/` (list + search/filter), `/teams//` (detail with Profile/Pay Schedule/Workers/History tabs — Pay Schedule tab uses the existing `get_pay_period()` helper to show current + next 2 periods), `/teams//edit/` (single-page form for name, supervisor, pay schedule, and workers M2M). **Project pages**: `/projects/`, `/projects//` (tabs: Profile/Supervisors/Teams/Workers/History), `/projects//edit/` (form for name, description, dates, supervisors M2M). Uses `TeamForm` and `ProjectForm` from `core/forms.py` (both simple ModelForms, no inline formsets). Batch reports at `/teams/report/` and `/projects/report/` with CSV exports; PDF exports deferred as a follow-up. Dashboard "Manage Resources" card now has "Manage All Workers/Projects/Teams" footer links on each tab. Django admin remains fully functional as a fallback. +- Worker Management UI: A friendlier alternative to `/admin/core/worker/`. Reachable via the "Resources" topbar dropdown → Workers (admin-only). Pages: `/workers/` (list with search + status filter), `/workers//` (detail with Profile/Certifications/Warnings/History tabs), `/workers//edit/` or `/workers/new/` (single-page form with sections for Personal & Pay, PPE, Documents, Driver's License, plus inline formsets for certifications and warnings). Uses `WorkerForm`, `WorkerCertificateFormSet`, `WorkerWarningFormSet` from `core/forms.py`. The "+ Add Certification" / "+ Add Warning" buttons clone a `