14 Commits
Author SHA1 Message Date
jhoogie a996c767f0 Merge pull request 'bugfix' (#19) from update-1.0.13 into main
Reviewed-on: #19
2026-10-01 17:02:12 +02:00
Jordy Hoogeveen 4181ac3f0f bugfix 2026-10-01 16:57:16 +02:00
jhoogie 65233fb5b4 Merge pull request 'bugfix' (#18) from update-1.0.12 into main
Reviewed-on: #18
2026-09-18 15:25:08 +02:00
jhoogie ec63906cb2 Merge pull request 'cve fixes' (#17) from update-1.0.11 into main
Reviewed-on: #17
2026-09-18 15:03:54 +02:00
jhoogie 2d7e67e315 Merge pull request 'bugfix dashboard' (#16) from update-1.0.10 into main
Reviewed-on: #16
2026-09-17 17:28:11 +02:00
jhoogie 539b42dde7 Merge pull request 'bugfix dashboard' (#15) from update-1.0.9 into main
Reviewed-on: #15
2026-09-17 17:07:24 +02:00
jhoogie 73ce30c5b0 Merge pull request 'Bugfixes' (#14) from update-1.0.8 into main
Reviewed-on: http://10.0.3.108:3000/Vibe/VibeFinance/pulls/14
2026-09-15 14:06:45 +02:00
jhoogie 4915a090a3 Merge pull request 'dashboard tooltip update' (#13) from update-1.0.7 into main
Reviewed-on: http://10.0.3.108:3000/Vibe/VibeFinance/pulls/13
2026-09-11 17:13:03 +02:00
jhoogie 6d1b114b78 Merge pull request 'dashboard update' (#12) from update-1.0.6 into main
Reviewed-on: http://10.0.3.108:3000/Vibe/VibeFinance/pulls/12
2026-09-11 15:22:34 +02:00
jhoogie a9b6203dec Merge pull request 'bugfix' (#11) from update-1.0.5 into main
Reviewed-on: http://10.0.3.108:3000/Vibe/VibeFinance/pulls/11
2026-09-11 14:10:57 +02:00
jhoogie 36f49b216f Merge pull request 'bugfix' (#10) from update-1.0.5 into main
Reviewed-on: http://10.0.3.108:3000/Vibe/VibeFinance/pulls/10
2026-09-10 21:38:12 +02:00
jhoogie 796245fefe Merge pull request 'bugfix' (#9) from update-1.0.4 into main
Reviewed-on: http://10.0.3.108:3000/Vibe/VibeFinance/pulls/9
2026-09-10 21:28:05 +02:00
jhoogie 0bbb166b32 Merge pull request 'bugfix' (#8) from update-1.0.3 into main
Reviewed-on: http://10.0.3.108:3000/Vibe/VibeFinance/pulls/8
2026-09-10 16:42:38 +02:00
jhoogie fe6b94aa7f Merge pull request 'bugfix' (#7) from update-1.0.2 into main
Reviewed-on: http://10.0.3.108:3000/Vibe/VibeFinance/pulls/7
2026-09-10 15:43:57 +02:00
9 changed files with 57 additions and 11 deletions
+26
View File
@@ -2,6 +2,32 @@
## [Niet vrijgegeven] ## [Niet vrijgegeven]
### Opgelost
- **De kaart "Rendement Eigen Vermogen" op Voortgang stond leeg.** Bedrag en
percentage waren sinds de eerste commit hardcoded als `—` in de JSX; er zat
geen berekening achter en `evRows` werd niet eens uit de context gehaald. Het
oogde als een datafout — lege database, mislukte API-call — maar de kaart was
nooit afgebouwd. Hij rekent nu met dezelfde formule als het blok "Rendement"
op Eigen vermogen: huidige waarde min geïnvesteerde fiat, gedeeld door die
inleg. Groen bij winst, rood bij verlies, en `—` zolang er niets is ingelegd,
zodat er niet door nul wordt gedeeld
- Beide kaarten tonen daarmee hetzelfde totaal. Dat is bewust: twee plekken die
"rendement" noemen horen niet twee verschillende getallen te geven
### Gewijzigd
- De achtergrond achter een popup is lichter: `rgba(0,0,0,0.75)` naar `0.45` in
de gedeelde `Overlay`. Op 0.75 was van het scherm eronder vrijwel niets meer
te zien, terwijl je bij het invullen van een modal juist wilt kunnen nakijken
waar je vandaan kwam. Gedimd genoeg om de modal de aandacht te laten houden
- De popups van NavBar, Instellingen en Gebruikersbeheer gebruiken de gedeelde
`Overlay` niet maar hadden hun eigen backdrop op `rgba(0,0,0,0.55)` met
`backdropFilter: blur(4px)`. Alle drie staan nu op dezelfde 0.45, en de blur
is eruit: die maakte de achtergrond onscherp in plaats van zichtbaar, en
zonder dat weg te halen bleven ze alsnog afwijken van de rest. Vier
popup-backdrops, één waarde
## [1.0.12] - 2026-09-18
### Beveiliging ### Beveiliging
- **De postgres-container draait niet meer als root.** Beide compose-bestanden - **De postgres-container draait niet meer als root.** Beide compose-bestanden
starten hem met `user: "postgres"`. Alle 46 bevindingen op `postgres:18-alpine` starten hem met `user: "postgres"`. Alle 46 bevindingen op `postgres:18-alpine`
+9 -2
View File
@@ -10,7 +10,7 @@ Eigen vermogen · Schulden · Voortgang · Gebruikersbeheer
![Node.js](https://img.shields.io/badge/Node.js_22-339933?style=flat&logo=node.js&logoColor=white) ![Node.js](https://img.shields.io/badge/Node.js_22-339933?style=flat&logo=node.js&logoColor=white)
![PostgreSQL](https://img.shields.io/badge/PostgreSQL_18-4169E1?style=flat&logo=postgresql&logoColor=white) ![PostgreSQL](https://img.shields.io/badge/PostgreSQL_18-4169E1?style=flat&logo=postgresql&logoColor=white)
![Docker](https://img.shields.io/badge/Docker_Compose-2496ED?style=flat&logo=docker&logoColor=white) ![Docker](https://img.shields.io/badge/Docker_Compose-2496ED?style=flat&logo=docker&logoColor=white)
![Version](https://img.shields.io/badge/versie-1.0.11-8b5cf6?style=flat) ![Version](https://img.shields.io/badge/versie-1.0.12-8b5cf6?style=flat)
![Built with Claude](https://img.shields.io/badge/Gebouwd_met-Claude.ai-8b5cf6?style=flat&logo=anthropic&logoColor=white) ![Built with Claude](https://img.shields.io/badge/Gebouwd_met-Claude.ai-8b5cf6?style=flat&logo=anthropic&logoColor=white)
<img src="docs/screenshot-dashboard.png" alt="VibeFinance dashboard" width="820"> <img src="docs/screenshot-dashboard.png" alt="VibeFinance dashboard" width="820">
@@ -190,7 +190,7 @@ build — anders zou de release met een placeholder als notes online komen.
| 📊 **Dashboard** | KPI's over inleg, vermogen, winst en ROI, de voortgang naar je doel, en de grafiek met vermogen tegen inleg | | 📊 **Dashboard** | KPI's over inleg, vermogen, winst en ROI, de voortgang naar je doel, en de grafiek met vermogen tegen inleg |
| 💰 **Eigen vermogen** | Vermogensposten per categorie beheren + geïnvesteerde fiat historiek | | 💰 **Eigen vermogen** | Vermogensposten per categorie beheren + geïnvesteerde fiat historiek |
| 📉 **Schuld** | Schulden bijhouden per blok met afbetalingsoverzicht | | 📉 **Schuld** | Schulden bijhouden per blok met afbetalingsoverzicht |
| 📈 **Voortgang Schuld & EV** | Grafieken en trends van EV en schuld over tijd (apart bij te houden) | | 📈 **Voortgang Schuld & EV** | KPI-kaarten met de verdeling van schuld en EV, het rendement en de netto waarde, plus grafieken en trends van EV en schuld over tijd (apart bij te houden) |
| 👥 **Gebruikers** | Accounts aanmaken, bewerken en beheren (Admin-rol vereist) | | 👥 **Gebruikers** | Accounts aanmaken, bewerken en beheren (Admin-rol vereist) |
| ⚙️ **Instellingen** | Kleurthema, licht/donker, backup downloaden, backup terugzetten en export naar HTML | | ⚙️ **Instellingen** | Kleurthema, licht/donker, backup downloaden, backup terugzetten en export naar HTML |
@@ -202,6 +202,13 @@ inleglijn is per definitie gelijk aan de KPI "Totaal geïnvesteerde fiat" — be
rekenen het oudste voortgangsmoment als startinleg en tellen daar de stortingen rekenen het oudste voortgangsmoment als startinleg en tellen daar de stortingen
per rij bij op. per rij bij op.
Rendement betekent overal hetzelfde: huidige waarde min geïnvesteerde fiat,
gedeeld door die inleg. De kaart "Rendement Eigen Vermogen" op Voortgang en het
blok "Rendement" op Eigen vermogen tonen daarom hetzelfde totaal — dat laatste
splitst het alleen nog uit per categorie. Zolang er geen inleg is vastgelegd
staat er `—` in plaats van een percentage, want zonder noemer is er geen
rendement te berekenen.
De x-as noemt maanden (`sep '26`), niet losse datums: de grafiek rekent uit De x-as noemt maanden (`sep '26`), niet losse datums: de grafiek rekent uit
hoeveel labels er naast elkaar passen en toont er zoveel, terugtellend vanaf het hoeveel labels er naast elkaar passen en toont er zoveel, terugtellend vanaf het
laatste punt zodat dat er altijd bij staat. Bij een langere reeks dunt hij laatste punt zodat dat er altijd bij staat. Bij een langere reeks dunt hij
+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "vibefinance-frontend", "name": "vibefinance-frontend",
"version": "1.0.12-dev", "version": "1.0.13-dev",
"private": true, "private": true,
"type": "module", "type": "module",
"scripts": { "scripts": {
+1 -1
View File
@@ -172,7 +172,7 @@ export default function GebruikersBeheer({ onClose }) {
onClick={onClose} onClick={onClose}
style={{ style={{
position: "fixed", inset: 0, zIndex: 400, position: "fixed", inset: 0, zIndex: 400,
background: "rgba(0,0,0,0.55)", backdropFilter: "blur(4px)", background: "rgba(0,0,0,0.45)",
display: "flex", alignItems: "center", justifyContent: "center", display: "flex", alignItems: "center", justifyContent: "center",
}} }}
> >
@@ -49,7 +49,7 @@ export default function InstellingenModal({ onClose }) {
onClick={onClose} onClick={onClose}
style={{ style={{
position: "fixed", inset: 0, zIndex: 400, position: "fixed", inset: 0, zIndex: 400,
background: "rgba(0,0,0,0.55)", backdropFilter: "blur(4px)", background: "rgba(0,0,0,0.45)",
display: "flex", alignItems: "center", justifyContent: "center", display: "flex", alignItems: "center", justifyContent: "center",
}} }}
> >
+1 -1
View File
@@ -116,7 +116,7 @@ function OverPopup({ onClose, nieuweVersie, T }) {
{/* Overlay */} {/* Overlay */}
<div onClick={onClose} style={{ <div onClick={onClose} style={{
position: "fixed", inset: 0, zIndex: 490, position: "fixed", inset: 0, zIndex: 490,
background: "rgba(0,0,0,0.55)", backdropFilter: "blur(4px)", background: "rgba(0,0,0,0.45)",
display: "flex", alignItems: "center", justifyContent: "center", display: "flex", alignItems: "center", justifyContent: "center",
}}> }}>
{/* Modal */} {/* Modal */}
+1 -1
View File
@@ -319,7 +319,7 @@ export function Overlay({ children, onClose, zIndex = 400 }) {
onClick={(e) => { if (e.target === e.currentTarget) onClose(); }} onClick={(e) => { if (e.target === e.currentTarget) onClose(); }}
style={{ style={{
position: "fixed", inset: 0, position: "fixed", inset: 0,
background: "rgba(0,0,0,0.75)", background: "rgba(0,0,0,0.45)",
zIndex, zIndex,
}} }}
> >
+16 -3
View File
@@ -237,13 +237,22 @@ export default function VoortgangTab() {
const [showAdd, setShowAdd] = useState(false); const [showAdd, setShowAdd] = useState(false);
const [editRow, setEditRow] = useState(null); const [editRow, setEditRow] = useState(null);
const { const {
totEV, totSchuld, catTotals, schuldBlokken, schuldHistory, totEV, totSchuld, cats, catTotals, evRows, schuldBlokken, schuldHistory,
evVoortgangHistory, setEvVoortgangHistory, evVoortgangHistory, setEvVoortgangHistory,
data, setData, schuld, locked, darkMode, T, data, setData, schuld, locked, darkMode, T,
} = useApp(); } = useApp();
const nettoWaarde = totEV - totSchuld; const nettoWaarde = totEV - totSchuld;
// Rendement t.o.v. de geinvesteerde fiat, zelfde formule als op de EV-tab.
const totGeinvesteerd = cats.reduce(
(a, c) => a + evRows.reduce((b, r) => b + (r[c.id] || 0), 0),
0
);
const rendementBedrag = totGeinvesteerd > 0 ? totEV - totGeinvesteerd : null;
const rendementPct = totGeinvesteerd > 0 ? (rendementBedrag / totGeinvesteerd) * 100 : null;
const rendementKleur = rendementBedrag === null ? T.muted : rendementBedrag >= 0 ? GREEN : RED;
const schuldCatsDash = schuldBlokken.map((b) => ({ const schuldCatsDash = schuldBlokken.map((b) => ({
naam: b.naam, color: b.color, naam: b.naam, color: b.color,
subtot: b.items.reduce((a, i) => a + (i.waarde || 0), 0), subtot: b.items.reduce((a, i) => a + (i.waarde || 0), 0),
@@ -377,11 +386,15 @@ export default function VoortgangTab() {
<div style={{ fontWeight: 700, fontSize: 12, letterSpacing: "0.08em", textTransform: "uppercase", color: "#f59e0b", marginBottom: 12 }}>Rendement Eigen Vermogen</div> <div style={{ fontWeight: 700, fontSize: 12, letterSpacing: "0.08em", textTransform: "uppercase", color: "#f59e0b", marginBottom: 12 }}>Rendement Eigen Vermogen</div>
<div style={{ padding: "10px 0", borderBottom: `1px solid ${T.border}` }}> <div style={{ padding: "10px 0", borderBottom: `1px solid ${T.border}` }}>
<div style={{ fontSize: 11, color: T.muted, marginBottom: 4 }}>Bedrag</div> <div style={{ fontSize: 11, color: T.muted, marginBottom: 4 }}>Bedrag</div>
<div style={{ fontSize: 15, fontWeight: 700, color: T.muted }}>—</div> <div style={{ fontSize: 15, fontWeight: 700, color: rendementKleur }}>
{rendementBedrag === null ? "—" : fmt(rendementBedrag)}
</div>
</div> </div>
<div style={{ padding: "10px 0" }}> <div style={{ padding: "10px 0" }}>
<div style={{ fontSize: 11, color: T.muted, marginBottom: 4 }}>Percentage</div> <div style={{ fontSize: 11, color: T.muted, marginBottom: 4 }}>Percentage</div>
<div style={{ fontSize: 15, fontWeight: 700, color: T.muted }}>—</div> <div style={{ fontSize: 15, fontWeight: 700, color: rendementKleur }}>
{rendementPct === null ? "—" : `${rendementPct >= 0 ? "+" : ""}${rendementPct.toFixed(1)}%`}
</div>
</div> </div>
</VCard> </VCard>
+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "vibefinance", "name": "vibefinance",
"version": "1.0.12", "version": "1.0.13",
"description": "VibeFinance — persoonlijk vermogensbeheer", "description": "VibeFinance — persoonlijk vermogensbeheer",
"private": true, "private": true,
"repository": "https://vibehoogie.duckdns.org/vibe/VibeFinance", "repository": "https://vibehoogie.duckdns.org/vibe/VibeFinance",