rtfeldman / elm-css

Typed CSS in Elm.
https://package.elm-lang.org/packages/rtfeldman/elm-css/latest
BSD 3-Clause "New" or "Revised" License
1.23k stars 196 forks source link

CSP: Hide wrapper span with class instead of style attribute #581

Open JohanWinther opened 2 years ago

JohanWinther commented 2 years ago

CSP nonces need to be added to any elements with a style attribute

This PR fixes the issue found in https://github.com/rtfeldman/elm-css/pull/570#issuecomment-1159400192

choonkeat commented 2 years ago

With this patch, I'm still seeing the csp errors in console of Safari, Firefox, Chrome. I believe for style-src, the nonce attribute only works for <style> elements; not meant for style= attributes

JohanWinther commented 2 years ago

Oh, so there's no way to use inline style attributes with nonces? Then I guess the only option left is to use the hash. Since the hash of display: none; never changes, you should be able to add it to your style-src with "unsafe-hashes".

Reference: https://content-security-policy.com/examples/allow-inline-style/ (the section about inline style attribute).

choonkeat commented 2 years ago

Then I guess the only option left is to use the hash... "unsafe-hashes"

I'm vendoring this repo and patching it :-/ instead of explaining "unsafe-hashes" to whom it may concern 😆

JohanWinther commented 2 years ago

I realised that perhaps the function can omit the style attribute if you use a nonce, so you will have to use the class to hide the span. I'm reopening this and then I'll push these changes.

Edit: I still think for most users is easier to add unsafe-hashes rather than introducing a new stylesheet to the CSP, especially if you only use elm-css.

JohanWinther commented 2 years ago

@choonkeat I think my latest commit https://github.com/rtfeldman/elm-css/pull/581/commits/4c1b33d63a8460c451e9bbf7a63431b856dda232 fixes all of the issues. By adding the style display: none; to the wrapper class internally we can

  1. avoid the style attribute,
  2. avoid having to force the user to add the style and
  3. still allow a user to override the style with the span.elm-css-style-wrapper selector

I saw that there is no nonce for the global function so I will try to implement that too (in a separate PR). Right now the <style> element that is created through global is represented as an Unstyled node, which means that toNonceUnstyled will not add the nonce to the <style> inside. I will have to explore a bit to solve it though.

choonkeat commented 2 years ago
|> styleToDeclaration (getCssTemplate [ Css.display Css.none ]) styleWrapperClass

nice solution!

I saw that there is no nonce for the global function

yes, I have a quick patch for local use for now

type Nonce
    = Nonce String

noncedGlobal : Nonce -> List Snippet -> Html.Styled.Html msg
noncedGlobal (Nonce nonce) snippets =
    snippets
        |> Preprocess.stylesheet
        |> Resolve.compile
        |> VirtualDom.text
        |> List.singleton
        |> VirtualDom.node "style" [ VirtualDom.attribute "nonce" nonce ]
        |> List.singleton
        |> VirtualDom.node "span"
            [ VirtualDom.attribute "class" "elm-css-style-wrapper"
            ]
        |> VirtualDom.Styled.unstyledNode

not particularly joyful to have 2 Nonce types