From 513f24e6554c0f823baceedaac82ae4be65b2cc4 Mon Sep 17 00:00:00 2001 From: Digital Studium Date: Sat, 24 May 2025 08:09:44 +0000 Subject: [PATCH] first commit --- .gitignore | 2 + deploy.sh | 8 ++ diff.conf | 15 +++ diff.service | 25 ++++ src/main.py | 289 +++++++++++++++++++++++++++++++++++++++++++ src/requirements.txt | 15 +++ src/uwsgi.ini | 12 ++ 7 files changed, 366 insertions(+) create mode 100644 .gitignore create mode 100755 deploy.sh create mode 100644 diff.conf create mode 100644 diff.service create mode 100644 src/main.py create mode 100644 src/requirements.txt create mode 100644 src/uwsgi.ini diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..a230a78 --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +.venv/ +__pycache__/ diff --git a/deploy.sh b/deploy.sh new file mode 100755 index 0000000..c61f3bf --- /dev/null +++ b/deploy.sh @@ -0,0 +1,8 @@ +#!/bin/bash +chown www-data:www-data -R src +cp diff.service /lib/systemd/system/ +systemctl enable --now diff +sudo systemctl daemon-reload +sudo systemctl restart diff-diff + + diff --git a/diff.conf b/diff.conf new file mode 100644 index 0000000..a4af260 --- /dev/null +++ b/diff.conf @@ -0,0 +1,15 @@ +server { + listen 80; + server_name diff.digitalstudium.com; + client_max_body_size 0; + + location / { + include uwsgi_params; + uwsgi_pass unix:///tmp/diff.sock; + proxy_buffering off; + proxy_set_header X-Real-IP $remote_addr; + proxy_set_header X-Forwarded-Host $host; + proxy_set_header X-Forwarded-Port $server_port; + } + +} diff --git a/diff.service b/diff.service new file mode 100644 index 0000000..6096b3d --- /dev/null +++ b/diff.service @@ -0,0 +1,25 @@ +[Unit] +Description=Diff web application +After=network.target + +[Service] +WorkingDirectory=/srv/diff/src +User=www-data +Group=www-data + +# Virtual environment setup +ExecStartPre=/bin/bash -c '[ -d ".venv" ] || python3 -m venv .venv' +ExecStartPre=/bin/bash -c 'source .venv/bin/activate && pip install -r requirements.txt' + +# uWSGI execution +ExecStart=/srv/diff/src/.venv/bin/uwsgi --ini uwsgi.ini + +Restart=always +Environment="PYTHONUNBUFFERED=1" +StandardOutput=journal +StandardError=journal +SyslogIdentifier=diff + +[Install] +WantedBy=multi-user.target + diff --git a/src/main.py b/src/main.py new file mode 100644 index 0000000..4abfac9 --- /dev/null +++ b/src/main.py @@ -0,0 +1,289 @@ +from flask import Flask, request, render_template_string +import difflib +import argparse + +app = Flask(__name__) + +HTML_TEMPLATE = ''' + + + + + Enhanced Diff Tool + + + + +
+
+

Diff Tool

+
🌓 Toggle Theme
+
+ +
+
+
+

Original Content

+ + +
+ +
+

Modified Content

+ + +
+
+ +
+ + {% if diff_html %} + + {% endif %} +
+
+ + {% if message %} +
{{ message }}
+ {% endif %} + + {% if diff_html %} +
+ {{ diff_html|safe }} +
+ {% endif %} +
+ + + + +''' + +@app.route('/', methods=['GET']) +def index(): + return render_template_string(HTML_TEMPLATE, + text1=request.args.get('text1', ''), + text2=request.args.get('text2', '')) + +@app.route('/diff', methods=['POST']) +def diff_files(): + # Handle file uploads and text inputs + file1 = request.files.get('file1') + file2 = request.files.get('file2') + text1 = request.form.get('text1', '').strip() + text2 = request.form.get('text2', '').strip() + + # Validate input + if (not file1 and not text1) or (not file2 and not text2): + return render_template_string(HTML_TEMPLATE, + message="Please provide content for both sides to compare.", + text1=text1, + text2=text2) + + try: + # Process first content + if file1 and file1.filename: + content1 = file1.read().decode('utf-8').splitlines() + filename1 = file1.filename + else: + content1 = text1.splitlines() + filename1 = "Original Content" + + # Process second content + if file2 and file2.filename: + content2 = file2.read().decode('utf-8').splitlines() + filename2 = file2.filename + else: + content2 = text2.splitlines() + filename2 = "Modified Content" + + except UnicodeDecodeError: + return render_template_string(HTML_TEMPLATE, + message="Error: Only UTF-8 encoded text files are supported.", + text1=text1, + text2=text2) + + # Generate diff + differ = difflib.HtmlDiff( + tabsize=4, + wrapcolumn=80, + linejunk=None, + charjunk=difflib.IS_CHARACTER_JUNK + ) + + diff_html = differ.make_file( + content1, + content2, + fromdesc=filename1, + todesc=filename2, + context=True, + numlines=3 + ) + + return render_template_string(HTML_TEMPLATE, + text1=text1, + text2=text2, + diff_html=diff_html) + +if __name__ == '__main__': + parser = argparse.ArgumentParser(description="Run SSL Certificate Decoder") + parser.add_argument('--port', type=int, default=5000, help='Port to run the service on') + parser.add_argument('--host', type=str, default='127.0.0.1', help='Host to run the service on') + args = parser.parse_args() + app.run(debug=True, port=args.port, host=args.host) diff --git a/src/requirements.txt b/src/requirements.txt new file mode 100644 index 0000000..9fc310f --- /dev/null +++ b/src/requirements.txt @@ -0,0 +1,15 @@ +astroid==3.3.10 +blinker==1.9.0 +click==8.2.0 +dill==0.4.0 +Flask==3.1.1 +isort==6.0.1 +itsdangerous==2.2.0 +Jinja2==3.1.6 +MarkupSafe==3.0.2 +mccabe==0.7.0 +platformdirs==4.3.8 +pylint==3.3.7 +tomlkit==0.13.2 +uWSGI==2.0.29 +Werkzeug==3.1.3 diff --git a/src/uwsgi.ini b/src/uwsgi.ini new file mode 100644 index 0000000..e0189f2 --- /dev/null +++ b/src/uwsgi.ini @@ -0,0 +1,12 @@ +[uwsgi] +socket = /tmp/diff.sock +chmod-socket = 660 +uid = www-data +gid = www-data +module = main:app +master = true +processes = 1 +threads = 2 +vacuum = true +die-on-term = true +