Skip to main content

Release Notes

Release NotesNotes: Drop — Fintech Payment App

Project: {{PROJECT_NAME}}Drop — Remittance + QR Payments Version: {{VERSION}}0.5.0 Date: {{DATE}}2026-02-23 Author: {{AUTHOR}}John (AI Director) Status: Draft | In Review | Approved Reviewers: {{REVIEWERS}}Alem Bašić (CEO)

Document History

Version Date Author Changes
0.1 {{DATE}}2026-02-23 {{AUTHOR}}John Initial draftrelease notes — Phase 0.5 Security Hardening

Release Metadata

Field Value
Version {{VERSION}}0.5.0
Release Date {{RELEASE_DATE}}2026-Q2 (TBD)
Environment Production (Fly.io, Stockholm)
Build {{BUILD_ID}}GitHub Actions CI #TBD
Git Tag v{{VERSION}}v0.5.0
Git SHA {{GIT_SHA}}TBD at release
Previous Version {{PREV_VERSION}}v0.4.0 (Phase 0 MVP)
Deployment Type {{TYPE}} Standard

Release Summary

{{RELEASE_SUMMARY}}

Example: "Version {{VERSION}}0.5.0 brings(Phase a0.5) redesigneddelivers checkoutthe experiencesecurity withhardening 40%sprint fewerrequired stepsbefore Drop can proceed to BaaS partner onboarding and improvedFinanstilsynet mobileregulatory support. We've also resolved {{N}} user-reported bugs and improved API response times by an average of 30%.submission. This release alsoresolves includes8 critical and high security updatesissues identified in the Phase 0 security audit (which scored Drop at 57/100), with a target score of 80/100 post-hardening. All existing featuresalluser usersregistration, OTP verification, PIN setup, remittance, QR payments, and exchange rates — remain fully functional. No new user-facing features are encouragedintroduced toin reviewthis therelease. SecurityThis Updatesis section."a mandatory security and compliance release.


New Features

Persistent

{{FEATURE_1_NAME}}Rate Limiting

Drop's

{{FEATURE_1_DESCRIPTION}}authentication rate limiter has been upgraded from in-memory to database-backed (SQLite in dev; PostgreSQL in production). This ensures rate limits survive server restarts and apply correctly across multiple instances. The limit remains 10 requests/minute for auth endpoints and 60 requests/minute for general API endpoints.

How to access: {{FEATURE_1_ACCESS}}Automatic — no user action required. Related ticket: {{TICKET_1}}SECURITY-AUDIT-001


{{FEATURE_2_NAME}}CSRF Protection on All Mutating Endpoints

{{FEATURE_2_DESCRIPTION}}CSRF middleware is now active on all POST, PATCH, and DELETE endpoints. This protects Drop users from cross-site request forgery attacks when logged in.

How to access: {{FEATURE_2_ACCESS}}Automatic — no user action required. Related ticket: {{TICKET_2}}SECURITY-AUDIT-002


Input Validation Hardening

All user inputs now pass through strict server-side validation including: XSS sanitization, SQL injection prevention (parameterized queries enforced), maximum field lengths, and Unicode normalization for Bosnian/Serbian characters (š, đ, ć, č, ž).

How to access: Automatic — affects all form submissions. Related ticket: SECURITY-AUDIT-003


Improvements & Enhancements

Improvement Description Impact Ticket
{{IMPROVEMENT_1}}bcrypt rounds upgrade {{DESCRIPTION}}Increased from 10 to 12 rounds {{IMPACT}}4x stronger password hashing; ~300ms increase in login time (within NFR target) {{TICKET}}SEC-001
{{IMPROVEMENT_2}}JWT secret enforcement {{DESCRIPTION}}App fails fast if JWT_SECRET env var is not set {{IMPACT}}Prevents accidental deployment with weak/default JWT secret {{TICKET}}SEC-002
{{IMPROVEMENT_3}}Security headers added {{DESCRIPTION}}HSTS, X-Frame-Options: DENY, X-Content-Type-Options: nosniff, CSP added {{IMPACT}}Protects against clickjacking, MIME sniffing, and XSS via CSP {{TICKET}}SEC-003
httpOnly cookie enforcementJWT now strictly httpOnly, SameSite=StrictPrevents JS access to JWT cookieSEC-004
Password hash validationSHA-256 hashes rejected at loginPrevents use of weak hashes even if introduced by data importSEC-005
Audit loggingAll auth events, transactions, KYC changes logged with user_id + IP + timestampCompliance with AML/AMLD6 audit trail requirementsSEC-006
Per-user transaction locksConcurrent transactions from same user serialisedPrevents double-spend race conditionSEC-007
10KB password rejectionPasswords > 1,000 characters rejected with validation errorPrevents bcrypt DoS attack via long passwordSEC-008

Bug Fixes

