# Host source (/en/docs/web-security/policies/content-security-policy/values/csp-host-source)



A host source is the most common kind of Content Security Policy (CSP) value: a
URL pattern that allows resources from a particular origin, such as
`https://cdn.example.com` or `*.example.com`. It is how you allowlist the third
parties a page may load script, images, fonts, or connections from. The matching
rules look simple but have edges that decide whether a real request is allowed,
so the details below matter.

A host source as you would ship it, one CDN allowed next to your own origin:

```http
Content-Security-Policy: img-src 'self' https://cdn.example.com
```

## Syntax [#syntax]

A host source is built from up to four optional parts: a scheme, a host, a port,
and a path.

```http
Content-Security-Policy: script-src https://cdn.example.com:443/assets/
```

The grammar, read left to right:

| Part          | Example           | Meaning                                                                                              |
| ------------- | ----------------- | ---------------------------------------------------------------------------------------------------- |
| Scheme        | `https://`        | Optional. If omitted, the page's own scheme is assumed, and an `http:` source also matches `https:`. |
| Host          | `cdn.example.com` | Required. A full host, or a leading `*.` wildcard for one subdomain level.                           |
| Wildcard host | `*.example.com`   | Matches any single subdomain prefix.                                                                 |
| Port          | `:443` or `:*`    | Optional. A specific port, or `:*` for any port. If omitted, the scheme's default port is used.      |
| Path          | `/assets/`        | Optional. Restricts to a path; a trailing `/` makes it a prefix match.                               |

The patterns you actually write fall into a few shapes, and they are not equally
safe.

| Pattern                   | Status  | Description                                                                      |
| ------------------------- | ------- | -------------------------------------------------------------------------------- |
| `https://cdn.example.com` | ✅ Good  | One specific host over HTTPS, the narrowest form of allowlisting.                |
| `*.example.com`           | ✅ Good  | Any subdomain of `example.com`, but not the apex `example.com` itself.           |
| `*`                       | ❌ Risky | Any host on a network scheme. In `script-src` it removes most of the protection. |

## What it matches [#what-it-matches]

A host source matches a request URL when the scheme, host, port, and path all
agree under these rules. The query string and fragment are never part of the
match, so `?v=2` or `#section` on a URL is ignored.

```http
Content-Security-Policy: img-src https://images.example.com
```

That allows `https://images.example.com/logo.png?cache=off` and any other path on
that exact host, because the query is ignored and no path was specified.

## Matching gotchas [#matching-gotchas]

These four behaviors cause most host-source surprises.

`*.example.com` does not match `example.com`. The wildcard stands for a subdomain
label, so `*.example.com` allows `cdn.example.com` and `static.example.com` but
not the bare apex `example.com`. List both if you need the apex too.

```http
Content-Security-Policy: script-src *.example.com example.com
```

A bare `*` does not match `data:`, `blob:`, or `filesystem:`. The `*` wildcard
covers network schemes (`http:` and `https:`) and any host, but the browser
deliberately excludes the `data:`, `blob:`, and `filesystem:` schemes. If a
directive needs those, name the
[scheme source](/en/docs/web-security/policies/content-security-policy/values/csp-scheme-source)
explicitly, for example `img-src * data:`.

A trailing `/` makes the path a prefix match. A path ending in `/` matches that
path and everything under it. A path without a trailing slash must match exactly.

```http
Content-Security-Policy: script-src https://cdn.example.com/lib/
```

That allows `/lib/app.js` and `/lib/vendor/chart.js`, but `/lib` on its own (no
slash) would only allow that exact URL.

Query and fragment are ignored. Two URLs that differ only in `?query` or
`#fragment` match the same host source, so you cannot allow or block a resource
based on its query string.

## Insecure values to avoid [#insecure-values-to-avoid]

An over-broad host source weakens the policy. A bare `*` in `script-src` allows
script from any origin, which removes most of CSP's protection; use a nonce or
hash instead. A wildcard like `*.googleapis.com` or `https:` in `script-src`
trusts every host under that scheme or domain, including ones an attacker might
control or abuse for an open redirect. Prefer the
[strict-dynamic pattern](/en/docs/web-security/policies/content-security-policy/values/csp-keywords)
over maintaining a script host allowlist at all.

