mirror of
https://github.com/eduardogsilva/wireguard_webadmin.git
synced 2025-04-19 08:55:12 +00:00
Add user permissions for reload and restart
This commit is contained in:
parent
b140362e86
commit
a58d233546
@ -251,16 +251,26 @@
|
|||||||
Your WireGuard settings have been modified. To apply these changes, please update the configuration and reload the WireGuard service.
|
Your WireGuard settings have been modified. To apply these changes, please update the configuration and reload the WireGuard service.
|
||||||
</p>
|
</p>
|
||||||
<p>
|
<p>
|
||||||
<a href="/tools/export_wireguard_config/?action=update_and_restart" class="btn btn-secondary">Update and restart service</a>
|
<a
|
||||||
<a href="/tools/export_wireguard_config/?action=update_and_reload" class="btn btn-secondary">Update and reload service</a>
|
{% if user_acl.enable_restart %}
|
||||||
|
href="/tools/export_wireguard_config/?action=update_and_restart" class="btn btn-secondary"
|
||||||
|
{% else %}
|
||||||
|
href="#" class="btn btn-secondary disabled"
|
||||||
|
{% endif %}
|
||||||
|
>Update and restart service</a>
|
||||||
|
|
||||||
|
<a
|
||||||
|
{% if user_acl.enable_reload %}
|
||||||
|
href="/tools/export_wireguard_config/?action=update_and_reload" class="btn btn-secondary"
|
||||||
|
{% else %}
|
||||||
|
href="#" class="btn btn-secondary disabled"
|
||||||
|
{% endif %}
|
||||||
|
>Update and reload service</a>
|
||||||
</p>
|
</p>
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
{% block content %}{% endblock %}
|
{% block content %}{% endblock %}
|
||||||
</div><!-- /.container-fluid -->
|
</div><!-- /.container-fluid -->
|
||||||
</section>
|
</section>
|
||||||
|
@ -1,15 +1,14 @@
|
|||||||
{% extends "base.html" %}
|
{% extends "base.html" %}
|
||||||
|
|
||||||
{% block content %}
|
{% block content %}
|
||||||
<table class="table table-striped">
|
<table class="table table-striped table-bordered">
|
||||||
<thead>
|
<thead>
|
||||||
<tr>
|
<tr>
|
||||||
<th>Username</th>
|
<th>Username</th>
|
||||||
<th>User Level</th>
|
<th>User Level</th>
|
||||||
<th>Peer Groups</th>
|
<th>Peer Groups</th>
|
||||||
<th></th>
|
<th colspan="4">Permissions</th>
|
||||||
<th></th>
|
<th><i class="far fa-edit"></i></th>
|
||||||
<th></th>
|
|
||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
<tbody>
|
<tbody>
|
||||||
@ -26,16 +25,29 @@
|
|||||||
Any
|
Any
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</td>
|
</td>
|
||||||
|
<td style="width: 1%; white-space: nowrap;">
|
||||||
|
{% if user_acl.enable_restart %}
|
||||||
|
<i class="fas fa-power-off" title="Restart Enabled"></i>
|
||||||
|
{% endif %}
|
||||||
|
</td>
|
||||||
|
<td style="width: 1%; white-space: nowrap;">
|
||||||
|
{% if user_acl.enable_reload %}
|
||||||
|
<i class="fas fa-sync-alt" title="Reload Enabled"></i>
|
||||||
|
{% endif %}
|
||||||
|
</td>
|
||||||
|
|
||||||
<td style="width: 1%; white-space: nowrap;">
|
<td style="width: 1%; white-space: nowrap;">
|
||||||
{% if user_acl.enable_console %}
|
{% if user_acl.enable_console %}
|
||||||
<i class="fas fa-terminal" title="Console Enabled"></i>
|
<i class="fas fa-terminal" title="Console Enabled"></i>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</td>
|
</td>
|
||||||
|
|
||||||
<td style="width: 1%; white-space: nowrap;">
|
<td style="width: 1%; white-space: nowrap;">
|
||||||
{% if user_acl.enable_enhanced_filter %}
|
{% if user_acl.enable_enhanced_filter %}
|
||||||
<i class="fas fa-eye-slash" title="Enhanced Filter Enabled"></i>
|
<i class="fas fa-eye-slash" title="Enhanced Filter Enabled"></i>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</td>
|
</td>
|
||||||
|
|
||||||
<td style="width: 1%; white-space: nowrap;">
|
<td style="width: 1%; white-space: nowrap;">
|
||||||
<a href="/user/manage/?uuid={{ user_acl.uuid }}" ><i class="far fa-edit"></i></a>
|
<a href="/user/manage/?uuid={{ user_acl.uuid }}" ><i class="far fa-edit"></i></a>
|
||||||
</td>
|
</td>
|
||||||
|
@ -7,8 +7,21 @@
|
|||||||
<div class="card card-primary card-outline">
|
<div class="card card-primary card-outline">
|
||||||
<div class="card-header">
|
<div class="card-header">
|
||||||
<a href='/tools/export_wireguard_config/' class='btn btn-outline-primary'>Update Configuration</a>
|
<a href='/tools/export_wireguard_config/' class='btn btn-outline-primary'>Update Configuration</a>
|
||||||
<a href='/tools/restart_wireguard/' class='btn btn-outline-primary'>Restart Wireguard service</a>
|
<a
|
||||||
<a href='/tools/restart_wireguard/?mode=reload' class='btn btn-outline-primary'>Reload Wireguard service</a>
|
{% if user_acl.enable_restart %}
|
||||||
|
href='/tools/restart_wireguard/' class='btn btn-outline-primary'
|
||||||
|
{% else %}
|
||||||
|
href='#' class='btn btn-outline-primary disabled'
|
||||||
|
{% endif %}
|
||||||
|
>Restart Wireguard service</a>
|
||||||
|
|
||||||
|
<a
|
||||||
|
{% if user_acl.enable_reload %}
|
||||||
|
href='/tools/restart_wireguard/?mode=reload' class='btn btn-outline-primary'
|
||||||
|
{% else %}
|
||||||
|
href='#' class='btn btn-outline-primary disabled'
|
||||||
|
{% endif %}
|
||||||
|
>Reload Wireguard service</a>
|
||||||
|
|
||||||
<div class="btn-group float-right" role="group" aria-label="Graph interval">
|
<div class="btn-group float-right" role="group" aria-label="Graph interval">
|
||||||
<a href="?period=6h" data-period="6h" class="btn btn-outline-primary">6h</a>
|
<a href="?period=6h" data-period="6h" class="btn btn-outline-primary">6h</a>
|
||||||
|
@ -1,11 +1,11 @@
|
|||||||
from django import forms
|
|
||||||
from django.contrib.auth.forms import UserCreationForm
|
|
||||||
from django.contrib.auth.models import User
|
|
||||||
from .models import UserAcl
|
|
||||||
from django.core.exceptions import ValidationError
|
|
||||||
from wireguard.models import PeerGroup
|
|
||||||
from crispy_forms.helper import FormHelper
|
from crispy_forms.helper import FormHelper
|
||||||
from crispy_forms.layout import Layout, Row, Column, Submit, HTML
|
from crispy_forms.layout import Column, HTML, Layout, Row, Submit
|
||||||
|
from django import forms
|
||||||
|
from django.contrib.auth.models import User
|
||||||
|
from django.core.exceptions import ValidationError
|
||||||
|
|
||||||
|
from wireguard.models import PeerGroup
|
||||||
|
from .models import UserAcl
|
||||||
|
|
||||||
|
|
||||||
class UserAclForm(forms.Form):
|
class UserAclForm(forms.Form):
|
||||||
@ -13,6 +13,8 @@ class UserAclForm(forms.Form):
|
|||||||
password1 = forms.CharField(widget=forms.PasswordInput, required=False, label="Password")
|
password1 = forms.CharField(widget=forms.PasswordInput, required=False, label="Password")
|
||||||
password2 = forms.CharField(widget=forms.PasswordInput, required=False, label="Password confirmation")
|
password2 = forms.CharField(widget=forms.PasswordInput, required=False, label="Password confirmation")
|
||||||
enable_console = forms.BooleanField(required=False, label="Enable Console")
|
enable_console = forms.BooleanField(required=False, label="Enable Console")
|
||||||
|
enable_reload = forms.BooleanField(required=False, label="Enable Reload")
|
||||||
|
enable_restart = forms.BooleanField(required=False, label="Enable Restart")
|
||||||
enable_enhanced_filter = forms.BooleanField(required=False, label="Enable Enhanced Filter")
|
enable_enhanced_filter = forms.BooleanField(required=False, label="Enable Enhanced Filter")
|
||||||
user_level = forms.ChoiceField(choices=UserAcl.user_level.field.choices, required=True, label="User Level")
|
user_level = forms.ChoiceField(choices=UserAcl.user_level.field.choices, required=True, label="User Level")
|
||||||
peer_groups = forms.ModelMultipleChoiceField(
|
peer_groups = forms.ModelMultipleChoiceField(
|
||||||
@ -30,14 +32,20 @@ class UserAclForm(forms.Form):
|
|||||||
self.fields['username'].widget.attrs['readonly'] = True
|
self.fields['username'].widget.attrs['readonly'] = True
|
||||||
self.fields['peer_groups'].initial = self.instance.useracl.peer_groups.all()
|
self.fields['peer_groups'].initial = self.instance.useracl.peer_groups.all()
|
||||||
self.fields['enable_console'].initial = self.instance.useracl.enable_console
|
self.fields['enable_console'].initial = self.instance.useracl.enable_console
|
||||||
|
self.fields['enable_reload'].initial = self.instance.useracl.enable_reload
|
||||||
|
self.fields['enable_restart'].initial = self.instance.useracl.enable_restart
|
||||||
self.fields['enable_enhanced_filter'].initial = self.instance.useracl.enable_enhanced_filter
|
self.fields['enable_enhanced_filter'].initial = self.instance.useracl.enable_enhanced_filter
|
||||||
else:
|
else:
|
||||||
self.fields['password1'].required = True
|
self.fields['password1'].required = True
|
||||||
self.fields['password2'].required = True
|
self.fields['password2'].required = True
|
||||||
self.fields['enable_console'].initial = True
|
self.fields['enable_console'].initial = True
|
||||||
|
self.fields['enable_reload'].initial = True
|
||||||
|
self.fields['enable_restart'].initial = True
|
||||||
self.fields['enable_enhanced_filter'].initial = False
|
self.fields['enable_enhanced_filter'].initial = False
|
||||||
|
|
||||||
self.fields['enable_console'].label = "Console"
|
self.fields['enable_console'].label = "Console"
|
||||||
|
self.fields['enable_reload'].label = "Reload"
|
||||||
|
self.fields['enable_restart'].label = "Restart"
|
||||||
self.fields['enable_enhanced_filter'].label = "Enhanced Filter"
|
self.fields['enable_enhanced_filter'].label = "Enhanced Filter"
|
||||||
|
|
||||||
self.helper = FormHelper()
|
self.helper = FormHelper()
|
||||||
@ -73,6 +81,14 @@ class UserAclForm(forms.Form):
|
|||||||
Column('enable_console', css_class='form-group col-md-12 mb-0'),
|
Column('enable_console', css_class='form-group col-md-12 mb-0'),
|
||||||
css_class='form-row'
|
css_class='form-row'
|
||||||
),
|
),
|
||||||
|
Row(
|
||||||
|
Column('enable_reload', css_class='form-group col-md-12 mb-0'),
|
||||||
|
css_class='form-row'
|
||||||
|
),
|
||||||
|
Row(
|
||||||
|
Column('enable_restart', css_class='form-group col-md-12 mb-0'),
|
||||||
|
css_class='form-row'
|
||||||
|
),
|
||||||
Row(
|
Row(
|
||||||
Column('enable_enhanced_filter', css_class='form-group col-md-12 mb-0'),
|
Column('enable_enhanced_filter', css_class='form-group col-md-12 mb-0'),
|
||||||
css_class='form-row'
|
css_class='form-row'
|
||||||
@ -118,6 +134,8 @@ class UserAclForm(forms.Form):
|
|||||||
user_level = self.cleaned_data['user_level']
|
user_level = self.cleaned_data['user_level']
|
||||||
peer_groups = self.cleaned_data.get('peer_groups', [])
|
peer_groups = self.cleaned_data.get('peer_groups', [])
|
||||||
enable_console = self.cleaned_data.get('enable_console', False)
|
enable_console = self.cleaned_data.get('enable_console', False)
|
||||||
|
enable_reload = self.cleaned_data.get('enable_reload', False)
|
||||||
|
enable_restart = self.cleaned_data.get('enable_restart', False)
|
||||||
enable_enhanced_filter = self.cleaned_data.get('enable_enhanced_filter', False)
|
enable_enhanced_filter = self.cleaned_data.get('enable_enhanced_filter', False)
|
||||||
|
|
||||||
if self.instance:
|
if self.instance:
|
||||||
@ -136,6 +154,8 @@ class UserAclForm(forms.Form):
|
|||||||
defaults={
|
defaults={
|
||||||
'user_level': user_level,
|
'user_level': user_level,
|
||||||
'enable_console': enable_console,
|
'enable_console': enable_console,
|
||||||
|
'enable_reload': enable_reload,
|
||||||
|
'enable_restart': enable_restart,
|
||||||
'enable_enhanced_filter': enable_enhanced_filter
|
'enable_enhanced_filter': enable_enhanced_filter
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
@ -0,0 +1,23 @@
|
|||||||
|
# Generated by Django 5.2 on 2025-04-11 13:18
|
||||||
|
|
||||||
|
from django.db import migrations, models
|
||||||
|
|
||||||
|
|
||||||
|
class Migration(migrations.Migration):
|
||||||
|
|
||||||
|
dependencies = [
|
||||||
|
('user_manager', '0005_useracl_enable_console_and_more'),
|
||||||
|
]
|
||||||
|
|
||||||
|
operations = [
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='useracl',
|
||||||
|
name='enable_reload',
|
||||||
|
field=models.BooleanField(default=True),
|
||||||
|
),
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='useracl',
|
||||||
|
name='enable_restart',
|
||||||
|
field=models.BooleanField(default=True),
|
||||||
|
),
|
||||||
|
]
|
@ -1,6 +1,8 @@
|
|||||||
from django.db import models
|
|
||||||
from django.contrib.auth.models import User
|
|
||||||
import uuid
|
import uuid
|
||||||
|
|
||||||
|
from django.contrib.auth.models import User
|
||||||
|
from django.db import models
|
||||||
|
|
||||||
from wireguard.models import PeerGroup
|
from wireguard.models import PeerGroup
|
||||||
|
|
||||||
|
|
||||||
@ -16,6 +18,8 @@ class UserAcl(models.Model):
|
|||||||
peer_groups = models.ManyToManyField(PeerGroup, blank=True)
|
peer_groups = models.ManyToManyField(PeerGroup, blank=True)
|
||||||
enable_console = models.BooleanField(default=True)
|
enable_console = models.BooleanField(default=True)
|
||||||
enable_enhanced_filter = models.BooleanField(default=False)
|
enable_enhanced_filter = models.BooleanField(default=False)
|
||||||
|
enable_reload = models.BooleanField(default=True)
|
||||||
|
enable_restart = models.BooleanField(default=True)
|
||||||
|
|
||||||
created = models.DateTimeField(auto_now_add=True)
|
created = models.DateTimeField(auto_now_add=True)
|
||||||
updated = models.DateTimeField(auto_now=True)
|
updated = models.DateTimeField(auto_now=True)
|
||||||
|
@ -1,9 +1,11 @@
|
|||||||
|
from user_manager.models import UserAcl
|
||||||
from .models import WireGuardInstance
|
from .models import WireGuardInstance
|
||||||
|
|
||||||
|
|
||||||
def pending_changes_warning(request):
|
def pending_changes_warning(request):
|
||||||
|
user_acl = UserAcl.objects.filter(user=request.user).first()
|
||||||
if request.user.is_authenticated:
|
if request.user.is_authenticated:
|
||||||
pending = WireGuardInstance.objects.filter(pending_changes=True).exists()
|
pending = WireGuardInstance.objects.filter(pending_changes=True).exists()
|
||||||
else:
|
else:
|
||||||
pending = False
|
pending = False
|
||||||
return {'pending_changes_warning': pending}
|
return {'pending_changes_warning': pending, 'user_acl': user_acl}
|
||||||
|
@ -218,7 +218,8 @@ def download_config_or_qrcode(request):
|
|||||||
|
|
||||||
@login_required
|
@login_required
|
||||||
def restart_wireguard_interfaces(request):
|
def restart_wireguard_interfaces(request):
|
||||||
if not UserAcl.objects.filter(user=request.user).filter(user_level__gte=30).exists():
|
user_acl = UserAcl.objects.filter(user=request.user).filter(user_level__gte=30).first()
|
||||||
|
if not user_acl:
|
||||||
return render(request, 'access_denied.html', {'page_title': 'Access Denied'})
|
return render(request, 'access_denied.html', {'page_title': 'Access Denied'})
|
||||||
mode = request.GET.get('mode', 'restart')
|
mode = request.GET.get('mode', 'restart')
|
||||||
config_dir = "/etc/wireguard"
|
config_dir = "/etc/wireguard"
|
||||||
@ -228,6 +229,9 @@ def restart_wireguard_interfaces(request):
|
|||||||
if filename.endswith(".conf"):
|
if filename.endswith(".conf"):
|
||||||
interface_name = filename[:-5]
|
interface_name = filename[:-5]
|
||||||
if mode == "reload":
|
if mode == "reload":
|
||||||
|
if not user_acl.enable_reload:
|
||||||
|
return render(request, 'access_denied.html', {'page_title': 'Access Denied'})
|
||||||
|
|
||||||
config_path = os.path.join(config_dir, filename)
|
config_path = os.path.join(config_dir, filename)
|
||||||
with open(config_path, 'r') as f:
|
with open(config_path, 'r') as f:
|
||||||
lines = f.readlines()
|
lines = f.readlines()
|
||||||
@ -253,6 +257,9 @@ def restart_wireguard_interfaces(request):
|
|||||||
interface_count += 1
|
interface_count += 1
|
||||||
|
|
||||||
else:
|
else:
|
||||||
|
if not user_acl.enable_restart:
|
||||||
|
return render(request, 'access_denied.html', {'page_title': 'Access Denied'})
|
||||||
|
|
||||||
stop_command = f"wg-quick down {interface_name}"
|
stop_command = f"wg-quick down {interface_name}"
|
||||||
stop_result = subprocess.run(stop_command, shell=True, capture_output=True, text=True)
|
stop_result = subprocess.run(stop_command, shell=True, capture_output=True, text=True)
|
||||||
if stop_result.returncode != 0:
|
if stop_result.returncode != 0:
|
||||||
|
@ -136,6 +136,6 @@ STATICFILES_DIRS = [
|
|||||||
DNS_CONFIG_FILE = '/etc/dnsmasq/wireguard_webadmin_dns.conf'
|
DNS_CONFIG_FILE = '/etc/dnsmasq/wireguard_webadmin_dns.conf'
|
||||||
DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'
|
DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'
|
||||||
|
|
||||||
WIREGUARD_WEBADMIN_VERSION = 9963
|
WIREGUARD_WEBADMIN_VERSION = 9964
|
||||||
|
|
||||||
from wireguard_webadmin.production_settings import *
|
from wireguard_webadmin.production_settings import *
|
||||||
|
Loading…
x
Reference in New Issue
Block a user