# Description Severity Reported By Ticket
1 {{BUG_1}}Rate limiter reset on server restart (in-memory only) {{SEVERITY}}High {{REPORTER}}Security audit {{TICKET}}SEC-AUDIT-H01
2 {{BUG_2}}JWT secret missing env var check — app started with undefined secret {{SEVERITY}}Critical {{REPORTER}}Security audit {{TICKET}}SEC-AUDIT-C01
3 {{BUG_3}}No CSRF protection on /api/transactions/remittance {{SEVERITY}}Critical {{REPORTER}}Security audit {{TICKET}}SEC-AUDIT-C02
4bcrypt rounds set to 10 (below fintech standard of 12)HighSecurity auditSEC-AUDIT-H02
5Missing security headers (no HSTS, no CSP, no X-Frame-Options)HighSecurity auditSEC-AUDIT-H03
6Long password (10KB) causes bcrypt to hangHighSecurity auditSEC-AUDIT-H04
7No per-user transaction lock — double-spend possible under loadCriticalSecurity auditSEC-AUDIT-C03
8Audit log missing for KYC status changesHighSecurity auditSEC-AUDIT-H05

Security Updates

# CVE / Reference Severity Component Fix
1 {{CVE_1}}SEC-AUDIT-C01 {{SEVERITY}}Critical {{COMPONENT}}JWT authentication UpdatedFail-fast toon {{VERSION}}missing JWT_SECRET; no default secret
2 SEC-AUDIT-C02CriticalTransaction APICSRF token required on all POST/PATCH/DELETE endpoints
3SEC-AUDIT-C03CriticalTransaction processingPer-user pessimistic locking (SQLite: serialized writes; PostgreSQL: SELECT FOR UPDATE)
4SEC-AUDIT-H01 High AuthenticationRate limiting FixedMigrated timingfrom attackin-memory into tokenDB-backed comparisonrate limiter
5SEC-AUDIT-H02HighPassword hashingbcrypt rounds increased to 12; SHA-256 hashes rejected
6SEC-AUDIT-H03HighHTTP securityHSTS, X-Frame-Options, X-Content-Type-Options, CSP headers enabled
7SEC-AUDIT-H04HighInput validation1,000 character password maximum enforced before bcrypt
8SEC-AUDIT-H05HighAudit loggingAudit log added for all auth events, transactions, KYC changes

Action required by users: {{USER_ACTION}}None — all security updates applied server-side automatically.


Breaking Changes

