#!/bin/bash # capture-upload.sh - Capture from USB webcam and upload to PicUpper # For Raspberry Pi 3 with Logitech USB webcam set -euo pipefail SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" CONFIG_FILE="${SCRIPT_DIR}/picupper.conf" # ============================================================================== # Load Configuration # ============================================================================== if [[ ! -f "$CONFIG_FILE" ]]; then echo "ERROR: Configuration file not found: $CONFIG_FILE" echo "Please copy picupper.conf.example to picupper.conf and configure it." exit 1 fi # shellcheck source=/dev/null source "$CONFIG_FILE" # Validate required settings if [[ -z "${API_KEY:-}" || "$API_KEY" == "your-api-key-here" ]]; then echo "ERROR: API_KEY not configured in $CONFIG_FILE" exit 1 fi # Set defaults for optional settings API_URL="${API_URL:-https://dev.seedheads.de/picUploadApi/upload}" CAMERA_ID="${CAMERA_ID:-rpi-webcam}" VIDEO_DEVICE="${VIDEO_DEVICE:-/dev/video0}" RESOLUTION="${RESOLUTION:-1920x1080}" SKIP_FRAMES="${SKIP_FRAMES:-5}" TEMP_DIR="${TEMP_DIR:-/tmp}" LOG_FILE="${LOG_FILE:-/var/log/picupper.log}" TIMEOUT="${TIMEOUT:-30}" MAX_RETRIES="${MAX_RETRIES:-3}" RETRY_DELAY="${RETRY_DELAY:-5}" # ============================================================================== # Helper Functions # ============================================================================== log() { local timestamp timestamp=$(date '+%Y-%m-%d %H:%M:%S') local msg="[$timestamp] $*" echo "$msg" echo "$msg" >> "$LOG_FILE" 2>/dev/null || true } log_error() { log "ERROR: $*" >&2 } cleanup() { rm -f "${TEMP_FILE:-}" 2>/dev/null || true } trap cleanup EXIT # ============================================================================== # Test Mode # ============================================================================== if [[ "${1:-}" == "--test" ]]; then echo "=== PicUpper Test Mode ===" echo "Config file: $CONFIG_FILE" echo "API URL: $API_URL" echo "Camera ID: $CAMERA_ID" echo "Video device: $VIDEO_DEVICE" echo "Resolution: $RESOLUTION" echo "" # Check video device if [[ ! -e "$VIDEO_DEVICE" ]]; then echo "❌ Video device not found: $VIDEO_DEVICE" echo " Available devices:" ls -la /dev/video* 2>/dev/null || echo " No video devices found" exit 1 fi echo "✓ Video device exists: $VIDEO_DEVICE" # Check fswebcam if ! command -v fswebcam &>/dev/null; then echo "❌ fswebcam not installed. Run: sudo apt install fswebcam" exit 1 fi echo "✓ fswebcam installed" # Try capture TEST_FILE="${TEMP_DIR}/picupper_test_$(date +%s).jpg" echo "Capturing test image to: $TEST_FILE" if fswebcam -d "$VIDEO_DEVICE" -r "$RESOLUTION" -S "$SKIP_FRAMES" --no-banner "$TEST_FILE" 2>/dev/null; then FILE_SIZE=$(stat -f%z "$TEST_FILE" 2>/dev/null || stat -c%s "$TEST_FILE" 2>/dev/null) echo "✓ Capture successful: $TEST_FILE (${FILE_SIZE} bytes)" echo "" echo "To view the image: gpicview $TEST_FILE" else echo "❌ Capture failed. Check webcam connection and permissions." exit 1 fi exit 0 fi # ============================================================================== # Main Capture & Upload # ============================================================================== TEMP_FILE="${TEMP_DIR}/picupper_${CAMERA_ID}_$(date +%s).jpg" # Check video device if [[ ! -e "$VIDEO_DEVICE" ]]; then log_error "Video device not found: $VIDEO_DEVICE" exit 1 fi # Capture image log "Capturing from $VIDEO_DEVICE ($RESOLUTION)" if ! fswebcam -d "$VIDEO_DEVICE" -r "$RESOLUTION" -S "$SKIP_FRAMES" --no-banner "$TEMP_FILE" 2>/dev/null; then log_error "Capture failed" exit 1 fi FILE_SIZE=$(stat -c%s "$TEMP_FILE" 2>/dev/null || echo "unknown") log "Captured: $TEMP_FILE ($FILE_SIZE bytes)" # Upload with retry upload_success=false attempt=1 while [[ $attempt -le $MAX_RETRIES ]]; do log "Upload attempt $attempt/$MAX_RETRIES" HTTP_RESPONSE=$(curl -s -w "\n%{http_code}" \ --max-time "$TIMEOUT" \ -X POST \ -H "X-API-Key: $API_KEY" \ -F "image=@$TEMP_FILE" \ -F "cameraId=$CAMERA_ID" \ "$API_URL" 2>/dev/null) || true HTTP_CODE=$(echo "$HTTP_RESPONSE" | tail -n1) RESPONSE_BODY=$(echo "$HTTP_RESPONSE" | sed '$d') if [[ "$HTTP_CODE" == "200" ]]; then log "Upload successful (HTTP $HTTP_CODE)" upload_success=true break else log_error "Upload failed (HTTP $HTTP_CODE): $RESPONSE_BODY" if [[ $attempt -lt $MAX_RETRIES ]]; then log "Retrying in $RETRY_DELAY seconds..." sleep "$RETRY_DELAY" fi fi ((attempt++)) done if [[ "$upload_success" != "true" ]]; then log_error "All upload attempts failed" exit 1 fi log "Done"