Code Monkey home page Code Monkey logo

secure's Introduction

secure.py

image Python 3 image image Build Status

secure.py πŸ”’ is a lightweight package that adds optional security headers for Python web frameworks.

Supported Python web frameworks

aiohttp, Bottle, CherryPy, Django, Falcon, FastAPI, Flask, hug, Masonite, Pyramid, Quart, Responder, Sanic, Starlette, Tornado

Install

pip:

pip install secure

Pipenv:

pipenv install secure

After installing secure:

import secure

secure_headers = secure.Secure()

Secure Headers

Example

secure_headers.framework(response)

Default HTTP response headers:

strict-transport-security: max-age=63072000; includeSubdomains
x-frame-options: SAMEORIGIN
x-xss-protection: 0
x-content-type-options: nosniff
referrer-policy: no-referrer, strict-origin-when-cross-origin
cache-control: no-store

Policy Builders

Policy Builder Example

Content Security Policy builder:

csp = (
        secure.ContentSecurityPolicy()
        .default_src("'none'")
        .base_uri("'self'")
        .connect_src("'self'", "api.spam.com")
        .frame_src("'none'")
        .img_src("'self'", "static.spam.com")
    )
secure_headers = secure.Secure(csp=csp)

HTTP response headers:

strict-transport-security: max-age=63072000; includeSubdomains
x-frame-options: SAMEORIGIN
x-xss-protection: 0
x-content-type-options: nosniff
referrer-policy: no-referrer, strict-origin-when-cross-origin
cache-control: no-store
content-security-policy: default-src 'none'; base-uri 'self'; connect-src 'self' api.spam.com; frame-src 'none'; img-src 'self' static.spam.com"

Documentation

Please see the full set of documentation at https://secure.readthedocs.io

FastAPI Example

import uvicorn
from fastapi import FastAPI
import secure

app = FastAPI()

server = secure.Server().set("Secure")

csp = (
    secure.ContentSecurityPolicy()
    .default_src("'none'")
    .base_uri("'self'")
    .connect_src("'self'" "api.spam.com")
    .frame_src("'none'")
    .img_src("'self'", "static.spam.com")
)

hsts = secure.StrictTransportSecurity().include_subdomains().preload().max_age(2592000)

referrer = secure.ReferrerPolicy().no_referrer()

permissions_value = (
    secure.PermissionsPolicy().geolocation("self", "'spam.com'").vibrate()
)

cache_value = secure.CacheControl().must_revalidate()

secure_headers = secure.Secure(
    server=server,
    csp=csp,
    hsts=hsts,
    referrer=referrer,
    permissions=permissions_value,
    cache=cache_value,
)


@app.middleware("http")
async def set_secure_headers(request, call_next):
    response = await call_next(request)
    secure_headers.framework.fastapi(response)
    return response


@app.get("/")
async def root():
    return {"message": "Secure"}


if __name__ == "__main__":
    uvicorn.run(app, port=8081, host="localhost")

HTTP response headers:

server: Secure
strict-transport-security: includeSubDomains; preload; max-age=2592000
x-frame-options: SAMEORIGIN
x-xss-protection: 0
x-content-type-options: nosniff
content-security-policy: default-src 'none'; base-uri 'self'; connect-src 'self'api.spam.com; frame-src 'none'; img-src 'self' static.spam.com
referrer-policy: no-referrer
cache-control: must-revalidate
permissions-policy: geolocation=(self 'spam.com'), vibrate=()

Resources

secure's People

Contributors

cak avatar chadwhawkins avatar jeffhoyo avatar oplik0 avatar sesh avatar vaibhavmule avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

secure's Issues

'report-to' directive implemented incorrectly, needs it's own header

The report-to directive should be taking in a 'group-name' string that references the values inside a separate Report-To header.

It looks like this library needs to be updated to:

  1. Clean up report_to because it should not be taking a json object, but rather a string corresponding to the group name

  2. Add a Report-To header

Happy to send a PR, just wanted to run this by you guys to check that I'm not mistaken or overlooking something.

This header is currently only supported on Chrome, but it's the future once report-uri gets fully deprecated: https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Security-Policy/report-uri

Correct sample policy:

Report-To: { "group": "csp-endpoint",
             "max_age": 10886400,
             "endpoints": [
               { "url": "https://example.com/csp-reports" }
             ] },
           { "group": "hpkp-endpoint",
             "max_age": 10886400,
             "endpoints": [
               { "url": "https://example.com/hpkp-reports" }
             ] }
Content-Security-Policy: ...; report-to csp-endpoint

SameSite cookie not being set Tornado

Hey,

I'm using Tornado 6.0.3 and apparently I have to use a patch (Morsel._reserved['samesite'] = 'SameSite') but the samesite cookies are not being set. Not sure I've understood how to use secure in my code but this is what I've done.

