diff --git a/CHANGELOG.md b/CHANGELOG.md index c0a18cb1b..ee6a16aa8 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,48 @@ # Changelog +## [1.39.6] — 2026-10-01 + +A critical security fix for the web framework, a workout token for devices +and bridges, a lab scan that no longer drops incomplete readings, and a +restore preview that appears at once. A full-history import can no longer +run beside its own retry, and the nightly clean-up steps around a restore. + +### Security + +- **Next.js 16.3.6.** Fixes a critical advisory against 16.2.0 to 16.3.5. + The floors of fast-uri (3.1.8), ip-address (10.7.1) and dompurify + (3.4.16) are raised for newer advisories; development-only copies of + @grpc/grpc-js, brace-expansion and undici 7 too. + +### Added + +- **Workout token.** Settings → API → Workout tokens mints a token with the + `workouts:write` scope (`POST /api/tokens/workouts`, recent confirmation + required, at most ten live tokens). It reaches `POST /api/workouts/batch` + only; workouts written with it carry the source `EXTERNAL`, and a body + that names a source is refused with 422. (#1054) + +### Fixed + +- **Lab scan review.** Saving is all or nothing over the selected readings; + incomplete ones are marked with a summary and focus on the first, instead + of being left out silently. (#1055) +- **Restore preview.** The counts a backup holds are stored with it + (migration 0364) and the preview answers from them; older backups are + read once and then stored. The query no longer retries, and only a real + schema failure is reported as one. (#1031) +- **Dashboard quick-add** follows the server's `intakeActionable` and no + longer offers an ended course. (#1040) +- **Dense glucose inside 90 days** is bucketed per local hour for the series + when the window holds more than 10 000 readings; statistics cover every + reading. The doctor report keeps glucose raw inside 90 days. +- **Full-history import lane.** Admission jobs expire after 16 hours instead + of pg-boss's default 15 minutes, each run holds an advisory lock on its + kind and account so a retry cannot run beside it, and the Google Health + import stops at its job budget as incomplete. (#1023) +- **Tombstone purge** deletes per account under the restore lock and leaves + an account being restored for the next night. (#1031) + ## [1.39.5] — 2026-09-28 A server with a per-minute heart-rate history stays inside its memory: the diff --git a/docs/api/openapi.yaml b/docs/api/openapi.yaml index 60b72dce6..20072acf6 100644 --- a/docs/api/openapi.yaml +++ b/docs/api/openapi.yaml @@ -1,7 +1,7 @@ openapi: 3.1.0 info: title: HealthLog API - version: 1.39.5 + version: 1.39.6 description: >- Self-hosted personal-health-tracking PWA — public API surface for the iOS native client and external ingest. diff --git a/package.json b/package.json index f9dc6e7a7..7dafc625f 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "healthlog", - "version": "1.39.5", + "version": "1.39.6", "description": "Self-hosted personal-health-tracking PWA with Withings integration, AI insights, and doctor-report PDF export.", "license": "PolyForm-Noncommercial-1.0.0", "homepage": "https://healthlog.dev", diff --git a/public/sw.js b/public/sw.js index d63ea1462..aee0ab404 100644 --- a/public/sw.js +++ b/public/sw.js @@ -36,7 +36,7 @@ try { // v1.4.38.4 → v1.4.42. Do not hand-edit; bump `package.json` and rebuild. const CACHE_VERSION = (typeof self !== "undefined" && self.__APP_VERSION__) || - /* @sw-version-fallback */ "v1.39.5"; + /* @sw-version-fallback */ "v1.39.6"; const STATIC_CACHE = `healthlog-static-${CACHE_VERSION}`; const PAGE_CACHE = `healthlog-pages-${CACHE_VERSION}`; // v1.18.6 — read-only data cache for a curated allowlist of safe GET `/api/*`