From f73003afca2b6cc9f48334958068b8f71e084342 Mon Sep 17 00:00:00 2001 From: Cédric Bonhomme Date: Sun, 22 Mar 2020 11:24:35 +0100 Subject: Added a way to manage Content Security Policy via the configuration file. --- instance/production.py | 10 ++++++++++ instance/sqlite.py | 10 ++++++++++ newspipe/bootstrap.py | 3 +++ poetry.lock | 17 ++++++++++++++++- pyproject.toml | 1 + 5 files changed, 40 insertions(+), 1 deletion(-) diff --git a/instance/production.py b/instance/production.py index d0aebd7e..05827a56 100644 --- a/instance/production.py +++ b/instance/production.py @@ -26,6 +26,16 @@ SQLALCHEMY_DATABASE_URI = "postgres://{user}:{password}@{host}:{port}/{name}".fo name=DATABASE_NAME, **DB_CONFIG_DICT ) +# Security +CONTENT_SECURITY_POLICY = { + 'default-src': '\'self\'', + 'img-src': '*', + 'media-src': [ + 'youtube.com', + ], + 'script-src': '\'self\'' +} + # Crawler CRAWLING_METHOD = "default" DEFAULT_MAX_ERROR = 6 diff --git a/instance/sqlite.py b/instance/sqlite.py index e6065ed3..cec46f48 100644 --- a/instance/sqlite.py +++ b/instance/sqlite.py @@ -17,6 +17,16 @@ SECURITY_PASSWORD_SALT = "L8gTsyrpRQEF8jNWQPyvRfv7U5kJkD" # Database SQLALCHEMY_DATABASE_URI = "sqlite:///newspipe.db" +# Security +CONTENT_SECURITY_POLICY = { + 'default-src': '\'self\'', + 'img-src': '*', + 'media-src': [ + 'youtube.com', + ], + 'script-src': '\'self\'' +} + # Crawler CRAWLING_METHOD = "default" DEFAULT_MAX_ERROR = 6 diff --git a/newspipe/bootstrap.py b/newspipe/bootstrap.py index 320fa261..edaee746 100644 --- a/newspipe/bootstrap.py +++ b/newspipe/bootstrap.py @@ -8,6 +8,7 @@ import logging import os from flask import Flask, request +from flask_talisman import Talisman from flask_babel import Babel, format_datetime from flask_sqlalchemy import SQLAlchemy @@ -65,6 +66,8 @@ set_logging(application.config["LOG_PATH"]) db = SQLAlchemy(application) +talisman = Talisman(application, content_security_policy=application.config["CONTENT_SECURITY_POLICY"]) + babel = Babel(application) diff --git a/poetry.lock b/poetry.lock index 1e5c1be6..e00f3973 100644 --- a/poetry.lock +++ b/poetry.lock @@ -268,6 +268,17 @@ version = "2.4.1" Flask = ">=0.10" SQLAlchemy = ">=0.8.0" +[[package]] +category = "main" +description = "HTTP security headers for Flask." +name = "flask-talisman" +optional = false +python-versions = "*" +version = "0.7.0" + +[package.dependencies] +six = ">=1.9.0" + [[package]] category = "main" description = "Simple integration of Flask and WTForms." @@ -572,7 +583,7 @@ idna = ">=2.0" multidict = ">=4.0" [metadata] -content-hash = "a76c1fbed09fe6be2b0351add63dc5b8e218761204f65f1e60d25ef202e2a9e1" +content-hash = "c8407863562e0f8573d3f8b8a7b1ab4b09ea3a40271ae077af278176246e934b" python-versions = "^3.8" [metadata.files] @@ -675,6 +686,10 @@ flask-sqlalchemy = [ {file = "Flask-SQLAlchemy-2.4.1.tar.gz", hash = "sha256:6974785d913666587949f7c2946f7001e4fa2cb2d19f4e69ead02e4b8f50b33d"}, {file = "Flask_SQLAlchemy-2.4.1-py2.py3-none-any.whl", hash = "sha256:0078d8663330dc05a74bc72b3b6ddc441b9a744e2f56fe60af1a5bfc81334327"}, ] +flask-talisman = [ + {file = "flask-talisman-0.7.0.tar.gz", hash = "sha256:468131464a249274ed226efc21b372518f442487e58918ccab8357eaa638fd1f"}, + {file = "flask_talisman-0.7.0-py2.py3-none-any.whl", hash = "sha256:eaa754f4b771dfbe473843391d69643b79e3a38c865790011ac5e4179c68e3ec"}, +] flask-wtf = [ {file = "Flask-WTF-0.14.3.tar.gz", hash = "sha256:d417e3a0008b5ba583da1763e4db0f55a1269d9dd91dcc3eb3c026d3c5dbd720"}, {file = "Flask_WTF-0.14.3-py2.py3-none-any.whl", hash = "sha256:57b3faf6fe5d6168bda0c36b0df1d05770f8e205e18332d0376ddb954d17aef2"}, diff --git a/pyproject.toml b/pyproject.toml index f522154a..6db36059 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -30,6 +30,7 @@ Flask-Script = "^2.0.6" WTForms = "^2.2.1" python-dateutil = "^2.8.1" psycopg2-binary = "^2.8.4" +flask-talisman = "^0.7.0" -- cgit