Developer Guide
Technical reference for contributors and advanced users.
1. Stack Overview
Area | Tech |
---|---|
Platform | Wails v3 (Go + WebView) |
Backend | Go 1.22+, GORM (SQLite) |
Frontend | React + TypeScript + Vite |
go-pdf/fpdf |
2. Repository Layout
internal/ Go models & services
frontend/ React app (Vite)
build/ Packaging assets & config
bin/ Output binaries/installers
docs/ Documentation site (MkDocs)
3. Models (GORM)
Relationships:
Company 1---* Client 1---* Invoice 1---* InvoiceItem
4. Services
File | Responsibility |
---|---|
services/database.go |
DB open/migrate (check actual implementation) |
services/pdf.go |
Invoice -> PDF rendering |
services/config.go |
Load configuration (language etc.) |
5. PDF Generation Flow
ExportInvoicePDF(dbPath, invoiceID, outPath, lang)
-> Open DB
-> Query invoice + relations
-> Render header/company/client
-> Render items & totals
-> Localized labels via i18n
6. Internationalization
The app uses simple key-based JSON locale bundles for both the UI and PDF generation.
Frontend (UI Strings)
Loaded at runtime from frontend/public/locales/<code>.json
via dynamic fetch
in frontend/src/i18n/index.tsx
.
Key lookup uses dot notation (e.g. common.save
, messages.noClientsYet
). Missing keys fall back to the path string itself so you can easily spot gaps.
Supported locale codes are declared in SUPPORTED_LOCALES
inside the i18n provider. The selected code (2‑letters) is persisted through the backend ConfigService
so that PDFs can reuse the same language.
Backend (PDF Labels)
PDF label translations live in embedded JSON under internal/i18n/locales/<code>.json
and are loaded at compile time using go:embed
. They currently only need the pdf
section (subset of labels used in the PDF layout).
Translator usage:
tr := i18n.T(lang)
tr("pdf.invoice") // -> localized string or key fallback
Adding a New Language
UI + PDF need coordinated additions.
- Frontend: copy
frontend/public/locales/en.json
→<code>.json
and translate values. - Backend: copy
internal/i18n/locales/en.json
→<code>.json
and translate values. - Update
SUPPORTED_LOCALES
andLOCALE_LABELS
infrontend/src/i18n/index.tsx
. - Rebuild (
wails3 dev
or build tasks). The UI will fetch the new JSON; backend will have the embedded file. - Switch language in the UI (persists to config) and generate a PDF to verify.
Keeping Frontend & Backend Locales in Sync
Because we embed backend JSON at compile time and serve frontend JSON at runtime, duplication exists.
Fallback Strategy
- Frontend: missing key → key path text.
- Backend: missing in chosen lang → English → key.
Keep keys stable; renames should update both JSON sets. Avoid embedding variable data inside values—string interpolation is not yet implemented.
7. Database
- SQLite single file
- Automatic schema creation via GORM
AutoMigrate
(assumed confirm in code) - Migration versioning not yet implemented
8. Frontend Architecture
- React functional components
- Context providers for selected company, database path, toasts
- Minimal styling
9. Dev Workflow
Install wails3 cli:
go install github.com/wailsapp/wails/v3/cmd/wails3@latest
Dev run with hot realoads:
wails3 dev
Build debug binary:
wails3 task build
Build production binary:
wails3 task build PRODUCTION=true
Create installed and packaged versions:
wails3 task package
10. Contributing
There's not official docs for this. Contributions are very welcomed and really appreaciated. Just open an Issue or directly a PR for small changes.