# HTTP Security Headers Analyzer (`andok/security-headers-analyzer`) Actor

Audit HTTP response headers (CSP, HSTS, X-Frame-Options) to verify web application security and compliance standards.

- **URL**: https://apify.com/andok/security-headers-analyzer.md
- **Developed by:** [Andok](https://apify.com/andok) (community)
- **Categories:** Business, Developer tools
- **Features:** Limited permissions
- **Stats:** 4 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $0.47 / 1,000 url scans

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.
Since this Actor supports Apify Store discounts, the price gets lower the higher subscription plan you have.

Learn more: https://docs.apify.com/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

An Actor is a serverless cloud program that runs on the Apify platform. It has two run modes.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.

Apify vocabulary and the platform model are defined once, in the agent quickstart at https://apify.com/agents.md.

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.

Do not guess an integration path. Every one of them is in the agent quickstart at https://apify.com/agents.md: the Apify MCP server, Agent Skills with the Apify CLI, the JavaScript and Python clients, the REST API, and the account-free path for an agent with no human to sign in. It also carries the rule on stating cost before the first paid run.

For examples already wired to this Actor's own input schema, see the [API](#api) section below.

Each client library has reference documentation the quickstart does not restate: [JavaScript/TypeScript](https://docs.apify.com/api/client/js/docs.md) (`npm install apify-client`) and [Python](https://docs.apify.com/api/client/python/docs.md) (`pip install apify-client`).

# README

## Security Headers Analyzer

Audit HTTP security headers against OWASP best practices across hundreds of URLs in a single run. Missing headers like HSTS, CSP, and X-Frame-Options are the most common findings in penetration tests — yet most teams only discover them after an incident. Scan your entire domain inventory in minutes with automatic grading from A to F.

### Features

- **OWASP header checks** — validates HSTS, CSP, X-Frame-Options, X-Content-Type-Options, Referrer-Policy, Permissions-Policy, COOP, CORP, and COEP
- **Automatic grading** — assigns a score (0-100) and letter grade (A-F) based on header coverage and configuration quality
- **Actionable warnings** — flags weak configurations like `unsafe-inline` in CSP or missing `max-age` in HSTS
- **Bulk processing** — scan hundreds of URLs concurrently in a single run
- **Redirect-aware** — optionally follows redirects and reports the full redirect chain
- **Flexible HTTP method** — use HEAD for speed or GET for servers that block HEAD requests

### Input

| Field | Type | Required | Default | Description |
|-------|------|----------|---------|-------------|
| `urls` | `array` | No | `["https://google.com"]` | List of URLs to analyze for security headers |
| `url` | `string` | No | — | Single URL to analyze (use `urls` for bulk scanning) |
| `method` | `string` | No | `HEAD` | HTTP method to use. HEAD is faster; switch to GET if a server blocks HEAD requests |
| `followRedirects` | `boolean` | No | `true` | Whether to follow HTTP redirects before analyzing headers |
| `maxRedirects` | `integer` | No | `5` | Maximum number of redirects to follow per URL (0-20) |
| `timeoutSeconds` | `integer` | No | `15` | Request timeout per URL in seconds (1-120) |
| `concurrency` | `integer` | No | `5` | Number of URLs to process in parallel (1-25) |

#### Input Example

```json
{
  "urls": [
    "https://google.com",
    "https://github.com",
    "https://example.com"
  ],
  "method": "HEAD",
  "followRedirects": true,
  "concurrency": 10
}
```

### Output

Each URL produces one dataset record containing the security grade, score, list of missing and misconfigured headers, and all response headers for reference.

Key output fields:

- `inputUrl` (`string`) — the URL as submitted
- `finalUrl` (`string`) — the URL after redirects (if followed)
- `status` (`number`) — HTTP status code
- `grade` (`string`) — letter grade from A (excellent) to F (critical gaps)
- `score` (`number`) — numeric score from 0 to 100
- `missing` (`array`) — list of required headers that are absent
- `warnings` (`array`) — list of configuration issues found
- `headers` (`object`) — all response headers (lower-cased keys)
- `redirects` (`array`) — redirect chain traversed
- `checkedAt` (`string`) — ISO 8601 timestamp

#### Output Example

```json
{
  "inputUrl": "https://github.com",
  "finalUrl": "https://github.com/",
  "status": 200,
  "grade": "B",
  "score": 80,
  "missing": [
    "Referrer-Policy"
  ],
  "warnings": [
    "Missing Permissions-Policy.",
    "Missing Cross-Origin-Opener-Policy (COOP).",
    "Missing Cross-Origin-Resource-Policy (CORP).",
    "Missing Cross-Origin-Embedder-Policy (COEP)."
  ],
  "headers": {
    "strict-transport-security": "max-age=31536000; includeSubdomains; preload",
    "content-security-policy": "default-src 'none'; base-uri 'self'; ...",
    "x-frame-options": "deny",
    "x-content-type-options": "nosniff"
  },
  "redirects": ["https://github.com/"],
  "checkedAt": "2026-03-09T12:00:00.000Z"
}
```

### Pricing

| Event | Cost |
|-------|------|
| URL Scan | $0.001 |

Pay only for URLs successfully scanned. Respects your per-run spending limit.

### Use Cases

- **Penetration test prep** — pre-scan client domains to identify missing security headers before a full engagement
- **Compliance audits** — verify OWASP header requirements across all production endpoints for SOC 2 or ISO 27001
- **DevOps CI/CD checks** — schedule regular scans to catch header regressions after deployments
- **Agency security reports** — generate client-ready security grades for website portfolios
- **M\&A due diligence** — quickly assess the security posture of acquisition targets

### Related Actors

| Actor | What it adds |
|-------|-------------|
| [SSL Cipher Checker](https://apify.com/andok/ssl-cipher-checker) | Audit TLS cipher suites and protocol versions alongside header analysis |
| [SSL Certificate Monitor](https://apify.com/andok/ssl-certificate-monitor) | Monitor certificate expiry dates to complement header-level security checks |
| [Tech Stack Analyzer](https://apify.com/andok/tech-stack-analyzer) | Identify the CMS, frameworks, and CDNs behind each scanned URL |

# Actor input Schema

## `urls` (type: `array`):

List of URLs to analyze for security headers. Each URL will be checked for HSTS, CSP, X-Frame-Options, and other OWASP-recommended headers.

## `url` (type: `string`):

Single URL to analyze. Use the URLs field above for bulk scanning.

## `followRedirects` (type: `boolean`):

Whether to follow HTTP redirects before analyzing headers. Enable this to check the final destination rather than the initial response.

## `maxRedirects` (type: `integer`):

Maximum number of redirects to follow per URL. Increase if your URLs pass through multiple CDN or load balancer hops.

## `timeoutSeconds` (type: `integer`):

Request timeout per URL in seconds. Increase for slow-responding servers or high-latency targets.

## `concurrency` (type: `integer`):

Number of URLs to scan in parallel. Higher values speed up large batches but may trigger rate limiting.

## `method` (type: `string`):

HTTP method for requests. HEAD is faster and sufficient for most servers. Switch to GET if a server returns different headers for HEAD requests.

## Actor input object example

```json
{
  "urls": [
    "https://google.com"
  ],
  "followRedirects": true,
  "maxRedirects": 5,
  "timeoutSeconds": 15,
  "concurrency": 5,
  "method": "HEAD"
}
```

# Actor output Schema

## `results` (type: `string`):

No description

## `resultsCsv` (type: `string`):

No description

## `run` (type: `string`):

No description

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "urls": [
        "https://google.com"
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("andok/security-headers-analyzer").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = { "urls": ["https://google.com"] }

# Run the Actor and wait for it to finish
run = client.actor("andok/security-headers-analyzer").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "urls": [
    "https://google.com"
  ]
}' |
apify call andok/security-headers-analyzer --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,andok/security-headers-analyzer"
        }
    }
}
```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/42iIFB509DoEhKlgl/builds/RzIh6fuGqTUddIsQY/openapi.json