## What it protects against [#what-it-protects-against]

Host sources let a policy say exactly which origins may serve each resource type,
which blocks an injected `<script src>` or `<img src>` pointing at an
attacker-controlled domain. Scope each directive to the hosts it actually needs,
then check the result with the [CSP evaluator](/tools/csp-evaluator) or a
[CSP scan](/tools/csp-scanner).

## Known bypasses and limitations [#known-bypasses-and-limitations]

A host allowlist is only as tight as its broadest entry. Allowlisting a host that
serves a JSONP endpoint, an open redirect, or a public CDN of arbitrary libraries
can let an attacker load executable script through that trusted origin, which is
why strict policies avoid script host allowlists in favor of nonces and
`'strict-dynamic'`. The wildcard rules above also mean a misjudged `*.` or missing
apex can silently block a legitimate resource.

## Risks [#risks]

The two failure modes pull in opposite directions: too broad a host source (a
bare `*`, a wide scheme, or a CDN that hosts anything) and the policy stops
protecting script; too narrow (forgetting the apex, a port, or a `data:` need)
and real resources break. Test changes in
[Report-Only mode](/en/docs/web-security/policies/content-security-policy/report-only)
before enforcing them.

## Recommendation [#recommendation]

For script, prefer a
[nonce or hash](/en/docs/web-security/policies/content-security-policy/values/csp-hashes-nonce)
with `'strict-dynamic'` over a host allowlist, and keep host sources for the
resource types that only display content. Set the remaining directives explicitly
so nothing falls back implicitly:

```http
Content-Security-Policy:
    default-src 'self';
    script-src 'nonce-{RANDOM}' 'strict-dynamic';
    style-src 'self';
    img-src 'self';
    font-src 'self';
    connect-src 'self';
    media-src 'self';
    manifest-src 'self';
    frame-src 'none';
    worker-src 'self';
    object-src 'none';
    base-uri 'none';
    form-action 'self';
    frame-ancestors 'none';
    upgrade-insecure-requests;
    report-to csp-endpoint
```

```http
Reporting-Endpoints: csp-endpoint="https://<Endpoint-ID>.report.centralcsp.com"
```

The [OWASP CSP cheat sheet](https://cheatsheetseries.owasp.org/cheatsheets/Content_Security_Policy_Cheat_Sheet.html)
and the [web.dev strict CSP guide](https://web.dev/articles/strict-csp) both make
this the default, because a script host allowlist stays bypassable through JSONP
endpoints and open redirects on the hosts you trusted, while a nonce or hash
trusts each script individually.

## Examples [#examples]

Allow your own origin plus one CDN subdomain on a specific path:

```http
Content-Security-Policy: script-src 'self' https://cdn.example.com/js/
```

Allow images from any subdomain of a host, on any port:

```http
Content-Security-Policy: img-src https://*.example.com:*
```

## Browser support [#browser-support]

Host-source matching is part of core CSP and is widely supported across current
browsers, including the wildcard, port, and path-prefix rules described here.

## See also [#see-also]

* [Scheme source](/en/docs/web-security/policies/content-security-policy/values/csp-scheme-source)
* [Keywords](/en/docs/web-security/policies/content-security-policy/values/csp-keywords)
* [script-src directive](/en/docs/web-security/policies/content-security-policy/directives/script-src)
* [img-src directive](/en/docs/web-security/policies/content-security-policy/directives/img-src)
* [connect-src directive](/en/docs/web-security/policies/content-security-policy/directives/connect-src)

## Sources [#sources]

* [W3C, Content Security Policy Level 3, host-source matching](https://w3c.github.io/webappsec-csp/#match-url-to-source-expression)
* [MDN, CSP source values, host-source](https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/Content-Security-Policy)
* [web.dev, Mitigate XSS with a strict CSP](https://web.dev/articles/strict-csp)
* [OWASP, Content Security Policy cheat sheet](https://cheatsheetseries.owasp.org/cheatsheets/Content_Security_Policy_Cheat_Sheet.html)
