Files
meshcore-gui/CHANGELOG.md
2026-02-08 21:29:52 +01:00

9.3 KiB

CHANGELOG

All notable changes to MeshCore GUI are documented in this file. Format follows Keep a Changelog and Semantic Versioning.


[5.4.0] - 2026-02-08 — Contact Maintenance Feature

Added

  • Pin/Unpin contacts (Iteratie A) — Toggle to pin individual contacts, protecting them from bulk deletion

    • Persistent pin state stored in ~/.meshcore-gui/cache/<ADDRESS>_pins.json
    • Pinned contacts visually marked with yellow background
    • Pinned contacts sorted to top of contact list
    • Pin state survives app restart
    • New service: services/pin_store.py — JSON-backed persistent pin storage
  • Bulk delete unpinned contacts (Iteratie B) — Remove all unpinned contacts from device in one action

    • "🧹 Clean up" button in contacts panel with confirmation dialog
    • Shows count of contacts to be removed vs. pinned contacts kept
    • Progress status updates during removal
    • Automatic device resync after completion
    • New service: services/contact_cleaner.py — ContactCleanerService with purge statistics
  • Auto-add contacts toggle (Iteratie C) — Control whether device automatically adds new contacts from mesh adverts

    • "📥 Auto-add" checkbox in contacts panel (next to Clean up button)
    • Syncs with device via set_manual_add_contacts() SDK call
    • Inverted logic handled internally (UI "Auto-add ON" = set_manual_add_contacts(false))
    • Optimistic update with automatic rollback on BLE failure
    • State synchronized from device on each GUI update cycle

Changed

  • 🔄 contacts_panel.py: Added pin checkbox per contact, purge button, auto-add toggle, DM dialog (all existing functionality preserved)
  • 🔄 commands.py: Added purge_unpinned and set_auto_add command handlers
  • 🔄 shared_data.py: Added auto_add_enabled field with thread-safe getter/setter
  • 🔄 protocols.py: Added set_auto_add_enabled and is_auto_add_enabled to Writer and Reader protocols
  • 🔄 dashboard.py: Passes PinStore and set_auto_add_enabled callback to ContactsPanel
  • 🔄 UI language: All Dutch strings in contacts_panel.py and commands.py translated to English

Fixed

  • 🐛 Route table names and IDs not displayed — Route tables in both current messages (RoutePage) and archive messages (ArchivePage) now correctly show node names and public key IDs for sender, repeaters and receiver

Changed

  • 🔄 CHANGELOG.md: Corrected version numbering (v1.0.x → v5.x), fixed inaccurate references (archive button location, filter state persistence)
  • 🔄 README.md: Added Message Archive feature, updated project structure, configuration table and architecture diagram
  • 🔄 MeshCore_GUI_Design.docx: Added ArchivePage, MessageArchive, Models components; updated project structure, protocols, configuration and version history

[5.2.0] - 2026-02-07 — Archive Viewer Feature

Added

  • Archive Viewer Page (/archive) — Full-featured message archive browser
    • Pagination (50 messages per page, configurable)
    • Channel filter dropdown (All + configured channels)
    • Time range filter (24h, 7d, 30d, 90d, All time)
    • Text search (case-insensitive)
    • Filter state stored in instance variables (reset on page reload)
    • Message cards with same styling as main messages panel
    • Clickable messages for route visualization (where available)
    • 💬 Reply functionality — Expandable reply panel per message
    • 🗺️ Inline route table — Expandable route display per archive message with sender, repeaters and receiver (names, IDs, node types)
  • MessageArchive.query_messages() method

    • Filter by: time range, channel, text search, sender
    • Pagination support (limit, offset)
    • Returns tuple: (messages, total_count)
    • Sorting: Newest first
  • UI Integration

    • "📚 Archive" button in Messages panel header (opens in new tab)
    • Back to Dashboard button in archive page
  • Reply Panel
    • Expandable reply per message (💬 Reply button)
    • Pre-filled with @sender mention
    • Channel selector
    • Send button with success notification
    • Auto-close expansion after send

