Testdaten Checkbox
Dieser Commit ist enthalten in:
@@ -1360,7 +1360,7 @@ def dashboard():
|
|||||||
security_level = 'success'
|
security_level = 'success'
|
||||||
security_level_text = 'NORMAL'
|
security_level_text = 'NORMAL'
|
||||||
|
|
||||||
# Resource Pool Statistiken
|
# Resource Pool Statistiken (nur Live-Daten, keine Testdaten)
|
||||||
cur.execute("""
|
cur.execute("""
|
||||||
SELECT
|
SELECT
|
||||||
resource_type,
|
resource_type,
|
||||||
@@ -1369,6 +1369,7 @@ def dashboard():
|
|||||||
COUNT(*) FILTER (WHERE status = 'quarantine') as quarantine,
|
COUNT(*) FILTER (WHERE status = 'quarantine') as quarantine,
|
||||||
COUNT(*) as total
|
COUNT(*) as total
|
||||||
FROM resource_pools
|
FROM resource_pools
|
||||||
|
WHERE is_test = FALSE
|
||||||
GROUP BY resource_type
|
GROUP BY resource_type
|
||||||
""")
|
""")
|
||||||
|
|
||||||
@@ -3163,6 +3164,9 @@ def resources():
|
|||||||
conn = get_connection()
|
conn = get_connection()
|
||||||
cur = conn.cursor()
|
cur = conn.cursor()
|
||||||
|
|
||||||
|
# Prüfe ob Testdaten angezeigt werden sollen (gleiche Logik wie bei Kunden)
|
||||||
|
show_test = request.args.get('show_test', 'false').lower() == 'true'
|
||||||
|
|
||||||
# Statistiken abrufen
|
# Statistiken abrufen
|
||||||
cur.execute("""
|
cur.execute("""
|
||||||
SELECT
|
SELECT
|
||||||
@@ -3172,8 +3176,9 @@ def resources():
|
|||||||
COUNT(*) FILTER (WHERE status = 'quarantine') as quarantine,
|
COUNT(*) FILTER (WHERE status = 'quarantine') as quarantine,
|
||||||
COUNT(*) as total
|
COUNT(*) as total
|
||||||
FROM resource_pools
|
FROM resource_pools
|
||||||
|
WHERE is_test = %s
|
||||||
GROUP BY resource_type
|
GROUP BY resource_type
|
||||||
""")
|
""", (show_test,))
|
||||||
|
|
||||||
stats = {}
|
stats = {}
|
||||||
for row in cur.fetchall():
|
for row in cur.fetchall():
|
||||||
@@ -3185,7 +3190,7 @@ def resources():
|
|||||||
'available_percent': round((row[1] / row[4] * 100) if row[4] > 0 else 0, 1)
|
'available_percent': round((row[1] / row[4] * 100) if row[4] > 0 else 0, 1)
|
||||||
}
|
}
|
||||||
|
|
||||||
# Letzte Aktivitäten
|
# Letzte Aktivitäten (gefiltert nach Test/Live)
|
||||||
cur.execute("""
|
cur.execute("""
|
||||||
SELECT
|
SELECT
|
||||||
rh.action,
|
rh.action,
|
||||||
@@ -3196,9 +3201,10 @@ def resources():
|
|||||||
rh.details
|
rh.details
|
||||||
FROM resource_history rh
|
FROM resource_history rh
|
||||||
JOIN resource_pools rp ON rh.resource_id = rp.id
|
JOIN resource_pools rp ON rh.resource_id = rp.id
|
||||||
|
WHERE rp.is_test = %s
|
||||||
ORDER BY rh.action_at DESC
|
ORDER BY rh.action_at DESC
|
||||||
LIMIT 10
|
LIMIT 10
|
||||||
""")
|
""", (show_test,))
|
||||||
recent_activities = cur.fetchall()
|
recent_activities = cur.fetchall()
|
||||||
|
|
||||||
# Ressourcen-Liste mit Pagination
|
# Ressourcen-Liste mit Pagination
|
||||||
@@ -3226,9 +3232,9 @@ def resources():
|
|||||||
FROM resource_pools rp
|
FROM resource_pools rp
|
||||||
LEFT JOIN licenses l ON rp.allocated_to_license = l.id
|
LEFT JOIN licenses l ON rp.allocated_to_license = l.id
|
||||||
LEFT JOIN customers c ON l.customer_id = c.id
|
LEFT JOIN customers c ON l.customer_id = c.id
|
||||||
WHERE 1=1
|
WHERE rp.is_test = %s
|
||||||
"""
|
"""
|
||||||
params = []
|
params = [show_test]
|
||||||
|
|
||||||
if resource_type:
|
if resource_type:
|
||||||
query += " AND rp.resource_type = %s"
|
query += " AND rp.resource_type = %s"
|
||||||
@@ -3268,6 +3274,7 @@ def resources():
|
|||||||
resource_type=resource_type,
|
resource_type=resource_type,
|
||||||
status_filter=status_filter,
|
status_filter=status_filter,
|
||||||
search=search,
|
search=search,
|
||||||
|
show_test=show_test,
|
||||||
datetime=datetime,
|
datetime=datetime,
|
||||||
timedelta=timedelta)
|
timedelta=timedelta)
|
||||||
|
|
||||||
@@ -3275,16 +3282,20 @@ def resources():
|
|||||||
@login_required
|
@login_required
|
||||||
def add_resources():
|
def add_resources():
|
||||||
"""Ressourcen zum Pool hinzufügen"""
|
"""Ressourcen zum Pool hinzufügen"""
|
||||||
|
# Hole show_test Parameter für die Anzeige
|
||||||
|
show_test = request.args.get('show_test', 'false').lower() == 'true'
|
||||||
|
|
||||||
if request.method == 'POST':
|
if request.method == 'POST':
|
||||||
resource_type = request.form.get('resource_type')
|
resource_type = request.form.get('resource_type')
|
||||||
resources_text = request.form.get('resources_text', '')
|
resources_text = request.form.get('resources_text', '')
|
||||||
|
is_test = request.form.get('is_test') == 'on' # Checkbox für Testdaten
|
||||||
|
|
||||||
# Parse resources (one per line)
|
# Parse resources (one per line)
|
||||||
resources = [r.strip() for r in resources_text.split('\n') if r.strip()]
|
resources = [r.strip() for r in resources_text.split('\n') if r.strip()]
|
||||||
|
|
||||||
if not resources:
|
if not resources:
|
||||||
flash('Keine Ressourcen angegeben', 'error')
|
flash('Keine Ressourcen angegeben', 'error')
|
||||||
return redirect(url_for('add_resources'))
|
return redirect(url_for('add_resources', show_test=show_test))
|
||||||
|
|
||||||
conn = get_connection()
|
conn = get_connection()
|
||||||
cur = conn.cursor()
|
cur = conn.cursor()
|
||||||
@@ -3295,10 +3306,10 @@ def add_resources():
|
|||||||
for resource_value in resources:
|
for resource_value in resources:
|
||||||
try:
|
try:
|
||||||
cur.execute("""
|
cur.execute("""
|
||||||
INSERT INTO resource_pools (resource_type, resource_value, status_changed_by)
|
INSERT INTO resource_pools (resource_type, resource_value, status_changed_by, is_test)
|
||||||
VALUES (%s, %s, %s)
|
VALUES (%s, %s, %s, %s)
|
||||||
ON CONFLICT (resource_type, resource_value) DO NOTHING
|
ON CONFLICT (resource_type, resource_value) DO NOTHING
|
||||||
""", (resource_type, resource_value, session['username']))
|
""", (resource_type, resource_value, session['username'], is_test))
|
||||||
|
|
||||||
if cur.rowcount > 0:
|
if cur.rowcount > 0:
|
||||||
added += 1
|
added += 1
|
||||||
@@ -3323,13 +3334,13 @@ def add_resources():
|
|||||||
conn.close()
|
conn.close()
|
||||||
|
|
||||||
log_audit('CREATE', 'resource_pool', None,
|
log_audit('CREATE', 'resource_pool', None,
|
||||||
new_values={'type': resource_type, 'added': added, 'duplicates': duplicates},
|
new_values={'type': resource_type, 'added': added, 'duplicates': duplicates, 'is_test': is_test},
|
||||||
additional_info=f"{added} Ressourcen hinzugefügt, {duplicates} Duplikate übersprungen")
|
additional_info=f"{added} {'Test-' if is_test else ''}Ressourcen hinzugefügt, {duplicates} Duplikate übersprungen")
|
||||||
|
|
||||||
flash(f'{added} Ressourcen hinzugefügt, {duplicates} Duplikate übersprungen', 'success')
|
flash(f'{added} {"Test-" if is_test else ""}Ressourcen hinzugefügt, {duplicates} Duplikate übersprungen', 'success')
|
||||||
return redirect(url_for('resources'))
|
return redirect(url_for('resources', show_test=show_test))
|
||||||
|
|
||||||
return render_template('add_resources.html')
|
return render_template('add_resources.html', show_test=show_test)
|
||||||
|
|
||||||
@app.route('/resources/quarantine/<int:resource_id>', methods=['POST'])
|
@app.route('/resources/quarantine/<int:resource_id>', methods=['POST'])
|
||||||
@login_required
|
@login_required
|
||||||
|
|||||||
5
v2_adminpanel/mark_resources_as_test.sql
Normale Datei
5
v2_adminpanel/mark_resources_as_test.sql
Normale Datei
@@ -0,0 +1,5 @@
|
|||||||
|
-- Markiere alle existierenden Ressourcen als Testdaten
|
||||||
|
UPDATE resource_pools SET is_test = TRUE WHERE is_test = FALSE OR is_test IS NULL;
|
||||||
|
|
||||||
|
-- Zeige Anzahl der aktualisierten Ressourcen
|
||||||
|
SELECT COUNT(*) as updated_resources FROM resource_pools WHERE is_test = TRUE;
|
||||||
@@ -115,12 +115,12 @@
|
|||||||
<h1 class="mb-0">Ressourcen hinzufügen</h1>
|
<h1 class="mb-0">Ressourcen hinzufügen</h1>
|
||||||
<p class="text-muted mb-0">Fügen Sie neue Domains, IPs oder Telefonnummern zum Pool hinzu</p>
|
<p class="text-muted mb-0">Fügen Sie neue Domains, IPs oder Telefonnummern zum Pool hinzu</p>
|
||||||
</div>
|
</div>
|
||||||
<a href="{{ url_for('resources') }}" class="btn btn-secondary">
|
<a href="{{ url_for('resources', show_test=show_test) }}" class="btn btn-secondary">
|
||||||
← Zurück zur Übersicht
|
← Zurück zur Übersicht
|
||||||
</a>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<form method="post" action="{{ url_for('add_resources') }}" id="addResourceForm">
|
<form method="post" action="{{ url_for('add_resources', show_test=show_test) }}" id="addResourceForm">
|
||||||
<!-- Resource Type Selection -->
|
<!-- Resource Type Selection -->
|
||||||
<div class="card main-card mb-4">
|
<div class="card main-card mb-4">
|
||||||
<div class="card-header bg-white">
|
<div class="card-header bg-white">
|
||||||
@@ -265,12 +265,20 @@ my-website.io</pre>
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<!-- Test Data Option -->
|
||||||
|
<div class="form-check mt-3">
|
||||||
|
<input class="form-check-input" type="checkbox" id="is_test" name="is_test" {% if show_test %}checked{% endif %}>
|
||||||
|
<label class="form-check-label" for="is_test">
|
||||||
|
Als Testdaten markieren
|
||||||
|
</label>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Submit Buttons -->
|
<!-- Submit Buttons -->
|
||||||
<div class="d-flex justify-content-between">
|
<div class="d-flex justify-content-between">
|
||||||
<button type="button" class="btn btn-secondary" onclick="window.location.href='{{ url_for('resources') }}'">
|
<button type="button" class="btn btn-secondary" onclick="window.location.href='{{ url_for('resources', show_test=show_test) }}'">
|
||||||
<i class="fas fa-times"></i> Abbrechen
|
<i class="fas fa-times"></i> Abbrechen
|
||||||
</button>
|
</button>
|
||||||
<button type="submit" class="btn btn-success btn-lg" id="submitBtn" disabled>
|
<button type="submit" class="btn btn-success btn-lg" id="submitBtn" disabled>
|
||||||
|
|||||||
@@ -274,7 +274,7 @@
|
|||||||
<div class="card-header bg-primary text-white">
|
<div class="card-header bg-primary text-white">
|
||||||
<h5 class="mb-0">
|
<h5 class="mb-0">
|
||||||
<i class="fas fa-server"></i> Resource Pool Status
|
<i class="fas fa-server"></i> Resource Pool Status
|
||||||
<a href="/resources" class="btn btn-sm btn-light float-end">Verwalten →</a>
|
<a href="/resources{{ '?show_test=true' if request.args.get('show_test') == 'true' else '' }}" class="btn btn-sm btn-light float-end">Verwalten →</a>
|
||||||
</h5>
|
</h5>
|
||||||
</div>
|
</div>
|
||||||
<div class="card-body">
|
<div class="card-body">
|
||||||
@@ -311,7 +311,7 @@
|
|||||||
<div class="col-12 text-center text-muted">
|
<div class="col-12 text-center text-muted">
|
||||||
<i class="fas fa-inbox fa-3x mb-3"></i>
|
<i class="fas fa-inbox fa-3x mb-3"></i>
|
||||||
<p>Keine Ressourcen im Pool vorhanden.</p>
|
<p>Keine Ressourcen im Pool vorhanden.</p>
|
||||||
<a href="/resources/add" class="btn btn-primary">
|
<a href="/resources/add{{ '?show_test=true' if request.args.get('show_test') == 'true' else '' }}" class="btn btn-primary">
|
||||||
<i class="fas fa-plus"></i> Ressourcen hinzufügen
|
<i class="fas fa-plus"></i> Ressourcen hinzufügen
|
||||||
</a>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -175,18 +175,32 @@
|
|||||||
<p class="text-muted mb-0">Verwalten Sie Domains, IPs und Telefonnummern</p>
|
<p class="text-muted mb-0">Verwalten Sie Domains, IPs und Telefonnummern</p>
|
||||||
</div>
|
</div>
|
||||||
<div>
|
<div>
|
||||||
<a href="{{ url_for('add_resources') }}" class="btn btn-success">
|
<a href="{{ url_for('add_resources', show_test=show_test) }}" class="btn btn-success">
|
||||||
➕ Ressourcen hinzufügen
|
➕ Ressourcen hinzufügen
|
||||||
</a>
|
</a>
|
||||||
<a href="{{ url_for('resources_metrics') }}" class="btn btn-info">
|
<a href="{{ url_for('resources_metrics', show_test=show_test) }}" class="btn btn-info">
|
||||||
📊 Metriken
|
📊 Metriken
|
||||||
</a>
|
</a>
|
||||||
<a href="{{ url_for('resources_report') }}" class="btn btn-secondary">
|
<a href="{{ url_for('resources_report', show_test=show_test) }}" class="btn btn-secondary">
|
||||||
📄 Report
|
📄 Report
|
||||||
</a>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<!-- Test/Live Mode Toggle -->
|
||||||
|
<div class="card mb-3">
|
||||||
|
<div class="card-body py-2">
|
||||||
|
<div class="form-check mb-0">
|
||||||
|
<input class="form-check-input" type="checkbox" id="showTestResources"
|
||||||
|
{% if show_test %}checked{% endif %}
|
||||||
|
onchange="toggleTestResources()">
|
||||||
|
<label class="form-check-label" for="showTestResources">
|
||||||
|
Testressourcen anzeigen
|
||||||
|
</label>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<!-- Statistik-Karten -->
|
<!-- Statistik-Karten -->
|
||||||
<div class="row g-4 mb-4">
|
<div class="row g-4 mb-4">
|
||||||
{% for type, data in stats.items() %}
|
{% for type, data in stats.items() %}
|
||||||
@@ -246,6 +260,7 @@
|
|||||||
<div class="card filter-card mb-4">
|
<div class="card filter-card mb-4">
|
||||||
<div class="card-body">
|
<div class="card-body">
|
||||||
<form method="get" action="{{ url_for('resources') }}" id="filterForm">
|
<form method="get" action="{{ url_for('resources') }}" id="filterForm">
|
||||||
|
<input type="hidden" name="show_test" value="{{ 'true' if show_test else 'false' }}">
|
||||||
<div class="row g-3">
|
<div class="row g-3">
|
||||||
<div class="col-md-3">
|
<div class="col-md-3">
|
||||||
<label for="type" class="form-label">🏷️ Typ</label>
|
<label for="type" class="form-label">🏷️ Typ</label>
|
||||||
@@ -272,7 +287,7 @@
|
|||||||
</div>
|
</div>
|
||||||
<div class="col-md-2">
|
<div class="col-md-2">
|
||||||
<label class="form-label"> </label>
|
<label class="form-label"> </label>
|
||||||
<a href="{{ url_for('resources') }}" class="btn btn-secondary w-100">
|
<a href="{{ url_for('resources', show_test=show_test) }}" class="btn btn-secondary w-100">
|
||||||
🔄 Zurücksetzen
|
🔄 Zurücksetzen
|
||||||
</a>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
@@ -417,13 +432,13 @@
|
|||||||
<ul class="pagination justify-content-center">
|
<ul class="pagination justify-content-center">
|
||||||
<li class="page-item {% if page == 1 %}disabled{% endif %}">
|
<li class="page-item {% if page == 1 %}disabled{% endif %}">
|
||||||
<a class="page-link"
|
<a class="page-link"
|
||||||
href="{{ url_for('resources', page=1, type=resource_type, status=status_filter, search=search) }}">
|
href="{{ url_for('resources', page=1, type=resource_type, status=status_filter, search=search, show_test=show_test) }}">
|
||||||
<i class="fas fa-angle-double-left"></i> Erste
|
<i class="fas fa-angle-double-left"></i> Erste
|
||||||
</a>
|
</a>
|
||||||
</li>
|
</li>
|
||||||
<li class="page-item {% if page == 1 %}disabled{% endif %}">
|
<li class="page-item {% if page == 1 %}disabled{% endif %}">
|
||||||
<a class="page-link"
|
<a class="page-link"
|
||||||
href="{{ url_for('resources', page=page-1, type=resource_type, status=status_filter, search=search) }}">
|
href="{{ url_for('resources', page=page-1, type=resource_type, status=status_filter, search=search, show_test=show_test) }}">
|
||||||
<i class="fas fa-angle-left"></i> Zurück
|
<i class="fas fa-angle-left"></i> Zurück
|
||||||
</a>
|
</a>
|
||||||
</li>
|
</li>
|
||||||
@@ -432,7 +447,7 @@
|
|||||||
{% if p == page or (p >= page - 2 and p <= page + 2) %}
|
{% if p == page or (p >= page - 2 and p <= page + 2) %}
|
||||||
<li class="page-item {% if p == page %}active{% endif %}">
|
<li class="page-item {% if p == page %}active{% endif %}">
|
||||||
<a class="page-link"
|
<a class="page-link"
|
||||||
href="{{ url_for('resources', page=p, type=resource_type, status=status_filter, search=search) }}">
|
href="{{ url_for('resources', page=p, type=resource_type, status=status_filter, search=search, show_test=show_test) }}">
|
||||||
{{ p }}
|
{{ p }}
|
||||||
</a>
|
</a>
|
||||||
</li>
|
</li>
|
||||||
@@ -441,13 +456,13 @@
|
|||||||
|
|
||||||
<li class="page-item {% if page == total_pages %}disabled{% endif %}">
|
<li class="page-item {% if page == total_pages %}disabled{% endif %}">
|
||||||
<a class="page-link"
|
<a class="page-link"
|
||||||
href="{{ url_for('resources', page=page+1, type=resource_type, status=status_filter, search=search) }}">
|
href="{{ url_for('resources', page=page+1, type=resource_type, status=status_filter, search=search, show_test=show_test) }}">
|
||||||
Weiter <i class="fas fa-angle-right"></i>
|
Weiter <i class="fas fa-angle-right"></i>
|
||||||
</a>
|
</a>
|
||||||
</li>
|
</li>
|
||||||
<li class="page-item {% if page == total_pages %}disabled{% endif %}">
|
<li class="page-item {% if page == total_pages %}disabled{% endif %}">
|
||||||
<a class="page-link"
|
<a class="page-link"
|
||||||
href="{{ url_for('resources', page=total_pages, type=resource_type, status=status_filter, search=search) }}">
|
href="{{ url_for('resources', page=total_pages, type=resource_type, status=status_filter, search=search, show_test=show_test) }}">
|
||||||
Letzte <i class="fas fa-angle-double-right"></i>
|
Letzte <i class="fas fa-angle-double-right"></i>
|
||||||
</a>
|
</a>
|
||||||
</li>
|
</li>
|
||||||
@@ -596,5 +611,13 @@ function showQuarantineModal(resourceId) {
|
|||||||
form.setAttribute('action', `/resources/quarantine/${resourceId}`);
|
form.setAttribute('action', `/resources/quarantine/${resourceId}`);
|
||||||
modal.show();
|
modal.show();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Toggle Testressourcen
|
||||||
|
function toggleTestResources() {
|
||||||
|
const showTest = document.getElementById('showTestResources').checked;
|
||||||
|
const currentUrl = new URL(window.location);
|
||||||
|
currentUrl.searchParams.set('show_test', showTest);
|
||||||
|
window.location.href = currentUrl.toString();
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
{% endblock %}
|
{% endblock %}
|
||||||
In neuem Issue referenzieren
Einen Benutzer sperren