Adds webhook-based update system that allows triggering updates
directly from the mc-webui menu. Includes:
- Webhook server (updater.py) on port 5050
- Systemd service and install script
- API proxy endpoints for container-to-host communication
- Update modal with progress tracking and auto-reload
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Add HTML table with 150px thumbnail previews of all screenshots.
Images are clickable to view full size. Updated and added new
screenshots for menu, map, console, and image preview features.
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- version.py now captures and exports GIT_BRANCH
- Display branch badge next to version in menu (e.g., "2026.01.20+abc1234 [dev]")
- /api/version now returns branch field
- /api/check-update uses frozen branch instead of hardcoded "dev"
- Allows proper update checking for both dev and main branches
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Add /api/check-update endpoint that queries GitHub API
- Compare current commit hash with latest on dev branch
- Add check button next to version in menu
- Show spinning icon during check, green checkmark when done
- Display "Update available" link when newer version exists
- Handle rate limits and network errors gracefully
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Add scripts/update.sh with colored output and error handling
- Automates: git pull, version freeze, docker compose rebuild
- Update README with script usage and alias instructions
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Reduce emoji avatar border from 2.5px to 1.5px
- Reduce horizontal padding from 0.5rem to 0.25rem
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Emoji avatars are now displayed with a colored ring/outline
instead of filled background for better readability.
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Reduce horizontal padding in messages container
- Add colored circle background to emoji avatars
- Fix vertical alignment of avatar with sender name
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Add mini avatars next to sender names in channel chat
- Extract emoji from username for avatar (first emoji only)
- Use initials for users without emoji (1-2 letters)
- Generate consistent colors based on username hash
- Move sender name outside message bubble (MeshCore style)
- Add responsive styles for mobile devices
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Format changed from @[User]: »text« to @[User] »text«
Guillemets alone are sufficient to separate the quote.
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Guillemets (» «) no longer displayed - styling is sufficient
- Added line break after quoted text for better readability
- Raw message still contains guillemets for compatibility
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Changed quote format to: @[Username]: »quoted text«
- Added processQuotes() to detect and style »text« patterns
- Quote styling: italic, gray background, left border
- Different styling for own messages vs others
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Adds a Quote button next to Reply that allows quoting a message.
- Messages ≤20 bytes are quoted in full
- Longer messages are truncated with "..."
- Format: @[Username] "quoted text"
- Uses UTF-8 byte counting for accurate truncation
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
The template literal had newlines and spaces that were preserved by
white-space: pre-wrap CSS, causing unwanted gaps before and after
image previews in chat messages.
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Changed message content container from <p> to <div> to fix invalid HTML
when image previews are embedded. The <p> tag cannot contain block-level
elements like <div>, causing browsers to auto-close the paragraph and
create unwanted spacing between text and image preview.
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Rename Settings to Device Info with new cpu icon
- Display device parameters in readable table format
- Add copy-to-clipboard buttons for Name and Public Key
- Add map button for device location coordinates
- Show human-readable parameter names and values
- Hide telemetry parameters (not commonly needed)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Messages are now displayed immediately, then re-rendered once geo cache
is ready so Map buttons appear for contacts with GPS coordinates.
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Geo cache now loads fully in background without blocking setupAutoRefresh().
UI is ready as soon as messages are displayed.
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Add 60s cache for /api/contacts/detailed (reduces 4 USB calls to 0)
- Optimize /api/messages/updates to read file once instead of N×2 times
- Parallelize initialization: timestamps loaded together, messages and
geo cache loaded in parallel
- Defer checkForUpdates() to after messages are displayed
- Remove blocking checkForUpdates() from loadChannels()
- Add cache invalidation for contacts on add/delete operations
- Add performance timing logs to browser console
Expected improvement: ~10-20s → ~2-3s initial load time
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Use CircleMarker with different colors per contact type:
- CLI (blue), REP (green), ROOM (purple), SENS (orange)
- Add type filter checkboxes in map modal header
- Dynamically update markers when filters change
- Hide filter panel for single contact view
- Reduce message action buttons to 32x32px
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Remove text labels from Reply and Map buttons
- Add consistent 36x36px square buttons with icons only
- Add tooltips for accessibility
- Prepare for adding more action buttons in the future
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Add Leaflet CSS/JS and map modal to contacts_base.html
- Add showContactOnMap function to contacts.js (contacts page has separate template)
- Load contactsGeoCache before messages to ensure Map buttons appear on bubbles
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Replace Google Maps with Leaflet + OpenStreetMap (free, no API key)
- Add Map button in main menu to show all contacts with GPS
- Add Map button on message bubbles (next to Reply) for senders with GPS
- Contact Management Map buttons now open modal instead of new tab
- Lazy map initialization with proper Bootstrap modal handling
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This variable was defined but never used in the code.
Contact cleanup threshold is controlled directly in the UI.
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Most users don't need to edit .env anymore. Serial port and device
name are auto-detected. Troubleshooting section collapsed by default.
Reduced installation from 8 steps to 7.
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
ttyACM uses major 166, not 188 like ttyUSB.
Needed for Espressif ESP32-S3 based devices (Heltec V3, etc.)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
When MC_SERIAL_PORT=auto, bridge scans /dev/serial/by-id/ and:
- Uses the device if exactly one found
- Fails with helpful message if multiple devices (list provided)
- Fails if no devices found
docker-compose.yml now uses device_cgroup_rules instead of explicit
device mapping, allowing auto-detection inside the container.
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Updated README.md and .env.example to recommend auto-detection
of device name from meshcli prompt instead of manual configuration.
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Meshcli outputs status lines like "Fetching channels ....DeviceName|*".
Updated detection to extract device name after dot sequences.
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Bridge now detects device name from meshcli prompt ("DeviceName|*")
and exposes it via /health endpoint. mc-webui fetches this at startup
and uses RuntimeConfig for dynamic device name throughout the app.
Fallback chain: prompt detection → .infos command → MC_DEVICE_NAME env var
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
The filteredCountBadge in "Add Filtered" button was not updating when
unchecking type filter checkboxes resulted in zero matching contacts.
Now resets badge to '0' and clears filteredPendingContacts array.
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
gevent async_mode requires monkey-patching at startup and was causing
6-12s page load times (vs 1-2s before). Threading mode doesn't require
special setup and is sufficient for occasional Console commands.
- Change async_mode from 'gevent' to 'threading'
- Remove gevent/gevent-websocket from requirements (bridge has its own)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Add Flask-SocketIO to Tech Stack
- Add WebSocket support to mc-webui container description
- Add console.js and socket.io to Project Structure
- Add console.html to templates list
- Add WebSocket API section with Console events and features
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Add Console to Key Features list
- Add Console to Basic Usage section
- Add Console to Completed Features checklist
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Previous fix with TERM=dumb caused Public channel to disappear.
Only setting COLUMNS and LINES as fallback for os.get_terminal_size().
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
meshcli calls os.get_terminal_size() which fails without a TTY.
Setting COLUMNS, LINES, and TERM=dumb provides fallback values.
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Previous regex was too specific with \[\d+\] pattern.
New pattern ^[^|]+\|\* matches any line starting with <name>|*
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>