Changed

  • 🔄 SharedData.get_snapshot(): Now includes 'archive' field
  • 🔄 MessagesPanel: Added archive button in header row
  • 🔄 Both entry points (__main__.py and meshcore_gui.py): Register /archive route

Performance

  • Query: ~10ms for 10k messages with filters
  • Memory: ~10KB per page (50 messages)
  • No impact on main UI (separate page)

Known Limitations

  • Route visualization only works for messages in recent buffer (last 100)
  • Archived-only messages show warning notification
  • Text search is linear scan (no indexing yet)
  • Sender filter exists in API but not in UI yet

[5.1.3] - 2026-02-07 — Critical Bugfix: Archive Overwrite Prevention

Fixed

  • 🐛 CRITICAL: Fixed bug where archive was overwritten instead of appended on restart
  • 🐛 Archive now preserves existing data when read errors occur
  • 🐛 Buffer is retained for retry if existing archive cannot be read

Changed

  • 🔄 _flush_messages(): Early return on read error instead of overwriting
  • 🔄 _flush_rxlog(): Early return on read error instead of overwriting
  • 🔄 Better error messages for version mismatch and JSON decode errors

Details

Problem: If the existing archive file had a JSON parse error or version mismatch, the flush operation would proceed with existing_messages = [], effectively overwriting all historical data with only the new buffered messages.

Solution: The flush methods now:

  1. Try to read existing archive first
  2. If read fails (JSON error, version mismatch, IO error), abort the flush
  3. Keep buffer intact for next retry
  4. Only clear buffer after successful write

Impact: No data loss on restart or when archive files have issues.

Testing

  • Added test_append_on_restart_not_overwrite() integration test
  • Verifies data is appended across multiple sessions
  • All existing tests still pass

[5.1.2] - 2026-02-07 — RxLog message_hash Enhancement

Added

  • message_hash field added to RxLogEntry model
  • RxLog entries now include message_hash for correlation with messages
  • Archive JSON includes message_hash in rxlog entries

Changed

  • 🔄 events.py: Restructured on_rx_log() to extract message_hash before creating RxLogEntry
  • 🔄 message_archive.py: Updated rxlog archiving to include message_hash field
  • 🔄 Tests updated to verify message_hash persistence

Benefits

  • Correlation: Link RX log entries to their corresponding messages
  • Analysis: Track which packets resulted in messages
  • Debugging: Better troubleshooting of packet processing

[5.1.1] - 2026-02-07 — Entry Point Fix

Fixed

  • meshcore_gui.py (root entry point) now passes ble_address to SharedData
  • Archive works correctly regardless of how application is started

Changed

  • 🔄 Both entry points (meshcore_gui.py and meshcore_gui/__main__.py) updated

[5.1.0] - 2026-02-07 — Message & Metadata Persistence

Added

  • MessageArchive class for persistent storage
  • Configurable retention periods (MESSAGE_RETENTION_DAYS, RXLOG_RETENTION_DAYS, CONTACT_RETENTION_DAYS)
  • Automatic daily cleanup of old data
  • Batch writes for performance
  • Thread-safe with separate locks
  • Atomic file writes
  • Contact retention in DeviceCache
  • Archive statistics API
  • Comprehensive tests (20+ unit, 8+ integration)
  • Full documentation

Storage Locations

  • ~/.meshcore-gui/archive/<ADDRESS>_messages.json
  • ~/.meshcore-gui/archive/<ADDRESS>_rxlog.json

Requirements Completed

  • R1: All incoming messages persistent
  • R2: All incoming RxLog entries persistent
  • R3: Configurable retention
  • R4: Automatic cleanup
  • R5: Backward compatibility
  • R6: Contact retention
  • R7: Archive stats API