Reconnaissance & Fingerprinting
WSTG-INFO-01 through WSTG-INFO-10
Goalβ
Before touching the application itself, build a complete picture of what you're dealing with: what's running, what version, what technology stack, what's exposed, and whether there's a WAF in the way. Every fact gathered here shapes every decision you make later.
Port Scanning - Find All Web Servicesβ
Don't assume only 80 and 443. Developers run staging servers, admin panels, API gateways, and debug interfaces on non-standard ports constantly.
# Quick scan of common web ports
nmap -sV -p 80,443,8080,8443,8888,8000,8008,8081,9090,9200,5000,3000,4848 <TARGET>
# Full port scan to catch everything
nmap -sV -p- --min-rate 1000 <TARGET>
# Web-focused NSE scripts - grab title, headers, methods, server info
nmap -sV -p 80,443 --script http-title,http-headers,http-methods,http-server-header,http-auth-finder <TARGET>
# SSL certificate enumeration - SANs often reveal internal hostnames and subdomains
nmap -p 443 --script ssl-cert,ssl-enum-ciphers <TARGET>
SANs are intelligence goldmines. A certificate's Subject Alternative Names field lists every domain the cert is valid for. Internal hostnames like dev.internal.corp, admin.app.com, and staging environments regularly appear here. Note all of them for follow-up.
Notable non-standard ports to knowβ
| Port | Common Service | Why It Matters |
|---|---|---|
| 8080/8443 | Tomcat, dev servers, proxies | Often runs without WAF; admin at /manager/html |
| 9200/9300 | Elasticsearch | Frequently unauthenticated - full database access |
| 27017 | MongoDB | Frequently unauthenticated |
| 6379 | Redis | Often unauthenticated; command execution possible |
| 4848 | GlassFish admin | Default creds common |
| 5601 | Kibana | Often exposes internal data |
| 3000 | Node.js/Grafana | Dev servers, API backends |
| 5000 | Flask/Python dev server | Dev servers almost never hardened |
Technology Fingerprintingβ
Knowing the tech stack tells you which vulnerability classes are most likely and which tools to use. A PHP app on Apache is attacked differently than a Java app on Tomcat or a .NET app on IIS.
whatweb - Automated tech fingerprintingβ
# Standard fingerprint
whatweb http://target.com
# Aggressive mode - follow redirects, more probes
whatweb -a 3 http://target.com
# Quiet output - just the findings
whatweb -q http://target.com
# Log to file
whatweb http://target.com -o whatweb-output.txt
whatweb identifies: CMS (WordPress, Drupal, Joomla), frameworks (Laravel, Django, Rails, ASP.NET), web servers (Apache, nginx, IIS), JavaScript libraries, analytics, CDNs, and version numbers.
Manual HTTP header inspection with curlβ
Headers often reveal what whatweb misses or confirm its findings:
# Grab headers only - the most informative first look at any web app
curl -sI http://target.com
# Follow redirects and show headers at each hop
curl -sIL http://target.com
# Include response body for further analysis
curl -si http://target.com | head -100
# Custom User-Agent (evade simple bot detection)
curl -sI -A "Mozilla/5.0 (Windows NT 10.0; Win64; x64)" http://target.com
# Force HTTP/1.1 (some servers behave differently)
curl -sI --http1.1 http://target.com
Headers to focus on:
| Header | What It Reveals |
|---|---|
Server | Web server type and version (e.g., Apache/2.4.29) |
X-Powered-By | Backend language/framework (e.g., PHP/7.4.3, ASP.NET) |
X-Generator | CMS (e.g., Drupal 9) |
X-AspNet-Version | .NET version |
X-AspNetMvc-Version | ASP.NET MVC version |
X-Frame-Options | Missing = potential clickjacking |
Content-Security-Policy | Absent/weak = XSS may be easier |
Set-Cookie | Session token format, cookie flags (Secure/HttpOnly/SameSite) |
Access-Control-Allow-Origin: * | Overly permissive CORS - potential credential exposure |
Location | Redirect target - may leak internal URLs |
Version numbers in headers are direct vulnerability research targets. Apache/2.4.29 β search for CVEs for that exact version. Same for PHP, nginx, IIS, and framework versions.
SSL/TLS analysisβ
# sslscan - check cipher suites, protocols, certificate details
sslscan https://target.com
# testssl.sh - comprehensive TLS analysis
testssl.sh https://target.com
# Quick cert check with openssl
echo | openssl s_client -connect target.com:443 2>/dev/null | openssl x509 -noout -text | grep -A5 "Subject Alternative"
Check for: expired cert, self-signed cert, weak ciphers (RC4, DES, export-grade), SSLv3/TLS 1.0 support (deprecated), and mismatched Common Name.
WAF Detectionβ
Identify whether a Web Application Firewall is present before running any aggressive tools. A WAF changes your entire approach - aggressive scanning gets you blocked.
# wafw00f - primary WAF detection tool
wafw00f http://target.com
# Verbose output
wafw00f -v http://target.com
# Test with a known attack payload to see WAF response
wafw00f -a http://target.com
wafw00f identifies 150+ WAF products including Cloudflare, Akamai, AWS WAF, F5, Barracuda, Imperva, ModSecurity.
If a WAF is detected:
- Prefer manual testing with clean, single-probe requests over automated scans
- Use
--tamperscripts in sqlmap (see injection section) - Use case variation, encoding, and fragmentation to bypass signature-based rules
- Be aware that some WAFs log and block at the IP level - triggering it once may blacklist you
Manual WAF probe:
# Send a basic XSS payload - see if it's blocked vs. reflected
curl -si "http://target.com/search?q=<script>alert(1)</script>" | head -20
# Check response code: 200 = no WAF or bypass; 403/406 = WAF blocking; 302 = redirect to WAF page
Passive Information Sourcesβ
These generate no traffic to the target - useful for initial mapping before touching anything.
# robots.txt - explicitly lists paths the site owner doesn't want crawled
curl http://target.com/robots.txt
# sitemap.xml - full URL listing of the application
curl http://target.com/sitemap.xml
# security.txt - sometimes lists contacts, policies, even internal bug trackers
curl http://target.com/.well-known/security.txt
robots.txt is not a security control - it's a disclosure document. Entries under Disallow: tell you exactly where the interesting paths are: admin panels, API endpoints, private directories, and backup locations. Always check it first.
Certificate Transparency Logsβ
Discover subdomains without sending any traffic to the target:
# Query crt.sh for all certificates issued for a domain
curl -s "https://crt.sh/?q=%.target.com&output=json" | jq '.[].name_value' | sort -u
This returns every subdomain that has ever had a certificate issued - including dev, staging, internal, and API subdomains that aren't publicly advertised.
HTML Source and JavaScript Analysisβ
This is manual work, but it consistently finds attack surface that no tool will.
# Download a page and search for interesting content
curl -s http://target.com | grep -iE "(api|key|token|secret|password|admin|debug|config|TODO|FIXME|internal)"
# Find all linked JS files
curl -s http://target.com | grep -oP 'src="[^"]+\.js[^"]*"' | sort -u
# Download and analyze a JS file
curl -s http://target.com/static/app.js | grep -iE "(api|endpoint|url|host|key|token|secret)"
What to look for in JavaScript:
- API endpoint paths (
/api/v1/users,/internal/admin) - Environment variables or config embedded in the bundle
- API keys, tokens, or credentials left in frontend code
- Internal hostnames or IP addresses
- Commented-out debug endpoints or old API versions
What to look for in HTML source:
<!-- TODO: remove before prod -->style comments- Hidden form fields (
<input type="hidden" name="role" value="user">) - try changing the value - Disabled form inputs - they often still get processed server-side
- Internal links that aren't visible in the UI
Error Page Analysisβ
Deliberately trigger error conditions to extract information:
# 404 - what framework info leaks?
curl -si http://target.com/doesnotexist404xyz
# 500 - provoke a server error with malformed input
curl -si "http://target.com/api/user?id='"
# Method not allowed
curl -si -X DELETE http://target.com/index.php
Error pages often reveal: web server version, framework name and version, full file paths on the server, database error messages (which confirm SQLi vectors), and stack traces showing internal function names.
Fingerprinting Summary: What You Should Know Before Moving Onβ
Before proceeding past recon, you should be able to answer:
- What web server and version is running on each port?
- What backend language/framework is the application built on?
- Is there a CMS? Which one and what version?
- Is there a WAF? Which product?
- What does the SSL certificate reveal about the infrastructure?
- What subdomains exist?
- What does robots.txt disclose?
- What do JS files and HTML source reveal about the application structure?
- What session cookie format is used, and what flags are set?