App rejected due to missing CSP headers - but which URLs must they be added on?

37 1 10



I have submitted an app for app review, but it keeps being rejected with this cause:

  1. App must set security headers to protect against clickjacking.
    To prevent clickjacking attacks, your app must set the proper content security policy directive. If your app is not embedded in an Iframe in the Shopify admin, and you are seeing this message, check your app's settings and make sure it is set to "non-embedded." If your app is embedded, then we expect the 'Content-Security-Policy' header to be frame-ancestors https://[shop], where [shop] is dynamically set to the shop domain the app is embedded on.

This requirement is new, as I have several other apps in the app store.
The documentation that is linked to, states that the headers must be added "in any routes that render HTML content.", but I am not quite sure exactly which URLs that entails, as I am not a react expert.

Please note that my app is an embedded app and that I have two servers in my app setup - one server with the polaris frontend (a next server), and another server with the backend code that calls Shopifys API etc. (a node server). I've done the following:

  1. Concluded that I need to add the "Content-Security-Policy" header to the response, with the value "frame-ancestors https://${encodeURIComponent(shop)};" where the "shop" parameter e.g. is ""
  2. Concluded that the header cannot be added on meta in the html header when it is frame-ancestors
  3. Concluded that I can use withSecureHeaders from next-secure-headers to set the header on the react response, although I cannot set the concrete shop, I can only set a wildcard i.e. "frame-ancestors https://*;"
  4. In total this means I have content security header on:
    1. The wildcard header on my app url - the url that's used when the app is installed
    2. The non-wildcard header on the OAuth URL that requests the merchant to approve the install (as this does not render HTML content, I guess the header should not be added here?)
    3. The non-wildcard header on the OAuth URL that is called when the merchant approves the install (as this does not render HTML content, I guess the header should not be added here?)

I tried with the wildcard header on all the URLs as well - that did not work either.
Using the Chrome inspect tool, I can see under the "Network" tab, that the CSP header is in fact present on the response on these URLs.
So I am left with the following assumptions:

  1. The wildcard header is not accepted - the header must be for the specific shop (and the Shopify documentation states as much, so it would not be a surprise). In this case my problem is that the withSecureHeaders is part of the code "export default withSecureHeaders...", so how do I access the specific shop in this code, i.e. how do I set a dynamic header with withSecureHeaders or how do I set it in an alternative way on a next server (I cannot set a dynamic header using next-config.js and next-secure-headers)?
  2. The CSP header should be added to other URLs than the ones I listed above. How do I determine which URLs these are? I have filtered all the calls in the "Network" tab og the Chrome "Inspect" tool to the name of the frontend- and backend server respectively, and I cannot find any calls that do not have the CSP header.
When approving the app, I sometimes get the message below - is that related to these CSP settings?



Replies 0 (0)