from http.cookies import Morsel
from secure import SecureHeaders
from secure import SecureCookie

Morsel._reserved['samesite'] = 'SameSite'
SECURE_HEADERS = SecureHeaders()
SECURE_COOKIE = SecureCookie(expires=1, samesite=SecureCookie.SameSite.LAX)

class BaseHandler(tornado.web.RequestHandler):
    """Main class used for general functions applying to entire application. """

    def set_default_headers(self):
        """docstring"""
        SECURE_HEADERS.tornado(self)

    def set_samesite_cookie(self, cookie_name, cookie_value):
        """Sets a samesite cookie"""

        SECURE_COOKIE.tornado(self, name=cookie_name, value=cookie_value)

and then I have used this in another class:

self.set_samesite_cookie("user", user_id)

Any suggestions to why it's not working is appreciated!
Thank you!

starlette `middleware` decorator is deprecated

The example code for starlette proposes to use the middleware decorator: https://secure.readthedocs.io/en/latest/frameworks.html#starlette

Anyhow, this decorator is deprecated, and will be removed in version 1.0.0 - at least there is a warning about that.

The message is:

[...]/site-packages/starlette/applications.py:248: DeprecationWarning: The `middleware` decorator is deprecated, and will be removed in version 1.0.0. Refer to https://www.starlette.io/middleware/#using-middleware for recommended approach.

It would be good to update the help.

I'm using this now, but would not say that I'm confident this is the correct solution:

class SecureHeadersMiddleware(BaseHTTPMiddleware):
    async def dispatch(self, request, call_next):
        response = await call_next(request)
        secure_headers.framework.starlette(response)
        return response

app.add_middleware(SecureHeadersMiddleware)

Error on Line 87, in cherrypy

Receiving error message on line 87, in cherrypy.

TypeError: tuple_headers() got an unexpected keyword argument 'report_to'

Python Version: Python 3.8.2
SecurePy Version: 0.2.1-py3.8
I installed this to run with SpiderFoot.

Question: why does the nonce staticmethod add angle brackets around the nonce value?

value = "'nonce-<{}>'".format(value)

The examples of adding a nonce to CSP that I've seen in, e.g., https://csp.withgoogle.com/docs/strict-csp.html#example and https://content-security-policy.com/nonce/ show 'nonce-rAnd0m'.

The CSP3 spec specifies the nonce production as:

; Nonces: 'nonce-[nonce goes here]'
nonce-source  = "'nonce-" [base64-value](https://www.w3.org/TR/CSP3/#grammardef-base64-value) "'"
base64-value  = 1*( [ALPHA](https://tools.ietf.org/html/rfc5234#appendix-B.1) / [DIGIT](https://tools.ietf.org/html/rfc5234#appendix-B.1) / "+" / "/" / "-" / "_" )*2( "=" )

Are the characters < and > even allowed?

Permission policy updates

Just integrated 'secure' into my flask app, and the documentation has been very useful (thank you!). One adjustment I'd make to the docs, is to mention that leaving a policy empty, like

    secure.PermissionsPolicy()
    .accelerometer()

means it's being disabled.


The main reason I made this issue though, is the missing permission policies.

I don't know whether they are new or not, either way, would be dope to have them added to 'secure' as well.

Apart from the proposed/experimental tabs, the ones I've found are missing are the following ones:

  • battery
  • cross-origin-isolated
  • display-capture
  • execution-while-not-rendered
  • execution-while-out-of-viewport
  • navigation-override
  • publickey-credentials-get
  • screen-wake-lock
  • web-share
  • xr-spatial-tracking

And I assume

  • Values
  • vr

are outdated, since they also throw errors when I attempt to use them?

Versioning strategy?

Hi,

What's the versioning strategy for new releases? I ask as the project appears to use Semantic Versioning, but the latest release 0.3.0 contains breaking changes.

Add back `report_uri` CSP directive until Reporting API stabilises

While the report_uri directive is deprecated, currently Report-To header required for report-to directive was removed from spec before it even became a Candidate Recommendation. Instead, current ED of Reporting API has a Reporting-Endpoints header that doesn't use the JSON values like the previous one, instead opting for a simpler groupname="url" syntax (with ability to add multiple comma-separated entries).
Considering that according to caniuse only about 70% of users have support for Report-To header, while over 93% support report-uri directive, for now report-uri seems to be more widely supported and could even live longer than Report-To header.

It can be added as a custom directive, but I think it'd be a good idea to re-add it as a normal directive. report-to CSP directive is still the way to go in the future, but for now it's much less practical due to its companion header not being truly widely supported yet and on its way to be replaced soon.

Server header is not overridden

I am using the following in a FastAPI project

server = secure.Server().set("Secure")

But the result is:

server: uvicorn
server: Secure

ie. it does not override the server header but simply adds another one.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    πŸ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. πŸ“ŠπŸ“ˆπŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❀️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.