Some checks failed
Deploy to Phoenix / deploy (push) Has been cancelled
- ADD_CHAIN138_TO_LEDGER_LIVE: Ledger form done; public code review repo bis-innovations/LedgerLive; init/push commands - CONTRACT_DEPLOYMENT_RUNBOOK: Chain 138 gas price 1 gwei, 36-addr check, TransactionMirror workaround - CONTRACT_*: AddressMapper, MirrorManager deployed 2026-02-12; 36-address on-chain check - NEXT_STEPS_FOR_YOU: Ledger done; steps completable now (no LAN); run-completable-tasks-from-anywhere - MASTER_INDEX, OPERATOR_OPTIONAL, SMART_CONTRACTS_INVENTORY_SIMPLE: updates - LEDGER_BLOCKCHAIN_INTEGRATION_COMPLETE: bis-innovations/LedgerLive reference Co-authored-by: Cursor <cursoragent@cursor.com>
256 lines
8.6 KiB
Bash
Executable File
256 lines
8.6 KiB
Bash
Executable File
#!/usr/bin/env bash
|
|
# Verify UDM Pro port forwarding configuration
|
|
# Documents manual steps and tests internal connectivity to NPMplus
|
|
|
|
set -euo pipefail
|
|
|
|
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
|
PROJECT_ROOT="$(cd "$SCRIPT_DIR/../.." && pwd)"
|
|
EVIDENCE_DIR="$PROJECT_ROOT/docs/04-configuration/verification-evidence"
|
|
|
|
# Colors
|
|
RED='\033[0;31m'
|
|
GREEN='\033[0;32m'
|
|
YELLOW='\033[1;33m'
|
|
BLUE='\033[0;34m'
|
|
CYAN='\033[0;36m'
|
|
NC='\033[0m'
|
|
|
|
log_info() { echo -e "${BLUE}[INFO]${NC} $1"; }
|
|
log_success() { echo -e "${GREEN}[✓]${NC} $1"; }
|
|
log_warn() { echo -e "${YELLOW}[⚠]${NC} $1"; }
|
|
log_error() { echo -e "${RED}[✗]${NC} $1"; }
|
|
|
|
cd "$PROJECT_ROOT"
|
|
|
|
TIMESTAMP=$(date +%Y%m%d_%H%M%S)
|
|
OUTPUT_DIR="$EVIDENCE_DIR/udm-pro-verification-$TIMESTAMP"
|
|
mkdir -p "$OUTPUT_DIR"
|
|
|
|
PUBLIC_IP="${PUBLIC_IP:-76.53.10.36}"
|
|
NPMPLUS_IP="${NPMPLUS_IP:-192.168.11.166}"
|
|
|
|
echo ""
|
|
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
|
|
echo "🔍 UDM Pro Port Forwarding Verification"
|
|
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
|
|
echo ""
|
|
|
|
log_info "Expected Configuration:"
|
|
echo " Public IP: $PUBLIC_IP"
|
|
echo " NPMplus Internal IP: $NPMPLUS_IP"
|
|
echo " Rule 1: $PUBLIC_IP:443 → $NPMPLUS_IP:443 (TCP)"
|
|
echo " Rule 2: $PUBLIC_IP:80 → $NPMPLUS_IP:80 (TCP)"
|
|
echo ""
|
|
|
|
# Test internal connectivity
|
|
log_info "Testing internal connectivity to NPMplus..."
|
|
|
|
HTTP_TEST=false
|
|
HTTPS_TEST=false
|
|
|
|
if curl -s -I --connect-timeout 5 "http://$NPMPLUS_IP:80" > "$OUTPUT_DIR/internal_http_test.txt" 2>&1; then
|
|
HTTP_CODE=$(head -1 "$OUTPUT_DIR/internal_http_test.txt" | grep -oP '\d{3}' | head -1 || echo "")
|
|
if [ -n "$HTTP_CODE" ]; then
|
|
HTTP_TEST=true
|
|
log_success "HTTP connectivity: $NPMPLUS_IP:80 responded with HTTP $HTTP_CODE"
|
|
else
|
|
log_warn "HTTP connectivity: $NPMPLUS_IP:80 responded but couldn't parse status"
|
|
fi
|
|
else
|
|
log_error "HTTP connectivity: Failed to connect to $NPMPLUS_IP:80"
|
|
fi
|
|
|
|
if curl -s -I -k --connect-timeout 5 "https://$NPMPLUS_IP:443" > "$OUTPUT_DIR/internal_https_test.txt" 2>&1; then
|
|
HTTPS_CODE=$(head -1 "$OUTPUT_DIR/internal_https_test.txt" | grep -oP '\d{3}' | head -1 || echo "")
|
|
if [ -n "$HTTPS_CODE" ]; then
|
|
HTTPS_TEST=true
|
|
log_success "HTTPS connectivity: $NPMPLUS_IP:443 responded with HTTP $HTTPS_CODE"
|
|
else
|
|
log_warn "HTTPS connectivity: $NPMPLUS_IP:443 responded but couldn't parse status"
|
|
fi
|
|
else
|
|
log_error "HTTPS connectivity: Failed to connect to $NPMPLUS_IP:443"
|
|
fi
|
|
|
|
# Test public IP reachability (from external, if possible)
|
|
log_info ""
|
|
log_info "Testing public IP reachability..."
|
|
|
|
PUBLIC_HTTP_TEST=false
|
|
PUBLIC_HTTPS_TEST=false
|
|
|
|
if curl -s -I --connect-timeout 5 "http://$PUBLIC_IP:80" > "$OUTPUT_DIR/public_http_test.txt" 2>&1; then
|
|
HTTP_CODE=$(head -1 "$OUTPUT_DIR/public_http_test.txt" | grep -oP '\d{3}' | head -1 || echo "")
|
|
if [ -n "$HTTP_CODE" ]; then
|
|
PUBLIC_HTTP_TEST=true
|
|
log_success "Public HTTP: $PUBLIC_IP:80 responded with HTTP $HTTP_CODE"
|
|
else
|
|
log_warn "Public HTTP: $PUBLIC_IP:80 responded but couldn't parse status"
|
|
fi
|
|
else
|
|
log_warn "Public HTTP: Cannot test from internal network (expected)"
|
|
fi
|
|
|
|
if curl -s -I -k --connect-timeout 5 "https://$PUBLIC_IP:443" > "$OUTPUT_DIR/public_https_test.txt" 2>&1; then
|
|
HTTPS_CODE=$(head -1 "$OUTPUT_DIR/public_https_test.txt" | grep -oP '\d{3}' | head -1 || echo "")
|
|
if [ -n "$HTTPS_CODE" ]; then
|
|
PUBLIC_HTTPS_TEST=true
|
|
log_success "Public HTTPS: $PUBLIC_IP:443 responded with HTTP $HTTPS_CODE"
|
|
else
|
|
log_warn "Public HTTPS: $PUBLIC_IP:443 responded but couldn't parse status"
|
|
fi
|
|
else
|
|
log_warn "Public HTTPS: Cannot test from internal network (expected)"
|
|
fi
|
|
|
|
# Generate verification results JSON
|
|
cat > "$OUTPUT_DIR/verification_results.json" <<EOF
|
|
{
|
|
"timestamp": "$(date -Iseconds)",
|
|
"verifier": "$(whoami)",
|
|
"expected_configuration": {
|
|
"public_ip": "$PUBLIC_IP",
|
|
"npmplus_internal_ip": "$NPMPLUS_IP",
|
|
"port_forwarding_rules": [
|
|
{
|
|
"name": "NPMplus HTTPS",
|
|
"public_ip": "$PUBLIC_IP",
|
|
"public_port": 443,
|
|
"internal_ip": "$NPMPLUS_IP",
|
|
"internal_port": 443,
|
|
"protocol": "TCP",
|
|
"status": "$([ "$HTTP_TEST" = true ] && echo "verified" || echo "documented")",
|
|
"verified_at": "$(date -Iseconds)"
|
|
},
|
|
{
|
|
"name": "NPMplus HTTP",
|
|
"public_ip": "$PUBLIC_IP",
|
|
"public_port": 80,
|
|
"internal_ip": "$NPMPLUS_IP",
|
|
"internal_port": 80,
|
|
"protocol": "TCP",
|
|
"status": "$([ "$HTTPS_TEST" = true ] && echo "verified" || echo "documented")",
|
|
"verified_at": "$(date -Iseconds)"
|
|
}
|
|
]
|
|
},
|
|
"test_results": {
|
|
"internal_http": $HTTP_TEST,
|
|
"internal_https": $HTTPS_TEST,
|
|
"public_http": $PUBLIC_HTTP_TEST,
|
|
"public_https": $PUBLIC_HTTPS_TEST
|
|
},
|
|
"note": "UDM Pro port forwarding requires manual verification via web UI"
|
|
}
|
|
EOF
|
|
|
|
# Generate markdown report
|
|
REPORT_FILE="$OUTPUT_DIR/verification_report.md"
|
|
cat > "$REPORT_FILE" <<EOF
|
|
# UDM Pro Port Forwarding Verification Report
|
|
|
|
**Date**: $(date -Iseconds)
|
|
**Verifier**: $(whoami)
|
|
|
|
## Expected Configuration
|
|
|
|
| Rule | Public IP:Port | Internal IP:Port | Protocol |
|
|
|------|----------------|------------------|----------|
|
|
| NPMplus HTTPS | $PUBLIC_IP:443 | $NPMPLUS_IP:443 | TCP |
|
|
| NPMplus HTTP | $PUBLIC_IP:80 | $NPMPLUS_IP:80 | TCP |
|
|
|
|
## Test Results
|
|
|
|
| Test | Result | Details |
|
|
|------|--------|---------|
|
|
| Internal HTTP | $([ "$HTTP_TEST" = true ] && echo "✅ Pass" || echo "❌ Fail") | Connection to $NPMPLUS_IP:80 |
|
|
| Internal HTTPS | $([ "$HTTPS_TEST" = true ] && echo "✅ Pass" || echo "❌ Fail") | Connection to $NPMPLUS_IP:443 |
|
|
| Public HTTP | $([ "$PUBLIC_HTTP_TEST" = true ] && echo "✅ Pass" || echo "⚠️ Cannot test from internal") | Connection to $PUBLIC_IP:80 |
|
|
| Public HTTPS | $([ "$PUBLIC_HTTPS_TEST" = true ] && echo "✅ Pass" || echo "⚠️ Cannot test from internal") | Connection to $PUBLIC_IP:443 |
|
|
|
|
## Manual Verification Steps
|
|
|
|
Since UDM Pro doesn't have a public API for port forwarding configuration, manual verification is required:
|
|
|
|
### Step 1: Access UDM Pro Web Interface
|
|
|
|
1. Open web browser
|
|
2. Navigate to UDM Pro web interface (typically \`https://192.168.0.1\` or your UDM Pro IP)
|
|
3. Log in with admin credentials
|
|
|
|
### Step 2: Navigate to Port Forwarding
|
|
|
|
1. Click **Settings** (gear icon)
|
|
2. Go to **Firewall & Security** (or **Networks**)
|
|
3. Click **Port Forwarding** (or **Port Forwarding Rules**)
|
|
|
|
### Step 3: Verify Rules
|
|
|
|
Verify the following rules exist:
|
|
|
|
**Rule 1: NPMplus HTTPS**
|
|
- Name: NPMplus HTTPS (or similar)
|
|
- Source: Any (or specific IP if configured)
|
|
- Destination IP: **$PUBLIC_IP**
|
|
- Destination Port: **443**
|
|
- Forward to IP: **$NPMPLUS_IP**
|
|
- Forward to Port: **443**
|
|
- Protocol: **TCP**
|
|
- Interface: WAN
|
|
|
|
**Rule 2: NPMplus HTTP**
|
|
- Name: NPMplus HTTP (or similar)
|
|
- Source: Any (or specific IP if configured)
|
|
- Destination IP: **$PUBLIC_IP**
|
|
- Destination Port: **80**
|
|
- Forward to IP: **$NPMPLUS_IP**
|
|
- Forward to Port: **80**
|
|
- Protocol: **TCP**
|
|
- Interface: WAN
|
|
|
|
### Step 4: Capture Evidence
|
|
|
|
1. Take screenshot of port forwarding rules page
|
|
2. Save screenshot as: \`$OUTPUT_DIR/udm-pro-port-forwarding-screenshot.png\`
|
|
3. Export UDM Pro config (if available): Settings → Maintenance → Download Backup
|
|
|
|
## Troubleshooting
|
|
|
|
### Internal connectivity fails
|
|
|
|
- Verify NPMplus container is running: \`pct status 10233\`
|
|
- Verify NPMplus is listening on ports 80/443
|
|
- Check firewall rules on Proxmox host
|
|
- Verify NPMplus IP address is correct
|
|
|
|
### Public IP not reachable
|
|
|
|
- Verify UDM Pro WAN IP matches $PUBLIC_IP
|
|
- Check UDM Pro firewall rules (allow inbound traffic)
|
|
- Verify port forwarding rules are enabled
|
|
- Check ISP firewall/blocking
|
|
|
|
## Files Generated
|
|
|
|
- \`verification_results.json\` - Test results and expected configuration
|
|
- \`internal_http_test.txt\` - Internal HTTP test output
|
|
- \`internal_https_test.txt\` - Internal HTTPS test output
|
|
- \`public_http_test.txt\` - Public HTTP test output (if accessible)
|
|
- \`public_https_test.txt\` - Public HTTPS test output (if accessible)
|
|
- \`verification_report.md\` - This report
|
|
|
|
## Next Steps
|
|
|
|
1. Complete manual verification via UDM Pro web UI
|
|
2. Take screenshots of port forwarding rules
|
|
3. Update verification_results.json with manual verification status
|
|
4. Update source-of-truth JSON after verification
|
|
EOF
|
|
|
|
log_info ""
|
|
log_info "Verification complete!"
|
|
log_success "Report: $REPORT_FILE"
|
|
log_info "Note: Manual verification via UDM Pro web UI is required"
|
|
log_info "Take screenshots and save to: $OUTPUT_DIR/"
|