bare.css is the kind of CSS library that security folks usually like: tiny, boring, and not trying to be a JavaScript framework in disguise.
That changes the CSP conversation quite a bit.
If your site uses bare.css and almost nothing else, you can usually run a very tight policy. If your “simple” site also includes analytics, consent banners, embedded forms, tag managers, and a couple of convenience scripts, your CSP gets messy fast. I’ve seen plenty of “minimal” websites end up with a header that looks like an ad-tech startup wrote it.
So the useful question is not “what is the CSP for bare.css?” Bare.css itself doesn’t need a special policy. The real question is:
How strict can your CSP be when bare.css is part of the stack?
The short answer
If bare.css is self-hosted and your site is mostly static, you can often get away with something close to this:
Content-Security-Policy:
default-src 'self';
style-src 'self';
img-src 'self' data:;
font-src 'self';
script-src 'self';
connect-src 'self';
base-uri 'self';
form-action 'self';
frame-ancestors 'none';
object-src 'none';
That’s a great baseline. Tight, readable, and easy to reason about.
But if you pull bare.css from a CDN, inject inline styles, or bolt on third-party services, the policy changes. That’s where the tradeoffs show up.
Option 1: Self-host bare.css and keep CSP strict
This is the best setup for most developer sites.
Example
Content-Security-Policy:
default-src 'self';
style-src 'self';
img-src 'self' data:;
font-src 'self';
script-src 'self';
connect-src 'self';
base-uri 'self';
form-action 'self';
frame-ancestors 'none';
object-src 'none';
Pros
- Very small attack surface
- Easy to audit
- No dependence on third-party CSS hosts
- Works well with static sites and Hugo
- No need for
unsafe-inlineif your templates are clean
If your bare.css file is just a local stylesheet under /css/bare.min.css, this is about as painless as CSP gets.
Cons
- You need to manage asset hosting yourself
- Any inline style attributes or
<style>blocks may break - Third-party widgets will force exceptions later
My bias: self-hosting wins almost every time. CSS frameworks are static assets. There’s rarely a good reason to outsource them to another origin in 2026 unless you really enjoy debugging blocked resources.
Option 2: Use bare.css from a CDN
If you load bare.css from jsDelivr, unpkg, or another CDN, your style-src needs to allow that host.
Example
Content-Security-Policy:
default-src 'self';
style-src 'self' https://cdn.jsdelivr.net;
img-src 'self' data:;
font-src 'self';
script-src 'self';
connect-src 'self';
base-uri 'self';
form-action 'self';
frame-ancestors 'none';
object-src 'none';
Pros
- Fast to set up
- No local asset pipeline needed
- Fine for prototypes and throwaway demos
Cons
- Expands trust to a third party
- Makes policy portability worse
- CDN changes, redirects, or extra domains can surprise you
- Harder to lock down long-term
This is acceptable, not ideal. If you’re building a real site, I’d still move bare.css local and remove the extra host from CSP.
Option 3: Allow inline styles for convenience
This is the slippery slope version.
A lot of sites using small CSS libraries still end up with inline style attributes, theme toggles, CMS-rendered blocks, or snippets from plugins. Then somebody adds this:
style-src 'self' 'unsafe-inline';
Example
Content-Security-Policy:
default-src 'self';
style-src 'self' 'unsafe-inline';
img-src 'self' data:;
font-src 'self';
script-src 'self';
connect-src 'self';
base-uri 'self';
form-action 'self';
frame-ancestors 'none';
object-src 'none';
Pros
- Fixes a lot of annoying breakage quickly
- Useful for legacy templates or CMS fragments
- Easier migration path if you’re tightening CSP gradually
Cons
- Weakens XSS defenses around style injection
- Encourages sloppy markup over time
- Makes it harder to know what your frontend actually depends on
For bare.css specifically, unsafe-inline usually means your app is the problem, not the CSS library. Bare.css doesn’t require it. If you can avoid this, avoid it.
If you need a deeper refresher on why directives like style-src, script-src, and default-src matter, csp-guide.com is a good reference without too much fluff.
Option 4: Strict CSP with nonces and modern script controls
This is where things get interesting if your “simple” site is no longer simple.
A real-world CSP from HeaderTest looks like this:
content-security-policy:
default-src 'self' https://www.googletagmanager.com https://*.cookiebot.com https://*.google-analytics.com;
script-src 'self' 'nonce-MmQyZTQ5YmItYTlkMy00YjI4LWFkMmUtZjNkNzhlY2VlYWJk' 'strict-dynamic' https://www.googletagmanager.com https://*.cookiebot.com https://*.google-analytics.com;
style-src 'self' 'unsafe-inline' https://www.googletagmanager.com https://*.cookiebot.com https://consent.cookiebot.com;
img-src 'self' data: https:;
font-src 'self';
connect-src 'self' https://api.headertest.com https://tallycdn.com https://or.headertest.com wss://or.headertest.com https://*.google-analytics.com https://*.googletagmanager.com https://*.cookiebot.com;
frame-src 'self' https://consentcdn.cookiebot.com;
frame-ancestors 'none';
base-uri 'self';
form-action 'self';
object-src 'none'
This is a good example of how CSP evolves in the real world. The site can still be security-conscious, but once analytics, consent tooling, and external services show up, the header gets broader.
Pros
- Strong script execution model with nonce-based trust
strict-dynamicis much better than giant script allowlists- Realistic for production sites with third-party dependencies
- Keeps dangerous stuff like
object-srcand framing locked down
Cons
- More operational complexity
- Nonce generation has to be correct on every response
- Harder to understand for teammates
- Still compromised somewhat by
style-src 'unsafe-inline'
For a bare.css site, this level of CSP is usually overkill unless the rest of your stack demands it. The CSS library isn’t what pushes you here. Tag managers and consent platforms do.
Comparison: which CSP style fits bare.css best?
Best security
Self-hosted bare.css + strict allowlist CSP
Use this if your site is mostly static and under your control.
Best convenience
CDN-hosted bare.css + host allowlist
Fine for demos. Not my first choice for production.
Best migration path
Allow unsafe-inline temporarily
Useful when cleaning up templates, but don’t treat it as “done.”
Best for complex production sites
Nonce-based CSP with strict-dynamic
Great when you have dynamic scripts and third-party services. More moving parts, more things to maintain.
My recommended CSP for a typical bare.css site
If you’re building a Hugo site with bare.css, a small amount of local JavaScript, and maybe a contact form, I’d start here:
Content-Security-Policy:
default-src 'self';
script-src 'self';
style-src 'self';
img-src 'self' data:;
font-src 'self';
connect-src 'self';
form-action 'self';
base-uri 'self';
frame-ancestors 'none';
object-src 'none';
Then only add directives when the app actually needs them.
If you use an external form backend:
connect-src 'self' https://api.exampleforms.com;
form-action 'self' https://api.exampleforms.com;
If you embed a privacy tool or analytics:
script-src 'self' https://www.googletagmanager.com;
connect-src 'self' https://www.google-analytics.com;
img-src 'self' data: https:;
That’s the sane approach: start strict, widen deliberately.
Common mistakes with bare.css and CSP
1. Blaming bare.css for inline style violations
Bare.css is just CSS. If CSP complains about inline styles, check your templates, components, or CMS output first.
2. Using default-src as if it covers everything cleanly
It helps, but explicit directives are clearer. I prefer being specific for script-src, style-src, img-src, and connect-src.
3. Copy-pasting a giant policy from another project
A CSP for a marketing site with GTM, Cookiebot, and analytics is not a good default for a minimal bare.css blog.
4. Forgetting frame-ancestors
If you don’t want your site embedded, say so:
frame-ancestors 'none';
That’s one of the easiest wins in the whole header.
Final take
bare.css is not the hard part. That’s the whole point.
If you keep it self-hosted and avoid inline styling habits, CSP for a bare.css site can be refreshingly strict. That’s rare on the modern web, and worth taking advantage of.
If your site grows extra dependencies, your policy should reflect reality instead of pretending to be pure. I’d rather see an honest CSP with a few justified exceptions than a fake “strict” one that breaks production and gets disabled two days later.
For most bare.css sites, the sweet spot is simple:
- self-host the stylesheet
- avoid
unsafe-inline - lock down scripts hard
- add third-party origins one by one
- keep
object-src 'none'andframe-ancestors 'none'
That gets you a CSP that is actually maintainable, not just theoretically secure.