I’m using some of my nginx reverse proxied home services as a testbed for writing minimal content security policies. The following policy allowed me to play content without triggering any CSP exceptions:
add_header Content-Security-Policy "default-src 'none'; connect-src 'self' https://plex.tv https://*.plex.direct:* wss://*.plex.direct:* wss://pubsub.plex.tv; object-src 'self'; font-src 'self' data:; img-src 'self' https://www.google-analytics.com data: blob:; script-src 'self' 'sha256-WYWOVIbktjxzj8LQgW7AYkuN+xTPTYJhegm6zoIXchY=' https://www.google-analytics.com https://www.gstatic.com; style-src 'self' 'sha256-MZKTI0Eg1N13tshpFaVW65co/LeICXq4hyVx6GWVlK0='; media-src https://*.plex.direct:*; frame-ancestors 'none'" always;
-
the following code in index.html required a workaround for inline scripts:
<script>webpackJsonp([3],[]);</script> -
the following code in main.js required a workaround for inline styles:
var u, c, d, p = "2.8.3", h = {}, f = t.documentElement, m = "modernizr", v = t.createElement(m), g = v.style, y = ({}.toString,
" -webkit- -moz- -o- -ms- ".split(" ")), b = "Webkit Moz O ms", w = b.split(" "), S = b.toLowerCase().split(" "), P = {}, _ = [], x = _.slice, C = function(e, n, i, r) {
var a, s, o, l, u = t.createElement("div"), c = t.body, d = c || t.createElement("body");
if (parseInt(i, 10))
for (; i--; )
o = t.createElement("div"),
o.id = r ? r* : m + (i + 1),
u.appendChild(o);
return a = ["", '<style id="s', m, '">', e, "</style>"].join(""),
u.id = m,
(c ? u : d).innerHTML += a,
d.appendChild(u),
c || (d.style.background = "",
d.style.overflow = "hidden",
l = f.style.overflow,
f.style.overflow = "hidden",
f.appendChild(d)),
s = n(u, e),
c ? u.parentNode.removeChild(u) : (d.parentNode.removeChild(d),
f.style.overflow = l),
!!s
}
Hopefully those looking to add some modern websec to their services or the Plex devs will find this handy as a starting point. It’d be great if Plex one day set its own CSP headers! More info at OWASP, Mozilla, and content-security-policy.com.
The sha-256 hashes for the script and style above are very likely to break as versions change, and this was only tested against PMS 1.0.3.2461 (Plex Web 2.7.4)