fixy i usprwnienia

This commit is contained in:
Mateusz Gruszczyński
2025-03-06 14:12:48 +01:00
parent c4b753d4bd
commit cae5ed787d
9 changed files with 329 additions and 35 deletions

200
app.py
View File

@@ -7,6 +7,8 @@ from datetime import datetime, timezone, timedelta
from io import StringIO
import socket
import ipaddress
import difflib
from croniter import croniter
from tzlocal import get_localzone
@@ -97,6 +99,13 @@ class RegexHostEntry(db.Model):
comment = db.Column(db.String(255), nullable=True)
user = db.relationship('User', backref='regex_entries')
class HostFileVersion(db.Model):
id = db.Column(db.Integer, primary_key=True)
hostfile_id = db.Column(db.Integer, db.ForeignKey('host_file.id'), nullable=False)
content = db.Column(db.Text, nullable=False)
timestamp = db.Column(db.DateTime, default=lambda: datetime.now(timezone.utc))
hostfile = db.relationship('HostFile', backref=db.backref('versions', lazy=True))
# Funkcje pomocnicze
def ensure_local_defaults(content):
required_lines = [
@@ -534,10 +543,15 @@ def edit_hosts_file(file_id):
flash('File not found or unauthorized', 'danger')
return redirect(url_for('list_hosts_files'))
if request.method == 'POST':
file.title = request.form['title']
file.content = request.form['content']
new_title = request.form['title']
new_content = request.form['content']
if file.content != new_content:
version = HostFileVersion(hostfile_id=file.id, content=file.content)
db.session.add(version)
file.title = new_title
file.content = new_content
db.session.commit()
flash('Hosts file updated', 'success')
flash('Hosts file updated and previous version saved.', 'success')
return redirect(url_for('list_hosts_files'))
return render_template('new_edit_hosts_file.html', file=file)
@@ -897,23 +911,23 @@ def delete_backup(backup_id):
# -------------------
# EDYCJA LOKALNEGO PLIKU HOSTS
# -------------------
@app.route('/edit-local-hosts', methods=['GET', 'POST'], endpoint='edit_local_hosts')
def edit_local_hosts():
if 'user_id' not in session:
return redirect(url_for('login'))
user_id = session['user_id']
hostfile = HostFile.query.filter_by(user_id=user_id, title="Default Hosts").first()
if not hostfile:
default_content = "# This is a sample hosts file.\n127.0.0.1 localhost\n"
hostfile = HostFile(user_id=user_id, title="Default Hosts", content=default_content)
db.session.add(hostfile)
db.session.commit()
if request.method == 'POST':
new_content = request.form['hosts_content']
hostfile.content = new_content
db.session.commit()
flash('Local hosts content updated successfully', 'success')
return render_template('edit_hosts.html', content=hostfile.content)
# @app.route('/edit-local-hosts', methods=['GET', 'POST'], endpoint='edit_local_hosts')
# def edit_local_hosts():
# if 'user_id' not in session:
# return redirect(url_for('login'))
# user_id = session['user_id']
# hostfile = HostFile.query.filter_by(user_id=user_id, title="Default Hosts").first()
# if not hostfile:
# default_content = "# This is a sample hosts file.\n127.0.0.1 localhost\n"
# hostfile = HostFile(user_id=user_id, title="Default Hosts", content=default_content)
# db.session.add(hostfile)
# db.session.commit()
# if request.method == 'POST':
# new_content = request.form['hosts_content']
# hostfile.content = new_content
# db.session.commit()
# flash('Local hosts content updated successfully', 'success')
# return render_template('edit_hosts.html', content=hostfile.content)
# -------------------
# DEPLOYMENT DOMYŚLNY DLA UŻYTKOWNIKA
@@ -1177,6 +1191,152 @@ def update_host_automation(id):
flash('Ustawienia automatyzacji zostały zaktualizowane.', 'success')
return redirect(url_for('server_list'))
@app.route('/edit-local-hosts', methods=['GET', 'POST'], endpoint='edit_local_hosts')
def edit_local_hosts():
if 'user_id' not in session:
return redirect(url_for('login'))
user_id = session['user_id']
hostfile = HostFile.query.filter_by(user_id=user_id, title="Default Hosts").first()
if not hostfile:
default_content = "# This is a sample hosts file.\n127.0.0.1 localhost\n"
hostfile = HostFile(user_id=user_id, title="Default Hosts", content=default_content)
db.session.add(hostfile)
db.session.commit()
if request.method == 'POST':
new_content = request.form['hosts_content']
# Zapisz obecną wersję do historii przed zmianą
version = HostFileVersion(hostfile_id=hostfile.id, content=hostfile.content)
db.session.add(version)
# Aktualizacja treści
hostfile.content = new_content
db.session.commit()
flash('Local hosts content updated successfully and previous version saved.', 'success')
return render_template('edit_hosts.html', content=hostfile.content, hostfile=hostfile)
@app.route('/hostfile/<int:hostfile_id>/versions', methods=['GET', 'POST'])
def hostfile_versions(hostfile_id):
if 'user_id' not in session:
return redirect(url_for('login'))
hostfile = HostFile.query.get(hostfile_id)
if not hostfile or hostfile.user_id != session['user_id']:
flash('Hostfile not found or unauthorized', 'danger')
return redirect(url_for('dashboard'))
if request.method == 'POST':
# Masowe usuwanie lista zaznaczonych wersji
selected_ids = request.form.getlist('selected_versions')
for version_id in selected_ids:
version = HostFileVersion.query.get(version_id)
if version and version.hostfile.user_id == session['user_id']:
db.session.delete(version)
db.session.commit()
flash('Wybrane wersje zostały usunięte.', 'info')
return redirect(url_for('hostfile_versions', hostfile_id=hostfile_id))
versions = HostFileVersion.query.filter_by(hostfile_id=hostfile.id)\
.order_by(HostFileVersion.timestamp.desc()).all()
return render_template('hostfile_versions.html', hostfile=hostfile, versions=versions)
@app.route('/hostfile/<int:hostfile_id>/versions/delete_old/<int:days>')
def delete_old_versions(hostfile_id, days):
if 'user_id' not in session:
return redirect(url_for('login'))
hostfile = HostFile.query.get(hostfile_id)
if not hostfile or hostfile.user_id != session['user_id']:
flash('Hostfile not found or unauthorized', 'danger')
return redirect(url_for('dashboard'))
cutoff = datetime.now(timezone.utc) - timedelta(days=days)
old_versions = HostFileVersion.query.filter(HostFileVersion.hostfile_id == hostfile_id,
HostFileVersion.timestamp < cutoff).all()
for version in old_versions:
db.session.delete(version)
db.session.commit()
flash(f'Usunięto wersje starsze niż {days} dni.', 'info')
return redirect(url_for('hostfile_versions', hostfile_id=hostfile_id))
@app.route('/hostfile/diff_current/<int:hostfile_id>')
def diff_current_hostfile(hostfile_id):
if 'user_id' not in session:
return redirect(url_for('login'))
hostfile = HostFile.query.get(hostfile_id)
if not hostfile or hostfile.user_id != session['user_id']:
flash('Hostfile not found or unauthorized.', 'danger')
return redirect(url_for('dashboard'))
# Używamy len() zamiast |length
if not hostfile.versions or len(hostfile.versions) == 0:
flash('Brak zapisanej historii wersji do porównania.', 'warning')
return redirect(url_for('hostfile_versions', hostfile_id=hostfile_id))
latest_version = hostfile.versions[0]
differ = difflib.HtmlDiff(wrapcolumn=80)
diff_html = differ.make_table(
latest_version.content.splitlines(),
hostfile.content.splitlines(),
fromdesc=f"Najnowsza wersja historii (ID: {latest_version.id}, {latest_version.timestamp.strftime('%Y-%m-%d %H:%M:%S')})",
todesc="Aktualna zawartość",
context=True,
numlines=3
)
return render_template('diff_versions.html', diff_html=diff_html, hostfile_id=hostfile.id)
@app.route('/hostfile/diff/<int:version1_id>/<int:version2_id>')
def diff_hostfile_versions(version1_id, version2_id):
if 'user_id' not in session:
return redirect(url_for('login'))
version1 = HostFileVersion.query.get(version1_id)
version2 = HostFileVersion.query.get(version2_id)
if not version1 or not version2 or version1.hostfile.user_id != session['user_id'] or version2.hostfile.user_id != session['user_id']:
flash('Wersje nie znalezione lub brak uprawnień.', 'danger')
return redirect(url_for('dashboard'))
differ = difflib.HtmlDiff(wrapcolumn=80)
diff_html = differ.make_table(
version1.content.splitlines(),
version2.content.splitlines(),
fromdesc=f"Wersja {version1.id} - {version1.timestamp.strftime('%Y-%m-%d %H:%M:%S')}",
todesc=f"Wersja {version2.id} - {version2.timestamp.strftime('%Y-%m-%d %H:%M:%S')}",
context=True,
numlines=3
)
# Przekazujemy hostfile_id, zakładając, że obie wersje należą do tego samego pliku
hostfile_id = version1.hostfile_id
return render_template('diff_versions.html', diff_html=diff_html, hostfile_id=hostfile_id)
@app.route('/hostfile/version/<int:version_id>')
def view_hostfile_version(version_id):
if 'user_id' not in session:
return redirect(url_for('login'))
version = HostFileVersion.query.get(version_id)
if not version or version.hostfile.user_id != session['user_id']:
flash('Version not found or unauthorized', 'danger')
return redirect(url_for('dashboard'))
return render_template('view_hostfile_version.html', version=version)
@app.route('/hostfile/version/<int:version_id>/restore')
def restore_hostfile_version(version_id):
if 'user_id' not in session:
return redirect(url_for('login'))
version = HostFileVersion.query.get(version_id)
if not version or version.hostfile.user_id != session['user_id']:
flash('Version not found or unauthorized', 'danger')
return redirect(url_for('dashboard'))
# Przywróć zawartość wersji do głównego hostfile
hostfile = version.hostfile
hostfile.content = version.content
db.session.commit()
flash('Version restored successfully.', 'success')
return redirect(url_for('edit_local_hosts'))
@app.route('/hostfile/versions')
def default_hostfile_versions():
if 'user_id' not in session:
return redirect(url_for('login'))
# Zakładamy, że domyślny plik hosts ma tytuł "Default Hosts"
hostfile = HostFile.query.filter_by(user_id=session['user_id'], title="Default Hosts").first()
if not hostfile:
flash("Default Hosts file not found.", "danger")
return redirect(url_for('edit_local_hosts'))
return redirect(url_for('hostfile_versions', hostfile_id=hostfile.id))
def scheduled_deployments():