5.6 KiB
RFCP Iteration 1.5.1: Fixes & Boundaries
Date: January 31, 2025
Type: Bugfix & Polish
Estimated: 2-3 hours
Location: /opt/rfcp/frontend/ + /opt/rfcp/backend/
🎯 Goal
Fix Fresnel endpoint 500 error, restore coverage boundary visualization, minor polish.
🐛 Issues to Fix
1. Fresnel Endpoint 500 Error
Symptom:
curl "/api/terrain/fresnel?tx_lat=48.46&tx_lon=35.05&tx_height=30&rx_lat=48.47&rx_lon=35.06&rx_height=1.5&frequency=1800"
# Returns: 500 Internal Server Error
Location: backend/app/api/routes/terrain.py
Likely cause: Missing rx_height default or async issue in los_service.check_fresnel_clearance()
Fix:
@router.get("/fresnel")
async def check_fresnel(
tx_lat: float,
tx_lon: float,
tx_height: float,
rx_lat: float,
rx_lon: float,
rx_height: float = 1.5, # Default receiver height
frequency: float = 1800 # Default frequency MHz
):
try:
result = await los_service.check_fresnel_clearance(
tx_lat, tx_lon, tx_height,
rx_lat, rx_lon, rx_height,
frequency
)
return result
except Exception as e:
raise HTTPException(500, f"Fresnel calculation error: {str(e)}")
Debug: Check backend logs for actual error:
journalctl -u rfcp-backend -n 50 | grep -i error
2. Coverage Boundary Not Showing
Symptom: Boundary contour line (-100 dBm) not visible on map after API integration
Location: frontend/src/components/map/CoverageBoundary.tsx
Likely cause: Component expecting old data format, not new API response
Check:
- Is
CoverageBoundarystill mounted in map? - Does it receive
pointsfrom coverage store? - Is boundary calculation using correct field (
rsrpvs old field name)?
Fix approach:
// CoverageBoundary.tsx
import { useCoverageStore } from '../../store/coverage';
export function CoverageBoundary() {
const { points, settings } = useCoverageStore();
// Generate boundary from API points
const boundaryPoints = useMemo(() => {
if (!points.length) return [];
// Filter points near threshold
const threshold = settings.min_signal; // -100 dBm
const tolerance = 5; // ±5 dBm
return points
.filter(p => Math.abs(p.rsrp - threshold) < tolerance)
.map(p => [p.lat, p.lon] as [number, number]);
}, [points, settings.min_signal]);
// ... rest of boundary rendering
}
Alternative: Use convex hull or marching squares for proper contour:
import { concaveman } from 'concaveman';
const boundaryPolygon = useMemo(() => {
const edgePoints = points
.filter(p => p.rsrp >= settings.min_signal && p.rsrp < settings.min_signal + 10)
.map(p => [p.lon, p.lat]);
if (edgePoints.length < 3) return null;
return concaveman(edgePoints, 2); // concavity factor
}, [points, settings.min_signal]);
3. Minor Polish
a) Stats panel — show models used:
// StatsPanel.tsx
{lastCalculation && (
<div className="models-used">
<span className="label">Models:</span>
<div className="model-tags">
{lastCalculation.models.map(m => (
<span key={m} className="model-tag">{m}</span>
))}
</div>
</div>
)}
b) Loading state during long calculations:
// Show elapsed time during calculation
const [elapsed, setElapsed] = useState(0);
useEffect(() => {
if (!isCalculating) {
setElapsed(0);
return;
}
const start = Date.now();
const interval = setInterval(() => {
setElapsed(Math.floor((Date.now() - start) / 1000));
}, 1000);
return () => clearInterval(interval);
}, [isCalculating]);
// In render:
{isCalculating && (
<div className="calculating-status">
Calculating... {elapsed}s
</div>
)}
c) Error toast for API failures:
// In coverage store calculateCoverage()
catch (error) {
const message = error instanceof Error ? error.message : 'Calculation failed';
toast.error(message); // If using toast library
set({ error: message, isCalculating: false });
}
✅ Tasks
- Fix Fresnel endpoint (backend)
- Debug and check logs for actual error
- Restore CoverageBoundary with API points
- Test boundary renders correctly
- Add elapsed time counter during calculation
- Add model tags to stats panel
- Test all presets still work
- Run integration test — should be 21/21
🧪 Testing
# 1. Test Fresnel fix
curl "https://api.rfcp.eliah.one/api/terrain/fresnel?tx_lat=48.46&tx_lon=35.05&tx_height=30&rx_lat=48.47&rx_lon=35.06&rx_height=1.5&frequency=1800"
# Should return: {"clearance_percent": ..., "has_adequate_clearance": ...}
# 2. Run integration test
./rfcp-integration-test.sh
# Should be 21/21
# 3. Visual test
# - Calculate coverage
# - Verify boundary line appears at -100 dBm edge
# - Verify elapsed time shows during calculation
📁 Files to Modify
backend/app/
├── api/routes/terrain.py # Fresnel fix
└── services/los_service.py # Check fresnel method
frontend/src/
├── components/
│ ├── map/CoverageBoundary.tsx # Fix boundary rendering
│ └── panels/
│ ├── CoverageStats.tsx # Add model tags
│ └── StatsPanel.tsx # Elapsed time
└── store/coverage.ts # Error handling
📝 Notes
- Boundary can use simple edge detection or proper contour algorithm
concavemanis lightweight (~2KB) for concave hull- Elapsed time helps user know calculation is progressing
Quick iteration — should be fast 🚀