- Rename Go module from github.com/cclohmar/ReceiptNext to NextExpense
- Update all import paths across 7 Go source files
- Update templates (titles, headings, branding)
- Update static files (manifest.json, sw.js, CSS)
- Update config (Makefile, install.sh, .env.example)
- Update README with new name and URLs
- Rename service file receiptnext.service -> nextexpense.service
- Update install paths, service names, log paths in install.sh
- Removed all pre-built binary download logic from install.sh
- install.sh now installs Go (via apt/dnf/apk) if not present
- Always builds from source — ensures latest code, correct platform
- Removed dist/ binaries from local disk (not tracked in git)
- Moves chown to the very beginning of the update
- Ensures app user can write to /opt/receiptnext/ before build
- Removes redundant chown later in update (already done upfront)
- go build can't overwrite a root-owned binary as app user
- Added rm -f app before go build in both update and fresh install paths
- Also chown the app binary alongside .go cache
- Build cache may be root-owned from previous builds
- Added sudo_if chown before both update and fresh build steps
- Prevents 'permission denied' on go mod cache writes
- Uses stat to get original owner:group before backup
- chown restores backup file to original owner
- Prevents database becoming readonly after update
- Added sudo -v at start of both fresh install and update mode
- Caches sudo credentials so subsequent sudo_if calls don't prompt
- If sudo is unavailable, shows clear error message
- Prevents 'Access denied' on systemctl restart
- Creates timestamped backup at /opt/receiptnext/backups/expenses-YYYYMMDD-HHMMSS.db
- rsync only targets templates/ and static/ — database is never touched
- update mode previously only rebuilt the binary
- Now also rsyncs templates/ and static/ to install dir
- Copies updated install.sh to install dir
- Fixes ownership of new files
- Uses sudo_if for systemctl restart
- Checks for git before clone/pull — installs via apt/dnf/apk
- Checks for curl before downloading release binary
- Checks for python3 before parsing release JSON
- Multi-distro support (apt-get, dnf, apk)
CR-1: Path traversal in createReceiptZip — validate image_path is within storage/
CR-2: Missing authz on EditExpense/UpdateExpense — verify event ownership
CR-3: OTP timing side-channel — use crypto/subtle.ConstantTimeCompare
CR-4: Logout doesn't invalidate session — moved to AuthHandler with Sessions.Delete()
CR-5: OTP reuse race condition — mutex lock around validate+delete
CR-6: Live credentials on disk — removed .env from disk entirely
CR-7: No TLS — documented as expected behind-proxy deployment
Additional:
- Removed stale github.com/expenseflow import path from auth.go
- Made EnvironmentFile optional (prefix with -) so .env is not required
- App runs and starts clean without any .env file
- glm-ocr is a 1.1B parameter model built specifically for OCR
- No reasoning overhead, no thinking field issues
- Faster inference than qwen3.5 on CPU
- Removed old qwen3.5 models (2B + 0.8B) to free ~4GB disk
- Updated install.sh, ollama.go, .env.example defaults
- ollamaResponse now reads both content and thinking fields
- Falls back to thinking if content is empty
- Install script adds model warm-up prompt to preload into memory
- Warm-up uses OLLAMA_HOST for correct user context
- Makes first real receipt analysis faster
- The Ollama installer run via sudo leaves /usr/share/ollama owned by root
- The ollama service runs as the ollama user and needs write access
- Added chown after installation to fix permissions
- Set GOMODCACHE + GOPATH to /opt/receiptnext/.go (writable location)
- Removes sudo from README one-liner — script self-elevates
- Build now works for users whose home directory isn't writable
- Wait loop now checks HTTP endpoint (127.0.0.1:11434/api/tags)
instead of just the CLI version
- Increased retries from 10 to 15 (30s → 30s with 2s intervals)
- Uses sudo -u ollama for pull so models go to correct user directory
- install.sh detects if Go is installed
- If Go available: builds from source (current behavior)
- If Go missing: downloads pre-built binary from latest release
- Detects amd64/arm64 architecture automatically
- Same logic applies to -update mode
- Removed hard dependency on ollama.service in systemd unit
- install.sh detects the real user (SUDO_USER or whoami)
- If root, creates receiptnext system user
- If regular user, uses that user for the service
- User is added to ollama group for CLI access
- Systemd service uses User=receiptnext (or detected user)
- All file ownership set to the app user