{{#if BREAKING_CHANGES}}

Warning: This release contains breaking changes. Review carefully before upgrading.

Breaking Change 1: {{BC_1_TITLE}}

What changed: {{BC_1_WHAT}} Why it changed: {{BC_1_WHY}} Who is affected: {{BC_1_AFFECTED}} Required action: {{BC_1_ACTION}}

Migration Guide

# Before (v{{PREV_VERSION}} and earlier)
{{BC_1_BEFORE}}

# After (v{{VERSION}})
{{BC_1_AFTER}}

Migration deadline: {{BC_1_DEADLINE}}


Breaking Change 2: {{BC_2_TITLE}}

{{else}}

No breaking changes in this release. All existing integrations and configurations remain compatible.

{{/if}}The API contract (endpoints, request/response shapes) is unchanged. Users will not notice any functional difference; only security and reliability improve.


Known Issues

# Description Severity Workaround Expected Fix
1 {{KNOWN_1}}BaaS integration mocked — real bank account balance not shown {{SEVERITY}}Medium {{WORKAROUND}}App clearly labels balance as "simulated" in mock mode {{FIX_VERSION}}Phase 2 (BaaS partner onboarding)
2 {{KNOWN_2}}BankID SCA not yet integrated — DOB validation via form only {{SEVERITY}}Medium {{WORKAROUND}}MVP validates DOB field; BankID replaces in Phase 2 {{FIX_VERSION}}Phase 2
3Sumsub KYC is mocked — no real identity verificationMediumMVP uses mock KYC; kyc_status auto-approved in devPhase 2
4SQLite concurrent write limit (~200 users)LowSufficient for MVP; PostgreSQL migration planned at 200 concurrent usersPhase 1 (PostgreSQL migration)
5Cards feature not availableLowFeature-flagged; requires card partner (Phase 3)Phase 3

API Changes

New Endpoints

Method Path Description
{{METHOD}}GET /api/healthHealth check endpoint — returns {{PATH}"status":"ok","db":"connected"}
{{DESCRIPTION}}GET/api/ratesExchange rates — returns 6 NOK corridors
GET/api/rates/:currencySingle exchange rate (e.g., /api/rates/RSD)

Modified Endpoints

Method Path Change Breaking
{{METHOD}}POST {{PATH}}/api/auth/register {{CHANGE}}Password max length 1,000 chars enforced YesNo
POST/api/auth/login SHA-256 hash rejection addedNo
POST/api/transactions/remittanceCSRF token required in headerNo (CSRF token auto-set by client)
POST/api/transactions/qr-paymentCSRF token required in headerNo

Deprecated Endpoints

MethodPathReplacementRemoval Date
{{METHOD}}{{PATH}}{{NEW_PATH}}{{DATE}}

Removed Endpoints

this
MethodPathRemoved

None in

Replacement
{{METHOD}}{{PATH}}v{{VERSION}}{{REPLACEMENT}}
release.

API documentation: {{API_DOCS_LINK}}docs/backend/API-REFERENCE.md


Database Changes

Change Type Table / Collection Details
{{CHANGE_1}}Add audit_logs table Add column / Remove / Index / Type changetable {{TABLE}}audit_logs {{COLUMN}}id, {{TYPE}}user_id, event_type, ip_address, metadata, created_at
{{CHANGE_2}}Add rate_limit_requests table {{TYPE}}Add table {{TABLE}}rate_limit_requests {{DETAILS}}id, key, request_count, window_start, created_at — replaces in-memory limiter
Add transaction_locks tableAdd tabletransaction_locksuser_id, locked_at, expires_at — prevents double-spend

Migration files:

  • Up: {{MIGRATION_PATH}}src/drop-app/db/migrations/0005_security_hardening.sql
  • Down: {{MIGRATION_PATH}}src/drop-app/db/migrations/0005_security_hardening_down.sql

Configuration Changes

Key Change Default Required Notes
{{KEY_1}}JWT_SECRETNow required (fail-fast if missing)NoneYesMust be cryptographically random; ≥ 32 chars
BCRYPT_ROUNDSNew — configurable12NoDo not set below 12 in production
RATE_LIMIT_WINDOW_MS New {{DEFAULT}}60000 (1 min) Yes / No {{NOTES}}Rate limit window in milliseconds
{{KEY_2}}RATE_LIMIT_MAX_AUTH ChangedNew {{OLD}} → {{NEW}}10 {{DEFAULT}}Yes / No {{NOTES}}Max auth requests per window per IP
{{KEY_3}}RATE_LIMIT_MAX_GENERAL RemovedNew 60 No UseMax general API requests per window per IP
NEXT_PUBLIC_SERVICE_MODEExistingmockYesKeep {{REPLACEMENT}}mock insteaduntil BaaS partner confirmed

Dependencies Updated

Package From To Type Notes
{{PKG_1}}jose {{OLD_VER}}5.x {{NEW_VER}}5.x (patch) Security CVE-{{ID}}JWT library — latest patch
{{PKG_2}}bcrypt {{OLD_VER}}5.x {{NEW_VER}}5.x (patch) FeatureSecurity {{NOTES}}Password hashing
{{PKG_3}}next 15.x15.x (patch)SecurityFramework security patches
{{OLD_VER}}zod 3.x3.x (patch)FeatureInput validation
{{NEW_VER}}csrf Maintenance NewSecurityCSRF protection middleware

Performance Impact

Metric Before After Change Notes
P95 API latency (overall)standard) {{BEFORE}}ms~200ms {{AFTER}}ms~200ms {{DELTA}}%0% No change — non-auth endpoints unaffected
P99P95 APIlogin latencytime (critical path)bcrypt) {{BEFORE}}ms~600ms {{AFTER}}ms~800ms {{DELTA}}%+33% Expected — bcrypt rounds 10→12; still within 1,000ms NFR
PageP95 loadregistration time (FCP) {{BEFORE}}ms~600ms {{AFTER}}ms~800ms {{DELTA}}%+33% HomepageSame as login
DatabaseRate querylimit timecheck (avg)50 concurrent) {{BEFORE}}ms~1,800ms {{AFTER}}ms~1,900ms {{DELTA}}%+5.5% DB-backed limiter; still within 2,000ms NFR
DB SELECT~5ms~5ms0%No change
DB INSERT~10ms~11ms+10%Audit log write added; still within 20ms NFR

Contributors

Contributor GitHub / ID Contributions
{{NAME_1}}John (AI Director) @{{GH_1}}AI Director — Claude Opus {{CONTRIBUTIONS}}Architecture, spec, coordination
{{NAME_2}}Builder Agent @{{GH_2}}AI — Claude Sonnet {{CONTRIBUTIONS}}Implementation, all code changes
Validator AgentAI — Claude Sonnet (read-only)Code review, test verification
Alem Bašić@alai-alemCEO review, business sign-off


Approval

Role Name Date Signature
Author John (AI Director) 2026-02-23 Approved (AI)
ReviewerTech Lead John 2026-02-23 Approved
ApproverAI Director (John) John 2026-02-23Approved
CEO (Alem)Alem BašićTBD