Commit graph

73 commits

Author SHA1 Message Date
b4206b63d1
Increase GPS drift threshold from 15m to 50m
Fixed issue where stationary stations like K5SGD-D were showing multiple
positions due to minor GPS accuracy variations. The previous 15-meter
threshold was too strict for typical GPS drift which can vary 5-30 meters.

- Increased default threshold in GeoUtils from 10m to 50m
- Updated packet processor to use 50m threshold for movement detection
- Verified with K5SGD-D showing ~24m variations that are now ignored

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-21 11:23:37 -05:00
7dc6c616a2
Bundle all vendor JavaScript files locally instead of loading from CDNs
This change eliminates all external CDN dependencies by bundling JavaScript
libraries locally using esbuild. All vendor files are now served from the
application's own assets, improving reliability and privacy.

Changes:
- Created assets/js/vendor.js to bundle all external libraries
- Added vendor bundle configuration to esbuild in config files
- Updated all templates to use local vendor.js instead of CDN scripts
- Created download-vendor-files.sh script to fetch vendor libraries
- Added vendor files to .gitignore (they're downloaded during setup)
- Updated CSS imports to include vendor stylesheets
- Added vendor build step to assets.deploy mix task

Bundled libraries:
- Leaflet 1.9.4 (mapping library)
- Leaflet.heat 0.2.0 (heatmap plugin)
- Leaflet.markercluster 1.5.3 (marker clustering)
- OverlappingMarkerSpiderfier 0.2.6 (overlapping marker handling)
- Chart.js 4.5.0 (charting library)
- chartjs-adapter-date-fns 3.0.0 (date adapter for Chart.js)

All functionality tested and working correctly with local bundles.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-21 09:52:39 -05:00
aa168f8dcd
Add URL parameter handling for trail duration and historical data
Implemented URL persistence for map settings to preserve user preferences:

- Added `trail` parameter for trail duration (1, 6, 12, 24, 48, 168 hours)
- Added `hist` parameter for historical data hours (1, 3, 6, 12, 24 hours)
- Parameters only appear in URL when different from default value (1 hour)

Changes:
- Updated handle_url_update to include trail and hist parameters
- Modified mount to parse these parameters on page load
- Updated handle_params to parse parameters on URL changes
- Added update_url_with_current_state helper function
- Modified update_trail_duration and update_historical_hours event handlers
  to update URL when settings change
- Fixed finalize_mount_assigns to preserve parsed values

This allows users to share or bookmark URLs with specific trail duration
and historical data settings, improving the user experience.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-21 09:14:46 -05:00
cf78298f46
Fix trail lines not connecting historical positions
When changing trail duration and historical data settings, historical positions
would show up on the map but trail lines wouldn't connect them. This was caused
by a mismatch between trail ID generation and callsign extraction.

## Changes

- Fix getTrailId() to properly extract base callsigns from historical marker IDs
- Add setTrailDuration() method to TrailManager for dynamic duration updates
- Add LiveView event to synchronize trail duration changes with client
- Add comprehensive tests for historical ID handling

## Problem
Historical markers have IDs like "hist_CALLSIGN_123" but getTrailId() was
returning the full ID while TrailManager.extractBaseCallsign() extracted just
"CALLSIGN", creating separate trails instead of connected ones.

## Solution
Updated getTrailId() to extract base callsigns from historical IDs using the
same logic as TrailManager, ensuring all positions from the same station use
the same trail ID and connect properly.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-21 08:31:16 -05:00
437cddfd51
Remove debug logger statements for RF path hover functionality
Removed three logger.info statements that were cluttering the logs:
- "RF path hover start - path: ..."
- "Parsed path stations: ..."
- "Found x station positions"

These were debug statements that are no longer needed in production.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-20 08:44:06 -05:00
92585ae34f
Fix race condition when zooming map quickly
- Increase debounce time from 300ms to 400ms for bounds updates
- Cancel in-progress historical loading when new bounds are scheduled
- Add stale update detection to skip outdated bounds updates
- Clear timer reference and pending bounds when processing updates
- Add debug logging for cancelled loads and stale updates

This prevents overlapping historical data loads during rapid zoom
changes, eliminating duplicate packets and improving performance.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-18 12:27:46 -05:00
566198afa7
clean up warnings 2025-07-16 08:55:46 -05:00
b4fcd4382e
Fix missing socket return in handle_pending_bounds
The function was sending a message but not returning the socket,
causing an ArgumentError when the result was passed to assign/3.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-15 11:14:48 -05:00
114514bdfe
Fix missing historical_packets in socket assigns
Add missing :historical_packets initialization to prevent KeyError when
HistoricalLoader tries to access it during zoom-based display handling.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-15 11:07:05 -05:00
e97d1d6e33
Fix duplicate indexes and missing socket assigns
- Remove duplicate received_at indexes (packets_received_at_asc_idx and packets_recent_hour_idx)
  that were consuming 423 MB, keeping only packets_received_at_idx
- Fix KeyError by initializing missing :all_packets and :visible_packets in socket assigns
- All tests now pass successfully

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-15 11:01:27 -05:00
53206978df
improvements 2025-07-14 17:06:39 -05:00
3730b8c848
performance improvements 2025-07-14 16:35:58 -05:00
e6ccb9662b
major refactor for cleanup 2025-07-14 12:06:10 -05:00
b065404803
Fix credo warnings and ensure clean compilation
- Renamed predicate functions to follow Elixir conventions:
  - is_finite? → finite?
  - is_finite_number? → finite_number?
  - is_finite_float? → finite_float?
- Fixed all function returns to ensure proper nil handling
- Applied mix format to all files
- All tests pass with no compilation warnings

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-14 10:25:01 -05:00
94f3a62539
Add comprehensive input sanitization for coordinate parsing
Security improvements:
- Added sanitize_numeric_string to remove dangerous characters
- Limited input string length to prevent DoS attacks (20 chars for numbers)
- Added is_finite? checks to prevent infinity/NaN values
- Validate coordinate ranges (lat: -90 to 90, lng: -180 to 180)
- Added safe_parse_coordinate with proper validation
- Updated to_float in EncodingUtils with security validations
- Protected against integer overflow in coordinate conversions
- Added sanitize_path_string for APRS path validation

All coordinate inputs from users are now:
1. Sanitized to remove injection characters
2. Length-limited to prevent resource exhaustion
3. Validated for finite values (no infinity/NaN)
4. Checked against valid geographic ranges
5. Given safe fallback defaults

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-14 10:20:10 -05:00
1934b8d014
Optimize memory pruning performance for large datasets
- Implemented dual-strategy pruning based on overage size
- Small overages (<10 packets): Only remove exactly what's needed
- Large overages: Batch prune with 20% buffer to reduce frequency
- Used Map.drop for more efficient bulk deletion
- Added Stream for lazy evaluation in small overage case
- Reduces complexity from O(n log n) on every insertion to:
  - O(k log k) for small overages where k << n
  - Amortized O(n log n) for large overages with buffering
- This significantly improves performance when managing thousands of packets

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-14 10:11:53 -05:00
133dd2cc0e
Fix integer overflow risk in duration parsing
- Added validation for trail_duration values (1, 6, 12, 24, 48, 168 hours)
- Added validation for historical_hours values (1, 3, 6, 12, 24 hours)
- Created parse_trail_duration and parse_historical_hours helper functions
- Functions return safe defaults (1 hour) for invalid input
- Prevents potential integer overflow from unchecked String.to_integer calls
- Fixed all compilation warnings by properly grouping handle_event clauses

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-14 10:08:00 -05:00
6026c0f888
Fix failing tests and improve movement tracking
- Fixed PHG parsing test to match actual parser behavior
- Fixed movement test to properly handle batch loading behavior
- Movement test now sets bounds and uses higher zoom level
- Added helper function to flush events during test setup
- All tests now passing with clean compilation

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-14 10:03:04 -05:00
93c3fe0f19
feat: improve APRS map with beacon filtering, error handling, and performance optimizations
- Filter APRS built-in beacon patterns (WIDE, TRACE, RELAY, etc.) from RF paths
- Add comprehensive error recovery for database query failures
- Implement memory management with packet limits to prevent unbounded growth
- Add loading state indicators with progress tracking
- Increase debounce timing and add generation-based request cancellation
- Refactor code to use pattern matching instead of conditionals
- Add input validation for callsigns
- Fix all credo and compilation warnings

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-14 09:42:29 -05:00
766a1301e0
fix stations that heard call 2025-07-13 18:55:51 -05:00
610a5b8949
refactor 2025-07-13 16:49:20 -05:00
fa89712587
main map improvements 2025-07-13 14:58:13 -05:00
532a81c0b4
integrate /:call to main page 2025-07-13 10:36:58 -05:00
4348d34f62
fix weather 2025-07-12 10:53:11 -05:00
ad88e34ab6
account for gps drift 2025-07-12 09:40:28 -05:00
b71ae879e9
debug cleanup 2025-07-11 14:05:42 -05:00
c40e85d47a
geolocation debug 2025-07-11 14:00:50 -05:00
55b1a771e2
geolocation debug 2025-07-11 13:57:32 -05:00
96e4c305f0
staging fix 2025-07-11 13:48:14 -05:00
d76006c2ae
fix locate me arrow 2025-07-11 13:40:00 -05:00
aaad32c683
geolocation fix 2025-07-11 13:34:54 -05:00
1b428cbf78
add spider cluster 2025-07-11 13:00:32 -05:00
1a52bf4baf
geolocation tweak 2025-07-10 17:54:35 -05:00
13ac1731fd
wip 2025-07-10 17:49:38 -05:00
f5e0f33ac2
fix geolocation hopefully 2025-07-10 17:12:49 -05:00
4f0fa59be8
ip lookup on page load 2025-07-10 16:45:21 -05:00
aaf92d9045
add heatmap on zoom out 2025-07-10 14:26:01 -05:00
d45aed256d
fix historical packet loading 2025-07-10 13:15:16 -05:00
48447ab42e
refactor and performance improvements 2025-07-10 10:53:34 -05:00
8eb1e90622
use postgis for testing 2025-07-09 16:48:55 -05:00
514d1b66d5
fix all the main map display issues 2025-07-09 16:20:29 -05:00
57fe2b0182
Remove all delays from historical packet loading for maximum speed
Server-side optimizations:
- Remove all Process.send_after delays - use immediate send()
- High zoom (10+): Load everything in single batch (up to 500 packets)
- Low zoom: Load all batches immediately without delays
- Remove debug logging for performance

Client-side optimizations:
- Remove chunking delays and requestAnimationFrame
- Process all packets immediately without setTimeout
- Remove 10-packet chunk limit - process everything at once

Result: Historical packets now load as fast as possible
without artificial delays or chunking bottlenecks.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-09 09:33:21 -05:00
a9414823f1
Fix spurious bounds_changed events and event loops
Key fixes:
- Combine bounds_changed and update_map_state into single event
- Remove duplicate sendBoundsToServer() calls
- Add programmaticMove flag to prevent event loops
- Only process bounds updates when bounds actually change
- Debounce events with 300ms timeout

This eliminates:
- Duplicate server events for same user action
- Event loops when server updates URL
- Unnecessary bounds processing
- Excessive server load

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-09 09:30:05 -05:00
c873614bf1
Fix compilation error by importing push_patch
- Add push_patch to Phoenix.LiveView imports
- Fix trailing whitespace issue
- App now compiles successfully with URL functionality
2025-07-09 09:25:52 -05:00
052e131400
Add URL updating and restoration for map state (zoom/pan)
Features implemented:
- Parse URL parameters on mount (lat, lng, z)
- Update URL when map moves or zooms
- Restore map state from URL parameters
- Handle URL changes via handle_params
- Validate and clamp coordinate values

URL format: /?lat=40.7128&lng=-74.0060&z=12

Benefits:
- Shareable map links with exact position
- Browser back/forward navigation support
- Bookmarkable map locations
- Deep linking to specific map views

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-09 09:23:54 -05:00
c2d3418972
Fix progressive loading activation and optimize for high zoom levels
Critical fixes:
- Replace old load_historical_packets_for_bounds with progressive loading
- Fix handle_info_initialize_replay to use progressive loading
- Fix process_bounds_update to use progressive loading
- Add debug logging to track batch loading

High zoom optimizations:
- Very zoomed in (15+): 10 packets per batch, 10ms delays
- Moderately zoomed (12-14): 20 packets per batch, 20ms delays
- Medium zoom (8-11): 35 packets per batch, 35ms delays
- Use linear delays instead of exponential for faster loading

This ensures progressive loading is actually used and optimized
for high zoom levels where viewport is small.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-09 09:18:42 -05:00
7318d2dfbc
Optimize viewport-based loading with zoom-aware batching
Key improvements:
- Fix spatial query order: Apply bounds filtering BEFORE limit/offset
- Add zoom-level based batch sizing (20-100 packets per batch)
- Dynamic batch count based on zoom level (2-5 batches)
- Faster loading delays for high zoom levels (25ms vs 50ms)
- Include zoom level in cache keys for better cache efficiency

Performance benefits:
- Zoomed in far (zoom 15+): 2 batches of 20 packets each
- Moderately zoomed (zoom 12-14): 3 batches of 35 packets each
- Medium zoom (zoom 8-11): 4 batches of 50 packets each
- Zoomed out (zoom <8): 5 batches of 75-100 packets each

This ensures packets are loaded from the current viewport first,
dramatically reducing load times when zoomed in.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-09 09:14:12 -05:00
1932f63b91
Implement progressive loading for historical packets to improve map performance
- Add progressive loading system that splits 200 packets into 4 batches of 50 each
- Implement client-side chunked rendering to prevent UI blocking
- Add caching layer using Aprsme.CachedQueries for better database performance
- Maintain proper chronological ordering for trail drawing
- Use LiveView's efficient update mechanisms for smooth user experience

Performance improvements:
- Faster initial load with immediate visual feedback
- Reduced memory pressure through smaller batch sizes
- Better caching with automatic cache invalidation
- Smooth, non-blocking UI updates using requestAnimationFrame

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-09 09:08:10 -05:00
41eaec5c8e
add user auth 2025-07-09 08:53:50 -05:00
7168448a38
fix weather page 2025-07-08 13:21:02 -05:00