Verified Commit 6614841e authored by erdnaxe's avatar erdnaxe 🎇

Continue to move models from machines to admin

parent 7bbef849
Pipeline #1112 passed with stage
in 2 minutes and 57 seconds
......@@ -14,12 +14,16 @@ from django.contrib import admin
from reversion.admin import VersionAdmin
from .models import (
Extension,
DName,
Extension,
IpType,
MachineType,
Mx,
Nas,
Ns,
OuverturePort,
OuverturePortList,
Role,
SOA,
Srv,
Txt,
......@@ -27,16 +31,25 @@ from .models import (
)
@admin.register(DName)
class DNameAdmin(VersionAdmin):
"""Admin view of a DName object"""
list_display = ('zone', 'alias')
@admin.register(Extension)
class ExtensionAdmin(VersionAdmin):
"""Admin view of a Extension object"""
list_display = ('name', 'need_infra', 'origin', 'soa', 'dnssec')
@admin.register(DName)
class DNameAdmin(VersionAdmin):
"""Admin view of a DName object"""
list_display = ('zone', 'alias')
@admin.register(IpType)
class IpTypeAdmin(VersionAdmin):
"""Admin view of a IpType object"""
list_display = (
'name', 'extension', 'need_infra', 'prefix_v6', 'vlan',
'ouverture_ports')
list_filter = ('need_infra',)
@admin.register(MachineType)
......@@ -72,6 +85,45 @@ class SrvAdmin(VersionAdmin):
'weight', 'port', 'target')
class OuverturePortInline(admin.TabularInline):
"""A inline for OuverturePortListAdmin, represents one range of ports"""
model = OuverturePort
extra = 1
@admin.register(OuverturePortList)
class OuverturePortListAdmin(VersionAdmin):
"""Admin view of a OuverturePortList object"""
list_display = ('name', 'tcp_in', 'tcp_out', 'udp_in', 'udp_out')
inlines = (OuverturePortInline,)
# TODO(erdnaxe): add machines list
def tcp_in(self, obj):
return None
def tcp_out(self, obj):
return None
def udp_in(self, obj):
return None
def udp_out(self, obj):
return None
@admin.register(Role)
class RoleAdmin(VersionAdmin):
"""Admin view of a Role object"""
list_display = ('role_type', 'specific_role', 'servers')
# TODO(erdnaxe): investigate why it was buggy before switching to admin
# TODO(erdnaxe): print machines on change list like in edit mode
# role_list = (Role.objects
# .prefetch_related(
# 'servers__domain__extension'
# ).all())
@admin.register(SOA)
class SOAAdmin(VersionAdmin):
"""Admin view of a SOA object"""
......
......@@ -18,8 +18,6 @@ Formulaires d'ajout, edition et suppressions de :
- ports ouverts et profils d'ouverture par interface
"""
from __future__ import unicode_literals
from django import forms
from django.forms import ModelForm, Form
from django.utils.translation import ugettext_lazy as _
......@@ -33,11 +31,9 @@ from .models import (
IpList,
MachineType,
Extension,
Role,
Service,
SshFp,
IpType,
OuverturePortList,
Ipv6List,
)
......@@ -217,39 +213,6 @@ class Ipv6ListForm(FormRevMixin, FieldPermissionFormMixin, ModelForm):
super(Ipv6ListForm, self).__init__(*args, prefix=prefix, **kwargs)
class RoleForm(FormRevMixin, ModelForm):
"""Add and edit role."""
class Meta:
model = Role
fields = '__all__'
def __init__(self, *args, **kwargs):
prefix = kwargs.pop('prefix', self.Meta.model.__name__)
super(RoleForm, self).__init__(*args, prefix=prefix, **kwargs)
self.fields['servers'].queryset = (Interface.objects.all()
.select_related(
'domain__extension'
))
class DelRoleForm(FormRevMixin, Form):
"""Deletion of one or several roles."""
role = forms.ModelMultipleChoiceField(
queryset=Role.objects.none(),
label=_("Current roles"),
widget=forms.CheckboxSelectMultiple
)
def __init__(self, *args, **kwargs):
instances = kwargs.pop('instances', None)
super(DelRoleForm, self).__init__(*args, **kwargs)
if instances:
self.fields['role'].queryset = instances
else:
self.fields['role'].queryset = Role.objects.all()
class ServiceForm(FormRevMixin, ModelForm):
"""Ajout et edition d'une classe de service : dns, dhcp, etc"""
......@@ -309,23 +272,6 @@ class EditOuverturePortConfigForm(FormRevMixin, ModelForm):
)
class EditOuverturePortListForm(FormRevMixin, ModelForm):
"""Edition de la liste des ports et profils d'ouverture
des ports"""
class Meta:
model = OuverturePortList
fields = '__all__'
def __init__(self, *args, **kwargs):
prefix = kwargs.pop('prefix', self.Meta.model.__name__)
super(EditOuverturePortListForm, self).__init__(
*args,
prefix=prefix,
**kwargs
)
class SshFpForm(FormRevMixin, ModelForm):
"""Edits a SSHFP record."""
......
This diff is collapsed.
......@@ -282,17 +282,36 @@ class MachineType(RevMixin, AclMixin, models.Model):
class IpType(RevMixin, AclMixin, models.Model):
""" Type d'ip, définissant un range d'ip, affecté aux machine types"""
name = models.CharField(max_length=255)
extension = models.ForeignKey('Extension', on_delete=models.PROTECT)
need_infra = models.BooleanField(default=False)
domaine_ip_start = models.GenericIPAddressField(protocol='IPv4')
domaine_ip_stop = models.GenericIPAddressField(protocol='IPv4')
"""IP range"""
name = models.CharField(
max_length=255,
verbose_name=_('name'),
)
extension = models.ForeignKey(
'Extension',
on_delete=models.PROTECT,
verbose_name=_('extension'),
)
need_infra = models.BooleanField(
default=False,
verbose_name=_("need infra role"),
help_text=_("When active, only users with the \"use_all_iptype\" "
"permission will be able to use this type of IP."),
)
domaine_ip_start = models.GenericIPAddressField(
protocol='IPv4',
verbose_name=_('IPv4 range start'),
)
domaine_ip_stop = models.GenericIPAddressField(
protocol='IPv4',
verbose_name=_('IPv4 range stop'),
)
domaine_ip_network = models.GenericIPAddressField(
protocol='IPv4',
null=True,
blank=True,
help_text=_("Network containing the domain's IPv4 range (optional)")
verbose_name=_('IPv4 network'),
help_text=_("Network containing the domain's IPv4 range (optional)."),
)
domaine_ip_netmask = models.IntegerField(
default=24,
......@@ -300,46 +319,51 @@ class IpType(RevMixin, AclMixin, models.Model):
MaxValueValidator(31),
MinValueValidator(8)
],
help_text=_("Netmask for the domain's IPv4 range")
verbose_name=_('IPv4 netmask'),
help_text=_("Netmask for this IPv4 range."),
)
reverse_v4 = models.BooleanField(
default=False,
help_text=_("Enable reverse DNS for IPv4"),
verbose_name=_("reverse DNS for IPv4"),
)
prefix_v6 = models.GenericIPAddressField(
protocol='IPv6',
null=True,
blank=True
blank=True,
verbose_name=_("IPv6 prefix"),
)
prefix_v6_length = models.IntegerField(
default=64,
validators=[
MaxValueValidator(128),
MinValueValidator(0)
]
],
verbose_name=_("IPv6 prefix lenght"),
)
reverse_v6 = models.BooleanField(
default=False,
help_text=_("Enable reverse DNS for IPv6"),
verbose_name=_("reverse DNS for IPv6"),
)
vlan = models.ForeignKey(
'Vlan',
on_delete=models.PROTECT,
blank=True,
null=True
null=True,
verbose_name=_("VLAN"),
)
ouverture_ports = models.ForeignKey(
'OuverturePortList',
blank=True,
null=True
null=True,
verbose_name=_("default open port profile"),
)
class Meta:
permissions = (
("use_all_iptype", _("Can use all IP types")),
)
verbose_name = _("IP type")
verbose_name_plural = _("IP types")
verbose_name = _("IP range")
verbose_name_plural = _("IP ranges")
@cached_property
def ip_range(self):
......@@ -1724,26 +1748,27 @@ class Role(RevMixin, AclMixin, models.Model):
('gateway', _("Gateway")),
)
role_type = models.CharField(max_length=255, unique=True)
servers = models.ManyToManyField('Interface')
role_type = models.CharField(
max_length=255,
unique=True,
verbose_name=_('name'),
)
servers = models.ManyToManyField(
'Interface',
verbose_name=_('servers'),
)
specific_role = models.CharField(
choices=ROLE,
null=True,
blank=True,
max_length=32,
verbose_name=_('specific role'),
)
class Meta:
verbose_name = _("server role")
verbose_name_plural = _("server roles")
@classmethod
def interface_for_roletype(cls, roletype):
"""Return interfaces for a roletype"""
return Interface.objects.filter(
role=cls.objects.filter(specific_role=roletype)
)
@classmethod
def all_interfaces_for_roletype(cls, roletype):
"""Return all interfaces for a roletype"""
......@@ -1754,10 +1779,9 @@ class Role(RevMixin, AclMixin, models.Model):
@classmethod
def interface_for_roletype(cls, roletype):
"""Return interfaces for a roletype"""
return Interface.objects.filter(role=cls.objects.filter(specific_role=roletype))
def save(self, *args, **kwargs):
super(Role, self).save(*args, **kwargs)
return Interface.objects.filter(
role=cls.objects.filter(specific_role=roletype)
)
def __str__(self):
return str(self.role_type)
......@@ -1867,13 +1891,14 @@ class OuverturePortList(RevMixin, AclMixin, models.Model):
"""Liste des ports ouverts sur une interface."""
name = models.CharField(
verbose_name=_('name'),
help_text=_("Name of the ports configuration"),
max_length=255
)
class Meta:
verbose_name = _("ports opening list")
verbose_name_plural = _("ports opening lists")
verbose_name = _("ports opening profile")
verbose_name_plural = _("ports opening profiles")
def can_delete(self, user_request, *_args, **_kwargs):
"""Verifie que l'user a les bons droits bureau pour delete
......@@ -1934,8 +1959,14 @@ class OuverturePort(RevMixin, AclMixin, models.Model):
UDP = 'U'
IN = 'I'
OUT = 'O'
begin = models.PositiveIntegerField(validators=[MaxValueValidator(65535)])
end = models.PositiveIntegerField(validators=[MaxValueValidator(65535)])
begin = models.PositiveIntegerField(
validators=[MaxValueValidator(65535)],
verbose_name=_('begins at'),
)
end = models.PositiveIntegerField(
validators=[MaxValueValidator(65535)],
verbose_name=_('ends at'),
)
port_list = models.ForeignKey(
'OuverturePortList',
on_delete=models.CASCADE
......@@ -1947,6 +1978,7 @@ class OuverturePort(RevMixin, AclMixin, models.Model):
(UDP, 'UDP'),
),
default=TCP,
verbose_name=_('protocole'),
)
io = models.CharField(
max_length=1,
......@@ -1955,6 +1987,7 @@ class OuverturePort(RevMixin, AclMixin, models.Model):
(OUT, 'OUT'),
),
default=OUT,
verbose_name=_('i/o'),
)
class Meta:
......@@ -2032,96 +2065,21 @@ def machinetype_post_save(**kwargs):
@receiver(post_save, sender=Domain)
def domain_post_save(**_kwargs):
"""Regeneration dns après modification d'un domain object"""
regen('dns')
@receiver(post_delete, sender=Domain)
def domain_post_delete(**_kwargs):
"""Regeneration dns après suppression d'un domain object"""
regen('dns')
@receiver(post_save, sender=Extension)
def extension_post_save(**_kwargs):
"""Regeneration dns après modification d'une extension"""
regen('dns')
@receiver(post_delete, sender=Extension)
def extension_post_selete(**_kwargs):
"""Regeneration dns après suppression d'une extension"""
regen('dns')
@receiver(post_save, sender=SOA)
def soa_post_save(**_kwargs):
"""Regeneration dns après modification d'un SOA"""
regen('dns')
@receiver(post_delete, sender=SOA)
def soa_post_delete(**_kwargs):
"""Regeneration dns après suppresson d'un SOA"""
regen('dns')
@receiver(post_save, sender=Mx)
def mx_post_save(**_kwargs):
"""Regeneration dns après modification d'un MX"""
regen('dns')
@receiver(post_delete, sender=Mx)
def mx_post_delete(**_kwargs):
"""Regeneration dns après suppresson d'un MX"""
regen('dns')
@receiver(post_save, sender=Ns)
def ns_post_save(**_kwargs):
"""Regeneration dns après modification d'un NS"""
regen('dns')
@receiver(post_delete, sender=Ns)
def ns_post_delete(**_kwargs):
"""Regeneration dns après modification d'un NS"""
regen('dns')
@receiver(post_save, sender=Txt)
def text_post_save(**_kwargs):
"""Regeneration dns après modification d'un TXT"""
regen('dns')
@receiver(post_delete, sender=Txt)
def text_post_delete(**_kwargs):
"""Regeneration dns après modification d'un TX"""
regen('dns')
@receiver(post_save, sender=DName)
def dname_post_save(**_kwargs):
"""Updates the DNS regen after modification of a DName object."""
regen('dns')
@receiver(post_delete, sender=DName)
def dname_post_delete(**_kwargs):
"""Updates the DNS regen after deletion of a DName object."""
regen('dns')
@receiver(post_save, sender=Srv)
def srv_post_save(**_kwargs):
"""Regeneration dns après modification d'un SRV"""
regen('dns')
@receiver(post_delete, sender=Srv)
def srv_post_delete(**_kwargs):
"""Regeneration dns après modification d'un SRV"""
def regen_dns_receiver(**_kwargs):
"""Regen DNS when configuration changes"""
regen('dns')
{% comment %}
Re2o est un logiciel d'administration développé initiallement au rezometz. Il
se veut agnostique au réseau considéré, de manière à être installable en
quelques clics.
Copyright © 2017 Gabriel Détraz
Copyright © 2017 Goulven Kermarec
Copyright © 2017 Augustin Lemesle
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License along
with this program; if not, write to the Free Software Foundation, Inc.,
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
{% endcomment %}
{% load acl %}
{% load i18n %}
{% load logs_extra %}
<table class="table table-striped">
<thead>
<tr>
<th>{% trans "Role name" %}</th>
<th>{% trans "Specific role" %}</th>
<th>{% trans "Servers" %}</th>
<th></th>
<th></th>
</tr>
</thead>
{% for role in role_list %}
<tr>
<td>{{ role.role_type }}</td>
<td>{{ role.specific_role }}</td>
<td>{% for serv in role.servers.all %}{{ serv }}, {% endfor %}</td>
<td class="text-right">
{% can_edit role %}
{% include 'buttons/edit.html' with href='machines:edit-role' id=role.id %}
{% acl_end %}
{% history_button role %}
</td>
</tr>
{% endfor %}
</table>
{% extends 'machines/sidebar.html' %}
{% comment %}
Re2o est un logiciel d'administration développé initiallement au rezometz. Il
se veut agnostique au réseau considéré, de manière à être installable en
quelques clics.
Copyright © 2017 Gabriel Détraz
Copyright © 2017 Goulven Kermarec
Copyright © 2017 Augustin Lemesle
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License along
with this program; if not, write to the Free Software Foundation, Inc.,
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
{% endcomment %}
{% load bootstrap3 %}
{% load i18n %}
{% block title %}{% trans "Machines" %}{% endblock %}
{% block content %}
{% bootstrap_form_errors port_list %}
<form class="form" method="post">
{% csrf_token %}
{% bootstrap_form port_list %}
{{ ports.management_form }}
<div id="formset">
{% for form in ports.forms %}
<div class="port">
<p>
{{ form }}
</p>
</div>
{% endfor %}
</div>
<p>
{% trans "Add a port" as value %}
<input class="btn btn-primary btn-sm" role="button" value="value" id="add_one">
</p>
{% trans "Create or edit" as tr_create_or_edit %}
{% bootstrap_button tr_create_or_edit icon='ok' button_class='btn-success' %}
</form>
<script type="text/javascript">
var template = `{{ports.empty_form}}`;
function add_port() {
var new_index = document.getElementsByClassName('port').length;
document.getElementById('id_form-TOTAL_FORMS').value =
parseInt(document.getElementById('id_form-TOTAL_FORMS').value) + 1;
var new_port = document.createElement('div');
new_port.className = 'port';
new_port.innerHTML = template.replace(/__prefix__/g, new_index);
document.getElementById('formset').appendChild(new_port);
}
document.addEventListener("DOMContentLoaded", function () {
document.getElementById("add_one").addEventListener("click", add_port, true);
});
</script>
{% endblock %}
......@@ -9,11 +9,6 @@
{% block content %}
<h2>{% trans "List of ports configurations" %}</h2>
{% can_create OuverturePortList %}
<a class="btn btn-primary btn-sm" role="button" href="{% url 'machines:add-portlist' %}">
<i class="fa fa-plus"></i>{% trans " Add a configuration" %}
</a>
{% acl_end %}
<table class="table table-striped">
<thead>
<tr>
......@@ -23,7 +18,6 @@
<th>{% trans "UDP (input)" %}</th>
<th>{% trans "UDP (output)" %}</th>
<th>{% trans "Machines" %}</th>
<th></th>
</tr>
</thead>
{% for pl in port_list %}
......@@ -51,14 +45,6 @@
</ul>
</div>
{% endif %}
<td class="text-right">
{% can_edit pl %}
{% include 'buttons/edit.html' with href='machines:edit-portlist' id=pl.id %}
{% acl_end %}
{% can_delete pl %}
{% include 'buttons/suppr.html' with href='machines:del-portlist' id=pl.id %}
{% acl_end %}
</td>
</tr>
{% endfor %}
</table>
......
{% extends 'machines/sidebar.html' %}
{% comment %}
Re2o est un logiciel d'administration développé initiallement au rezometz. Il
se veut agnostique au réseau considéré, de manière à être installable en
quelques clics.
Copyright © 2017 Gabriel Détraz
Copyright © 2017 Goulven Kermarec
Copyright © 2017 Augustin Lemesle
This program is free software; you can redistribute it and/or modify