Skip to main content

Server Disclosure.

Security Headers & TLS Config

Exposed server version helps attackers target known vulnerabilities

What does this check test?

Server disclosure occurs when HTTP response headers like `Server`, `X-Powered-By`, `X-AspNet-Version`, or `X-Generator` reveal the web server software, version number, or application framework in use. For example, `Server: Apache/2.4.51 (Ubuntu)` or `X-Powered-By: Express` tells an attacker exactly what technology stack is running. This information is sent by default in most server configurations and provides no value to legitimate users.

Why does it matter?

Knowing the exact server software and version allows attackers to search for known CVEs and exploit code specific to that version. An `Apache/2.4.49` disclosure immediately points to the path traversal vulnerability CVE-2021-41773. Removing version information forces attackers to spend time fingerprinting your stack, which increases the cost of an attack and may cause automated scanners to skip your site. While security through obscurity is not a primary defense, it is a valuable layer in defense-in-depth.

Who is affected?

Every production web server should minimize information disclosure. This is especially important for organizations that cannot patch immediately when new vulnerabilities are discovered, as the disclosed version makes them obvious targets for automated scanning. Compliance frameworks like PCI DSS explicitly require removal of unnecessary server information.

Where does this apply?

Check the `Server`, `X-Powered-By`, `X-AspNet-Version`, `X-Generator`, and `X-Drupal-Cache` headers in your HTTP responses. These are typically set by the web server, application framework, or CMS. Also check HTML meta tags and comments for generator information. Inspect responses using `curl -sI https://yoursite.com`.

How to fix it

Nginx, remove version from the Server header

nginx
server_tokens off;

Apache

apache
ServerTokens Prod
ServerSignature Off

Node.js / Express

js
app.disable('x-powered-by');
// Or use helmet which does this automatically:
app.use(helmet());

Django — Django does not set a `Server` header, but your WSGI server (Gunicorn, uWSGI) might. For Gunicorn

python
# gunicorn.conf.py
server_tokens = False  # Gunicorn does not expose version by default
For Flask — Flask does not add server disclosure headers, but Werkzeug sets `Server: Werkzeug/x.x.x`. In production, use a proper WSGI server behind Nginx.

Next.js — disable the `X-Powered-By: Next.js` header

js
// next.config.js
module.exports = {
  poweredByHeader: false
};

Spring Boot

java
server.server-header=
server.error.include-message=never

PHP, disable `expose_php` in `php.ini`

expose_php = Off
Some CDNs (Cloudflare, Fastly) can strip these headers at the edge. After making changes, verify with `curl -sI https://yoursite.com` and confirm no version information appears.

References

AppVet checks Server Disclosure automatically

Run a free security scan and get a full report with actionable fixes, including a Fix with AI prompt you can paste into any coding tool.

Run Audit