Fix security issues.

This commit is contained in:
2025-08-04 13:45:13 +02:00
committed by Jens Luedicke
parent f98e8f3e71
commit 64b8c3fccb
7 changed files with 1100 additions and 174 deletions

View File

@@ -14,6 +14,7 @@ from flask import (Blueprint, Response, abort, flash, g, redirect, request,
from frontmatter_utils import parse_frontmatter
from models import Note, db
from routes.auth import company_required, login_required
from security_utils import sanitize_folder_path, validate_folder_access
# Create blueprint
notes_download_bp = Blueprint('notes_download', __name__)
@@ -30,8 +31,11 @@ def download_note(slug, format):
if not note.can_user_view(g.user):
abort(403)
# Prepare filename
# Prepare filename - extra sanitization
safe_filename = re.sub(r'[^a-zA-Z0-9_-]', '_', note.title)
# Ensure filename isn't too long
if len(safe_filename) > 100:
safe_filename = safe_filename[:100]
timestamp = datetime.now().strftime('%Y%m%d')
if format == 'md':
@@ -142,6 +146,8 @@ def download_notes_bulk():
if note and note.can_user_view(g.user):
# Get content based on format
safe_filename = re.sub(r'[^a-zA-Z0-9_-]', '_', note.title)
if len(safe_filename) > 100:
safe_filename = safe_filename[:100]
if format == 'md':
content = note.content
@@ -195,8 +201,15 @@ def download_notes_bulk():
@company_required
def download_folder(folder_path, format):
"""Download all notes in a folder as a zip file"""
# Decode folder path (replace URL encoding)
folder_path = unquote(folder_path)
# Decode and sanitize folder path
try:
folder_path = sanitize_folder_path(unquote(folder_path))
except ValueError:
abort(400, "Invalid folder path")
# Validate folder exists and user has access
if not validate_folder_access(folder_path, g.user.company_id, db.session):
abort(404, "Folder not found")
# Get all notes in this folder
notes = Note.query.filter_by(
@@ -220,6 +233,8 @@ def download_folder(folder_path, format):
for note in viewable_notes:
# Get content based on format
safe_filename = re.sub(r'[^a-zA-Z0-9_-]', '_', note.title)
if len(safe_filename) > 100:
safe_filename = safe_filename[:100]
if format == 'md':
content = note.content