elk
elk copied to clipboard
feat: add security headers (with nuxt-security)
This pull request adds the nuxt-security module to the setup, and using it to add several recommended security headers like Strict-Transport-Security and Referrer-Policy.
Personally the greatest interest lies in the Content-Security-Policy (CSP) header that can act as a good last line of defense against script injections and such. Unfortunately I couldn't find a current way to run Nuxt v3 without allowing 'unsafe-inline'
in the script-src and style-src directives. In the ideal case hashes of inline scripts and styles (or per-request random nonces added to those inline elements) could be collected to get rid of the 'unsafe-inline'
s, realizing the full benefits of CSP. Maybe in the future!
Despite this I believe this could be a good starting point: the other headers and CSP directives still have their benefits.
In addition to the modified CSP headers, the following nuxt-security defaults have been disabled:
- Cross-Origin-Embedder-Policy headers are disabled to allow cross-origin embeds.
- Disabled rate limiter ~~& request size limiter~~, as I don't have enough information for possible proper values for them 🙂
Run & review this pull request in StackBlitz Codeflow.
Deploy Preview for elk-docs canceled.
Name | Link |
---|---|
Latest commit | 0809658b8021052b38f0b9476e59dbf78f18a7af |
Latest deploy log | https://app.netlify.com/sites/elk-docs/deploys/63c49ff7d11ae700086969da |
Deploy Preview for elk-zone ready!
Name | Link |
---|---|
Latest commit | 0809658b8021052b38f0b9476e59dbf78f18a7af |
Latest deploy log | https://app.netlify.com/sites/elk-zone/deploys/63c49ff70845fa00089f0433 |
Deploy Preview | https://deploy-preview-1025--elk-zone.netlify.app |
Preview on mobile | Toggle QR Code...Use your smartphone camera to open QR code link. |
To edit notification comments on pull requests, go to your Netlify site settings.
Hey @jviide
I am glad that you liked the module enough to recommend implementing it here!
I would recommend keeping two of these middlewares enabled as they were set with the values considered as secure (Rate Limiter has Twitter rate limitting, while request size limiter uses the values provided by Atlassian)
@Baroshem Good points, and great to see you here! I re-enabled the request size limiter, as there doesn't seem to be any routes in Elk that would require large request payloads to pass.
As for the rate limit, enabling it makes sense, but in the context of Elk but I'm a bit worried about using the default rate limit of 150 tokens / hour for all routes. It seems it might be somewhat easily triggered in relatively normal scenarios - for example, multiple people behind a shared corporate IP opening a link to a post that's shared on a company channel. Or a burst of people behind a shared conference wi-fi opeing elk.zone during a talk about Elk 😉
How about enabling the rate limiter, but allowing a high but still limited amount of bursty requests? Like 600 tokens per minute or something to that effect.
@jviide
Sounds good! Keep in mind that the rate limiter here is using memory-cache to store the IP's so for big application handling many many requests this may not be efficient.
At this point maybe it would be reasonable to disable this middleware and implement the same funtionality as a part of the infrastructure, not application itself by using a tool like Fail2Ban for example.
The built in rate limiter is aimed for smaller projects with less traffic.
What we can also do here is that we could try to implement another source of storage for the rate limiter so that the values are not stored in memory but somewhere else (maybe Redis?).
Let me know what you think about it 🙂
@Baroshem I agree, rate limiting could be left to the infrastructure in this case. As far as I know Elk itself doesn't serve routes that need to be protected from stuff like password brute forcing attempts. As for denial of service protection, for example elk.zone is behind Cloudflare, which I assume takes care of DDoS protection. So I think leaving the rate limiting middleware off can be justified here 👍
@jviide
Agree. If you will have some spare time, could you do a little research and create an issue in my repo for potential module improvements? I am always open for any feedback on what can be done better 😃
I would really appreciate it!
I'm probably an idiot, but pnpm run dev
after this commit on Mac OS will fail due to all requests after the first to http://localhost:5314/ being upgraded to https. Disabled nuxt-security and localhost dev started to work again.
Interesting - I don't get it in same setup. Have you overridden NODE_ENV in any way?
I haven't. The problem reproduces on a fresh clone of the repo and with both node 18 and 19 from Homebrew.
hmm, apparently relatedly, also elk.zone is presenting me with security errors I haven't seen from previous versions. Clearly not the same issue as I have with dev, but also clearly to do with the new directives from nuxt-security... Browser: Safari 16.2 (17614.3.7.1.7, 17614)
The Access-Control-Allow-Origin failures are likely not related to nuxt-security, but mas.to's CORS policy blocking those requests to the /nodeinfo/2.0 endpoint. These nodeinfo requests were added in these lines. Disabling nuxt-security also doesn't get rid of those errors.
@osmaa Does the dev mode work for you again after https://github.com/elk-zone/elk/commit/3050350f25f7a25442bf015a2531c631b6e36331?
yes it does! thank you. As for the CORS error, that indeed is unrelated and instead caused by https://github.com/elk-zone/elk/commit/2e7979817a539496925bb0b897fdee1165dfd133 which tries to fetch /nodeinfo/2.0, a GoToSocial-specific API that doesn't exist in Mastodon.
Great 🙂 Thanks to @danielroe and @antfu for fixing the dev mode!