Enhance CyberPanel functionality with FTP Quota and Bandwidth Management features: Added models, views, and templates for managing FTP quotas and bandwidth resets. Implemented IP blocking functionality with associated views and templates. Updated system scripts for improved repository synchronization and OS detection. Removed outdated workflow files.

This commit is contained in:
Master3395
2025-09-23 21:09:38 +02:00
parent 11991c0f80
commit 2c57ad595e
23 changed files with 2278 additions and 903 deletions

View File

@@ -0,0 +1,322 @@
{% extends "baseTemplate/index.html" %}
{% load static %}
{% block title %}
Security Management - CyberPanel
{% endblock %}
{% block content %}
<div class="container-fluid">
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-header">
<h3 class="card-title">
<i class="fas fa-shield-alt"></i>
Security Management
</h3>
</div>
<div class="card-body">
<!-- Security Alerts Section -->
<div class="row mb-4">
<div class="col-12">
<div class="alert alert-warning">
<h5><i class="fas fa-exclamation-triangle"></i> Security Alerts</h5>
<p>Monitor and manage security threats detected by the system.</p>
<button class="btn btn-warning" onclick="refreshSecurityAlerts()">
<i class="fas fa-sync"></i> Refresh Alerts
</button>
</div>
</div>
</div>
<!-- Security Alerts List -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-header">
<h4>Recent Security Alerts</h4>
</div>
<div class="card-body">
<div id="securityAlertsContainer">
<!-- Alerts will be loaded here -->
<div class="text-center">
<i class="fas fa-spinner fa-spin"></i> Loading security alerts...
</div>
</div>
</div>
</div>
</div>
</div>
<!-- Blocked IPs Management -->
<div class="row mt-4">
<div class="col-12">
<div class="card">
<div class="card-header">
<h4>Blocked IP Addresses</h4>
<button class="btn btn-success btn-sm" onclick="refreshBlockedIPs()">
<i class="fas fa-sync"></i> Refresh
</button>
</div>
<div class="card-body">
<div class="table-responsive">
<table class="table table-striped" id="blockedIPsTable">
<thead>
<tr>
<th>IP Address</th>
<th>Blocked At</th>
<th>Reason</th>
<th>Actions</th>
</tr>
</thead>
<tbody id="blockedIPsTableBody">
<tr>
<td colspan="4" class="text-center">
<i class="fas fa-spinner fa-spin"></i> Loading...
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</div>
</div>
<!-- Manual IP Blocking -->
<div class="row mt-4">
<div class="col-12">
<div class="card">
<div class="card-header">
<h4>Manual IP Blocking</h4>
</div>
<div class="card-body">
<form id="blockIPForm">
<div class="row">
<div class="col-md-6">
<div class="form-group">
<label for="ipAddress">IP Address</label>
<input type="text" class="form-control" id="ipAddress" name="ip_address" placeholder="192.168.1.100" required>
</div>
</div>
<div class="col-md-6">
<div class="form-group">
<label for="blockReason">Reason</label>
<input type="text" class="form-control" id="blockReason" name="reason" placeholder="Suspicious activity" value="Manual block via CyberPanel">
</div>
</div>
</div>
<button type="submit" class="btn btn-danger">
<i class="fas fa-ban"></i> Block IP Address
</button>
</form>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
<script>
// Sample security alerts data (in a real implementation, this would come from the backend)
const sampleAlerts = [
{
id: 1,
type: 'brute_force',
ip: '129.212.176.254',
attempts: 85,
severity: 'HIGH',
timestamp: '2024-01-15 14:30:25',
description: 'IP address 129.212.176.254 has made 85 failed password attempts. This indicates a potential brute force attack.'
},
{
id: 2,
type: 'brute_force',
ip: '177.10.47.186',
attempts: 10,
severity: 'HIGH',
timestamp: '2024-01-15 14:25:10',
description: 'IP address 177.10.47.186 has made 10 failed password attempts. This indicates a potential brute force attack.'
}
];
function refreshSecurityAlerts() {
const container = document.getElementById('securityAlertsContainer');
if (sampleAlerts.length === 0) {
container.innerHTML = '<div class="alert alert-info">No security alerts found.</div>';
return;
}
let html = '';
sampleAlerts.forEach(alert => {
const severityClass = alert.severity === 'HIGH' ? 'danger' : alert.severity === 'MEDIUM' ? 'warning' : 'info';
html += `
<div class="alert alert-${severityClass} mb-3">
<div class="d-flex justify-content-between align-items-start">
<div>
<h6 class="alert-heading">
<i class="fas fa-exclamation-triangle"></i>
${alert.type.replace('_', ' ').toUpperCase()} Attack Detected
</h6>
<p class="mb-2">${alert.description}</p>
<div class="row">
<div class="col-md-3">
<strong>IP Address:</strong> ${alert.ip}
</div>
<div class="col-md-3">
<strong>Failed Attempts:</strong> ${alert.attempts}
</div>
<div class="col-md-3">
<strong>Attack Type:</strong> Brute Force
</div>
<div class="col-md-3">
<strong>Time:</strong> ${alert.timestamp}
</div>
</div>
</div>
<div class="ml-3">
<span class="badge badge-${severityClass}">${alert.severity}</span>
<div class="mt-2">
<button class="btn btn-sm btn-danger" onclick="blockIP('${alert.ip}', 'Brute force attack - ${alert.attempts} attempts')">
<i class="fas fa-ban"></i> Block IP
</button>
</div>
</div>
</div>
</div>
`;
});
container.innerHTML = html;
}
function blockIP(ipAddress, reason) {
if (!confirm(`Are you sure you want to block IP address ${ipAddress}?`)) {
return;
}
const formData = {
'csrfmiddlewaretoken': '{{ csrf_token }}',
'ip_address': ipAddress,
'reason': reason
};
$.post('{% url "blockIPAddress" %}', formData, function(data) {
if (data.status === 1) {
showNotification('success', data.message);
refreshBlockedIPs();
refreshSecurityAlerts(); // Refresh to remove the alert or update its status
} else {
showNotification('error', data.message);
}
});
}
function unblockIP(ipAddress) {
if (!confirm(`Are you sure you want to unblock IP address ${ipAddress}?`)) {
return;
}
const formData = {
'csrfmiddlewaretoken': '{{ csrf_token }}',
'ip_address': ipAddress
};
$.post('{% url "unblockIPAddress" %}', formData, function(data) {
if (data.status === 1) {
showNotification('success', data.message);
refreshBlockedIPs();
} else {
showNotification('error', data.message);
}
});
}
function refreshBlockedIPs() {
$.post('{% url "getBlockedIPs" %}', {
'csrfmiddlewaretoken': '{{ csrf_token }}'
}, function(data) {
if (data.status === 1) {
displayBlockedIPs(data.blocked_ips);
} else {
showNotification('error', data.message);
}
});
}
function displayBlockedIPs(blockedIPs) {
const tbody = document.getElementById('blockedIPsTableBody');
if (blockedIPs.length === 0) {
tbody.innerHTML = '<tr><td colspan="4" class="text-center">No blocked IP addresses found</td></tr>';
return;
}
let html = '';
blockedIPs.forEach(ip => {
html += `
<tr>
<td>${ip}</td>
<td>N/A</td>
<td>Blocked via CyberPanel</td>
<td>
<button class="btn btn-sm btn-warning" onclick="unblockIP('${ip}')">
<i class="fas fa-unlock"></i> Unblock
</button>
</td>
</tr>
`;
});
tbody.innerHTML = html;
}
function showNotification(type, message) {
const alertClass = type === 'success' ? 'alert-success' : 'alert-danger';
const icon = type === 'success' ? 'fa-check-circle' : 'fa-exclamation-circle';
const notification = `
<div class="alert ${alertClass} alert-dismissible fade show" role="alert">
<i class="fas ${icon}"></i> ${message}
<button type="button" class="close" data-dismiss="alert">
<span>&times;</span>
</button>
</div>
`;
$('.card-body').prepend(notification);
setTimeout(() => {
$('.alert').fadeOut();
}, 5000);
}
// Handle manual IP blocking form
$(document).ready(function() {
$('#blockIPForm').on('submit', function(e) {
e.preventDefault();
const ipAddress = $('#ipAddress').val();
const reason = $('#blockReason').val();
if (!ipAddress) {
showNotification('error', 'Please enter an IP address');
return;
}
blockIP(ipAddress, reason);
$('#blockIPForm')[0].reset();
});
// Load initial data
refreshSecurityAlerts();
refreshBlockedIPs();
});
</script>
{% endblock %}