Ce serveur Gitlab sera éteint le 30 juin 2020, pensez à migrer vos projets vers les serveurs gitlab-research.centralesupelec.fr et gitlab-student.centralesupelec.fr !

forms.py 25.3 KB
Newer Older
1
# -*- mode: python; coding: utf-8 -*-
2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
# 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.
chirac's avatar
chirac committed
23 24
"""
Definition des forms pour l'application users.
25

chirac's avatar
chirac committed
26 27 28 29 30 31 32
Modification, creation de :
    - un user (informations personnelles)
    - un bannissement
    - le mot de passe d'un user
    - une whiteliste
    - un user de service
"""
33

34
from __future__ import unicode_literals
35 36

from django import forms
37
from django.forms import ModelForm, Form
38
from django.contrib.auth.forms import ReadOnlyPasswordHashField
Gabriel Detraz's avatar
Gabriel Detraz committed
39
from django.core.validators import MinLengthValidator
40
from django.utils import timezone
41
from django.contrib.auth.models import Group, Permission
42
from django.utils.translation import ugettext_lazy as _
43

44 45
from machines.models import Interface, Machine, Nas
from topologie.models import Port
chirac's avatar
chirac committed
46
from preferences.models import OptionalUser
47
from re2o.utils import remove_user_room, get_input_formats_help_text
48 49 50
from re2o.mixins import FormRevMixin
from re2o.field_permissions import FieldPermissionFormMixin

root's avatar
root committed
51 52
from .widgets import DateTimePicker

53 54 55 56 57 58
from .models import (
    User,
    ServiceUser,
    School,
    ListRight,
    Whitelist,
59
    EMailAddress,
60 61 62 63 64
    ListShell,
    Ban,
    Adherent,
    Club
)
65

66

67
class PassForm(FormRevMixin, FieldPermissionFormMixin, forms.ModelForm):
chirac's avatar
chirac committed
68 69 70
    """Formulaire de changement de mot de passe. Verifie que les 2
    nouveaux mots de passe renseignés sont identiques et respectent
    une norme"""
71
    selfpasswd = forms.CharField(
72
        label=_("Current password"),
73 74 75
        max_length=255,
        widget=forms.PasswordInput
    )
chirac's avatar
chirac committed
76
    passwd1 = forms.CharField(
77
        label=_("New password"),
chirac's avatar
chirac committed
78 79 80 81 82
        max_length=255,
        validators=[MinLengthValidator(8)],
        widget=forms.PasswordInput
    )
    passwd2 = forms.CharField(
83
        label=_("New password confirmation"),
chirac's avatar
chirac committed
84 85 86 87
        max_length=255,
        validators=[MinLengthValidator(8)],
        widget=forms.PasswordInput
    )
88

89 90 91 92
    class Meta:
        model = User
        fields = []

93
    def clean_passwd2(self):
chirac's avatar
chirac committed
94
        """Verifie que passwd1 et 2 sont identiques"""
95 96 97 98
        # Check that the two password entries match
        password1 = self.cleaned_data.get("passwd1")
        password2 = self.cleaned_data.get("passwd2")
        if password1 and password2 and password1 != password2:
99
            raise forms.ValidationError(
100
                _("The new passwords don't match.")
101
            )
102
        return password2
103

104 105
    def clean_selfpasswd(self):
        """Verifie si il y a lieu que le mdp self est correct"""
106
        if not self.instance.check_password(
107 108
                self.cleaned_data.get("selfpasswd")
            ):
109
            raise forms.ValidationError(_("The current password is incorrect."))
110 111 112 113 114 115 116 117
        return

    def save(self, commit=True):
        """Changement du mot de passe"""
        user = super(PassForm, self).save(commit=False)
        user.set_password(self.cleaned_data.get("passwd1"))
        user.save()

chirac's avatar
chirac committed
118

119
class UserCreationForm(FormRevMixin, forms.ModelForm):
120
    """A form for creating new users. Includes all the required
chirac's avatar
chirac committed
121 122 123 124 125 126
    fields, plus a repeated password.

    Formulaire pour la création d'un user. N'est utilisé que pour
    l'admin, lors de la creation d'un user par admin. Inclu tous les
    champs obligatoires"""
    password1 = forms.CharField(
127
        label=_("Password"),
chirac's avatar
chirac committed
128 129 130 131 132
        widget=forms.PasswordInput,
        validators=[MinLengthValidator(8)],
        max_length=255
    )
    password2 = forms.CharField(
133
        label=_("Password confirmation"),
chirac's avatar
chirac committed
134 135 136 137
        widget=forms.PasswordInput,
        validators=[MinLengthValidator(8)],
        max_length=255
    )
138
    is_admin = forms.BooleanField(label=_("Is admin"))
139

140
    def __init__(self, *args, **kwargs):
141
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
142 143
        super(UserCreationForm, self).__init__(*args, prefix=prefix, **kwargs)

144 145 146 147
    def clean_email(self):
        if not OptionalUser.objects.first().local_email_domain in self.cleaned_data.get('email'):
            return self.cleaned_data.get('email').lower()
        else:
148 149
            raise forms.ValidationError(_("You can't use an internal address"
                                          " as your external address."))
150

151
    class Meta:
152
        model = Adherent
153
        fields = ('pseudo', 'surname', 'email')
154 155

    def clean_password2(self):
chirac's avatar
chirac committed
156
        """Verifie que password1 et 2 sont identiques"""
157 158 159 160
        # Check that the two password entries match
        password1 = self.cleaned_data.get("password1")
        password2 = self.cleaned_data.get("password2")
        if password1 and password2 and password1 != password2:
161
            raise forms.ValidationError(_("The passwords don't match."))
162 163 164 165 166 167 168 169 170 171
        return password2

    def save(self, commit=True):
        # Save the provided password in hashed format
        user = super(UserCreationForm, self).save(commit=False)
        user.set_password(self.cleaned_data["password1"])
        user.save()
        user.is_admin = self.cleaned_data.get("is_admin")
        return user

chirac's avatar
chirac committed
172

173
class ServiceUserCreationForm(FormRevMixin, forms.ModelForm):
chirac's avatar
chirac committed
174
    """A form for creating new users. Includes all the required
chirac's avatar
chirac committed
175 176 177 178 179
    fields, plus a repeated password.

    Formulaire pour la creation de nouveaux serviceusers.
    Requiert seulement un mot de passe; et un pseudo"""
    password1 = forms.CharField(
180
        label=_("Password"),
chirac's avatar
chirac committed
181 182 183 184 185
        widget=forms.PasswordInput,
        min_length=8,
        max_length=255
    )
    password2 = forms.CharField(
186
        label=_("Password confirmation"),
chirac's avatar
chirac committed
187 188 189 190
        widget=forms.PasswordInput,
        min_length=8,
        max_length=255
    )
chirac's avatar
chirac committed
191

192
    def __init__(self, *args, **kwargs):
193
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
chirac's avatar
chirac committed
194 195 196 197 198
        super(ServiceUserCreationForm, self).__init__(
            *args,
            prefix=prefix,
            **kwargs
        )
199

chirac's avatar
chirac committed
200 201 202 203 204
    class Meta:
        model = ServiceUser
        fields = ('pseudo',)

    def clean_password2(self):
chirac's avatar
chirac committed
205
        """Verifie que password1 et 2 sont indentiques"""
chirac's avatar
chirac committed
206 207 208 209
        # Check that the two password entries match
        password1 = self.cleaned_data.get("password1")
        password2 = self.cleaned_data.get("password2")
        if password1 and password2 and password1 != password2:
210
            raise forms.ValidationError(_("The passwords don't match."))
chirac's avatar
chirac committed
211 212 213 214 215 216 217 218
        return password2

    def save(self, commit=True):
        # Save the provided password in hashed format
        user = super(ServiceUserCreationForm, self).save(commit=False)
        user.set_password(self.cleaned_data["password1"])
        user.save()
        return user
219

chirac's avatar
chirac committed
220

221
class UserChangeForm(FormRevMixin, forms.ModelForm):
222 223 224
    """A form for updating users. Includes all the fields on
    the user, but replaces the password field with admin's
    password hash display field.
chirac's avatar
chirac committed
225 226

    Formulaire pour la modification d'un user coté admin
227 228
    """
    password = ReadOnlyPasswordHashField()
229
    is_admin = forms.BooleanField(label=_("Is admin"), required=False)
230 231

    class Meta:
232
        model = Adherent
233
        fields = ('pseudo', 'password', 'surname', 'email')
234 235

    def __init__(self, *args, **kwargs):
236
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
237
        super(UserChangeForm, self).__init__(*args, prefix=prefix, **kwargs)
238
        print(_("User is admin: %s") % kwargs['instance'].is_admin)
239 240 241
        self.initial['is_admin'] = kwargs['instance'].is_admin

    def clean_password(self):
chirac's avatar
chirac committed
242
        """Dummy fun"""
243 244 245 246 247 248 249 250 251 252 253 254
        # Regardless of what the user provides, return the initial value.
        # This is done here, rather than on the field, because the
        # field does not have access to the initial value
        return self.initial["password"]

    def save(self, commit=True):
        # Save the provided password in hashed format
        user = super(UserChangeForm, self).save(commit=False)
        user.is_admin = self.cleaned_data.get("is_admin")
        if commit:
            user.save()
        return user
chirac's avatar
chirac committed
255

chirac's avatar
chirac committed
256

257
class ServiceUserChangeForm(FormRevMixin, forms.ModelForm):
chirac's avatar
chirac committed
258 259 260
    """A form for updating users. Includes all the fields on
    the user, but replaces the password field with admin's
    password hash display field.
chirac's avatar
chirac committed
261 262

    Formulaire pour l'edition des service users coté admin
chirac's avatar
chirac committed
263 264 265
    """
    password = ReadOnlyPasswordHashField()

266
    def __init__(self, *args, **kwargs):
267
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
chirac's avatar
chirac committed
268 269 270 271 272
        super(ServiceUserChangeForm, self).__init__(
            *args,
            prefix=prefix,
            **kwargs
        )
273

chirac's avatar
chirac committed
274 275 276 277 278
    class Meta:
        model = ServiceUser
        fields = ('pseudo',)

    def clean_password(self):
chirac's avatar
chirac committed
279
        """Dummy fun"""
chirac's avatar
chirac committed
280 281
        return self.initial["password"]

chirac's avatar
chirac committed
282

chirac's avatar
chirac committed
283
class ResetPasswordForm(forms.Form):
chirac's avatar
chirac committed
284 285
    """Formulaire de demande de reinitialisation de mot de passe,
    mdp oublié"""
286
    pseudo = forms.CharField(label=_("Username"), max_length=255)
chirac's avatar
chirac committed
287
    email = forms.EmailField(max_length=255)
288

chirac's avatar
chirac committed
289

290
class MassArchiveForm(forms.Form):
chirac's avatar
chirac committed
291 292 293
    """Formulaire d'archivage des users inactif. Prend en argument
    du formulaire la date de depart avant laquelle archiver les
    users"""
294 295 296
    date = forms.DateTimeField(help_text='%d/%m/%y')

    def clean(self):
chirac's avatar
chirac committed
297
        cleaned_data = super(MassArchiveForm, self).clean()
298 299
        date = cleaned_data.get("date")
        if date:
300
            if date > timezone.now():
301 302 303
                raise forms.ValidationError(_("Impossible to archive users"
                                              " whose end access date is in"
                                              " the future."))
chirac's avatar
chirac committed
304

305

306
class AdherentForm(FormRevMixin, FieldPermissionFormMixin, ModelForm):
chirac's avatar
chirac committed
307 308 309
    """Formulaire de base d'edition d'un user. Formulaire de base, utilisé
    pour l'edition de self par self ou un cableur. On formate les champs
    avec des label plus jolis"""
310
    def __init__(self, *args, **kwargs):
311
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
312
        super(AdherentForm, self).__init__(*args, prefix=prefix, **kwargs)
313 314 315 316 317 318 319 320
        self.fields['name'].label = _("First name")
        self.fields['surname'].label = _("Surname")
        self.fields['email'].label = _("Email address")
        self.fields['school'].label = _("School")
        self.fields['comment'].label = _("Comment")
        self.fields['room'].label = _("Room")
        self.fields['room'].empty_label = _("No room")
        self.fields['school'].empty_label = _("Select a school")
Fernet Laouen's avatar
Fernet Laouen committed
321
        self.fields['gpg_fingerprint'].widget.attrs['placeholder'] = _("Leave empty if you don't have any GPG key.")
322 323
        if 'shell' in self.fields:
            self.fields['shell'].empty_label = _("Default shell")
324

325 326 327 328
    def clean_email(self):
        if not OptionalUser.objects.first().local_email_domain in self.cleaned_data.get('email'):
            return self.cleaned_data.get('email').lower()
        else:
329 330 331
            raise forms.ValidationError(
                    _("You can't use a {} address.").format(
                        OptionalUser.objects.first().local_email_domain))
332

333
    class Meta:
334
        model = Adherent
335 336 337 338
        fields = [
            'name',
            'surname',
            'pseudo',
339
            'email',
340 341
            'school',
            'comment',
342
            'telephone',
343
            'room',
344
            'shell',
345
            'gpg_fingerprint'
346 347
        ]

348

349
    def clean_telephone(self):
chirac's avatar
chirac committed
350 351
        """Verifie que le tel est présent si 'option est validée
        dans preferences"""
352
        telephone = self.cleaned_data['telephone']
353
        if not telephone and OptionalUser.get_cached_value('is_tel_mandatory'):
chirac's avatar
chirac committed
354
            raise forms.ValidationError(
355
                _("A valid telephone number is required.")
chirac's avatar
chirac committed
356
            )
357 358
        return telephone

359 360 361 362 363 364
    def clean_gpg_fingerprint(self):
        """Format the GPG fingerprint"""
        gpg_fingerprint = self.cleaned_data.get('gpg_fingerprint', None)
        if gpg_fingerprint:
            return gpg_fingerprint.replace(' ', '').upper()

365
    force = forms.BooleanField(
366
        label=_("Force the move?"),
367 368 369 370 371 372 373 374
        initial=False,
        required=False
    )

    def clean_force(self):
        """On supprime l'ancien user de la chambre si et seulement si la
        case est cochée"""
        if self.cleaned_data.get('force', False):
375
            remove_user_room(self.cleaned_data.get('room'))
376
        return
chirac's avatar
chirac committed
377

378

379
class ClubForm(FormRevMixin, FieldPermissionFormMixin, ModelForm):
380 381 382 383 384
    """Formulaire de base d'edition d'un user. Formulaire de base, utilisé
    pour l'edition de self par self ou un cableur. On formate les champs
    avec des label plus jolis"""
    def __init__(self, *args, **kwargs):
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
385
        super(ClubForm, self).__init__(*args, prefix=prefix, **kwargs)
386 387 388 389 390 391 392
        self.fields['surname'].label = _("Name")
        self.fields['school'].label = _("School")
        self.fields['comment'].label = _("Comment")
        self.fields['room'].label = _("Room")
        self.fields['room'].empty_label = _("No room")
        self.fields['school'].empty_label = _("Select a school")
        self.fields['mailing'].label = _("Use a mailing list")
393 394 395 396 397 398 399 400 401 402

    class Meta:
        model = Club
        fields = [
            'surname',
            'pseudo',
            'school',
            'comment',
            'room',
            'telephone',
403
            'shell',
404
            'mailing'
405 406 407 408 409 410
        ]

    def clean_telephone(self):
        """Verifie que le tel est présent si 'option est validée
        dans preferences"""
        telephone = self.cleaned_data['telephone']
411
        if not telephone and OptionalUser.get_cached_value('is_tel_mandatory'):
412
            raise forms.ValidationError(
413
                _("A valid telephone number is required.")
414 415 416 417
            )
        return telephone


418
class ClubAdminandMembersForm(FormRevMixin, ModelForm):
419 420 421 422 423 424 425 426
    """Permet d'éditer la liste des membres et des administrateurs
    d'un club"""
    class Meta:
        model = Club
        fields = ['administrators', 'members']

    def __init__(self, *args, **kwargs):
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
427 428 429 430 431
        super(ClubAdminandMembersForm, self).__init__(
            *args,
            prefix=prefix,
            **kwargs
        )
432 433


434
class PasswordForm(FormRevMixin, ModelForm):
chirac's avatar
chirac committed
435 436
    """ Formulaire de changement brut de mot de passe.
    Ne pas utiliser sans traitement"""
437 438 439 440
    class Meta:
        model = User
        fields = ['password', 'pwd_ntlm']

441
    def __init__(self, *args, **kwargs):
442
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
443 444
        super(PasswordForm, self).__init__(*args, prefix=prefix, **kwargs)

chirac's avatar
chirac committed
445

446
class ServiceUserForm(FormRevMixin, ModelForm):
chirac's avatar
chirac committed
447
    """ Modification d'un service user"""
chirac's avatar
chirac committed
448
    password = forms.CharField(
449
        label=_("New password"),
chirac's avatar
chirac committed
450 451 452 453 454
        max_length=255,
        validators=[MinLengthValidator(8)],
        widget=forms.PasswordInput,
        required=False
    )
455 456 457

    class Meta:
        model = ServiceUser
458
        fields = ('pseudo', 'access_group','comment')
459

460
    def __init__(self, *args, **kwargs):
461
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
462 463
        super(ServiceUserForm, self).__init__(*args, prefix=prefix, **kwargs)

464 465 466 467 468 469 470
    def save(self, commit=True):
        """Changement du mot de passe"""
        user = super(ServiceUserForm, self).save(commit=False)
        if self.cleaned_data['password']:
            user.set_password(self.cleaned_data.get("password"))
        user.save()

chirac's avatar
chirac committed
471

472
class EditServiceUserForm(ServiceUserForm):
chirac's avatar
chirac committed
473 474
    """Formulaire d'edition de base d'un service user. Ne permet
    d'editer que son group d'acl et son commentaire"""
475
    class Meta(ServiceUserForm.Meta):
chirac's avatar
chirac committed
476 477
        fields = ['access_group', 'comment']

478

479
class StateForm(FormRevMixin, ModelForm):
chirac's avatar
chirac committed
480
    """ Changement de l'état d'un user"""
481 482 483 484
    class Meta:
        model = User
        fields = ['state']

485
    def __init__(self, *args, **kwargs):
486
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
487 488
        super(StateForm, self).__init__(*args, prefix=prefix, **kwargs)

489

Levy--Falk Hugo's avatar
Levy--Falk Hugo committed
490
class GroupForm(FieldPermissionFormMixin, FormRevMixin, ModelForm):
491 492 493 494 495 496 497 498 499
    """ Gestion des groupes d'un user"""
    groups = forms.ModelMultipleChoiceField(
        Group.objects.all(),
        widget=forms.CheckboxSelectMultiple,
        required=False
    )

    class Meta:
        model = User
500
        fields = ['is_superuser', 'groups']
501 502 503 504

    def __init__(self, *args, **kwargs):
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
        super(GroupForm, self).__init__(*args, prefix=prefix, **kwargs)
Levy--Falk Hugo's avatar
Levy--Falk Hugo committed
505
        if 'is_superuser' in self.fields:
506
            self.fields['is_superuser'].label = _("Superuser")
507 508


509
class SchoolForm(FormRevMixin, ModelForm):
chirac's avatar
chirac committed
510
    """Edition, creation d'un école"""
511 512 513 514 515
    class Meta:
        model = School
        fields = ['name']

    def __init__(self, *args, **kwargs):
516
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
517
        super(SchoolForm, self).__init__(*args, prefix=prefix, **kwargs)
518
        self.fields['name'].label = _("School")
519

chirac's avatar
chirac committed
520

521
class ShellForm(FormRevMixin, ModelForm):
522 523 524 525 526 527 528 529
    """Edition, creation d'un école"""
    class Meta:
        model = ListShell
        fields = ['shell']

    def __init__(self, *args, **kwargs):
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
        super(ShellForm, self).__init__(*args, prefix=prefix, **kwargs)
530
        self.fields['shell'].label = _("Shell name")
531 532


533
class ListRightForm(FormRevMixin, ModelForm):
chirac's avatar
chirac committed
534
    """Edition, d'un groupe , équivalent à un droit
535
    Ne permet pas d'editer le gid, car il sert de primary key"""
536
    permissions = forms.ModelMultipleChoiceField(
537
        Permission.objects.all().select_related('content_type'),
538 539 540 541
        widget=forms.CheckboxSelectMultiple,
        required=False
    )

542 543
    class Meta:
        model = ListRight
544
        fields = ('name', 'unix_name', 'critical', 'permissions', 'details')
545 546

    def __init__(self, *args, **kwargs):
547
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
548
        super(ListRightForm, self).__init__(*args, prefix=prefix, **kwargs)
549
        self.fields['unix_name'].label = _("Name of the group of rights")
550

chirac's avatar
chirac committed
551

552
class NewListRightForm(ListRightForm):
chirac's avatar
chirac committed
553
    """Ajout d'un groupe/list de droit """
554
    class Meta(ListRightForm.Meta):
555 556
        fields = ('name', 'unix_name', 'gid', 'critical', 'permissions',
                  'details')
557 558 559

    def __init__(self, *args, **kwargs):
        super(NewListRightForm, self).__init__(*args, **kwargs)
560 561
        self.fields['gid'].label = _("GID. Warning: this field must not be"
                                     " edited after creation.")
chirac's avatar
chirac committed
562

563

564
class DelListRightForm(Form):
chirac's avatar
chirac committed
565 566
    """Suppression d'un ou plusieurs groupes"""
    listrights = forms.ModelMultipleChoiceField(
567
        queryset=ListRight.objects.none(),
568
        label=_("Current groups of rights"),
chirac's avatar
chirac committed
569 570 571
        widget=forms.CheckboxSelectMultiple
    )

572 573 574 575
    def __init__(self, *args, **kwargs):
        instances = kwargs.pop('instances', None)
        super(DelListRightForm, self).__init__(*args, **kwargs)
        if instances:
576
            self.fields['listrights'].queryset = instances
577
        else:
578
            self.fields['listrights'].queryset = ListRight.objects.all()
579

580

581
class DelSchoolForm(Form):
chirac's avatar
chirac committed
582 583
    """Suppression d'une ou plusieurs écoles"""
    schools = forms.ModelMultipleChoiceField(
584
        queryset=School.objects.none(),
585
        label=_("Current schools"),
chirac's avatar
chirac committed
586 587 588
        widget=forms.CheckboxSelectMultiple
    )

589
    def __init__(self, *args, **kwargs):
590
        instances = kwargs.pop('instances', None)
591
        super(DelSchoolForm, self).__init__(*args, **kwargs)
592 593 594 595
        if instances:
            self.fields['schools'].queryset = instances
        else:
            self.fields['schools'].queryset = School.objects.all()
596

597

598
class BanForm(FormRevMixin, ModelForm):
chirac's avatar
chirac committed
599
    """Creation, edition d'un objet bannissement"""
600
    def __init__(self, *args, **kwargs):
601
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
602
        super(BanForm, self).__init__(*args, prefix=prefix, **kwargs)
603
        self.fields['date_end'].label = _("End date")
604
        self.fields['date_end'].localize = False
605 606 607 608

    class Meta:
        model = Ban
        exclude = ['user']
609
        widgets = {'date_end':DateTimePicker}
610 611


612
class WhitelistForm(FormRevMixin, ModelForm):
chirac's avatar
chirac committed
613
    """Creation, edition d'un objet whitelist"""
614
    def __init__(self, *args, **kwargs):
615
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
616
        super(WhitelistForm, self).__init__(*args, prefix=prefix, **kwargs)
617
        self.fields['date_end'].label = _("End date")
root's avatar
root committed
618
        self.fields['date_end'].localize = False
619 620 621 622

    class Meta:
        model = Whitelist
        exclude = ['user']
root's avatar
root committed
623
        widgets = {'date_end':DateTimePicker}
624 625


626 627
class EMailAddressForm(FormRevMixin, ModelForm):
    """Create and edit a local email address"""
628 629
    def __init__(self, *args, **kwargs):
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
630
        super(EMailAddressForm, self).__init__(*args, prefix=prefix, **kwargs)
631 632
        self.fields['local_part'].label = _("Local part of the email address")
        self.fields['local_part'].help_text = _("Can't contain @")
633

634 635
    def clean_local_part(self):
        return self.cleaned_data.get('local_part').lower()
636 637

    class Meta:
638
        model = EMailAddress
639
        exclude = ['user']
640

641 642 643

class EmailSettingsForm(FormRevMixin, FieldPermissionFormMixin, ModelForm):
    """Edit email-related settings"""
644 645
    def __init__(self, *args, **kwargs):
        prefix = kwargs.pop('prefix', self.Meta.model.__name__)
646
        super(EmailSettingsForm, self).__init__(*args, prefix=prefix, **kwargs)
647
        self.fields['email'].label = _("Main email address")
648
        if 'local_email_redirect' in self.fields:
649
            self.fields['local_email_redirect'].label = _("Redirect local emails")
650
        if 'local_email_enabled' in self.fields:
651
            self.fields['local_email_enabled'].label = _("Use local emails")
652

653 654 655 656
    def clean_email(self):
        if not OptionalUser.objects.first().local_email_domain in self.cleaned_data.get('email'):
            return self.cleaned_data.get('email').lower()
        else:
657 658 659
            raise forms.ValidationError(
                    _("You can't use a {} address.").format(
                        OptionalUser.objects.first().local_email_domain))
660

661
    class Meta:
662
        model = User
663
        fields = ['email','local_email_enabled', 'local_email_redirect']
664

665 666 667 668 669 670 671 672 673 674 675 676 677 678 679 680 681 682 683 684 685 686 687 688 689 690

class InitialRegisterForm(forms.Form):
    register_room = forms.BooleanField(required=False)
    register_machine = forms.BooleanField(required=False)

    def __init__(self, *args, **kwargs):
        switch_ip = kwargs.pop('switch_ip')
        switch_port = kwargs.pop('switch_port')
        client_mac = kwargs.pop('client_mac')
        self.user = kwargs.pop('user')
        if switch_ip and switch_port:
            # Looking for a port
            port = Port.objects.filter(switch__interface__ipv4__ipv4=switch_ip, port=switch_port).first()
            # If a port exists, checking there is a room AND radius
            if port:
                if port.get_port_profile.radius_type != 'NO' and port.get_port_profile.radius_mode == 'STRICT' and hasattr(port, 'room'):
                    # Requesting user is not in this room ?
                    if self.user.room != port.room:
                        self.new_room = port.room
        if client_mac and switch_ip:
            # If this interface doesn't already exists
            if not Interface.objects.filter(mac_address=client_mac):
                self.mac_address = client_mac
                self.nas_type = Nas.objects.filter(nas_type__interface__ipv4__ipv4=switch_ip).first()
        super(InitialRegisterForm, self).__init__(*args, **kwargs)
        if hasattr(self, 'new_room'):
691
            self.fields['register_room'].label = _("New connection from room %s. Is it yours? If that is the case, type OK." % self.new_room)
692 693 694
        else:
            self.fields.pop('register_room')
        if hasattr(self, 'mac_address'):
695
            self.fields['register_machine'].label = _("New connection from new device. Register it? Say Yes to get Internet access from it (MAC Address : %s)." % self.mac_address)
696 697 698 699 700 701 702 703 704 705 706 707 708 709 710 711 712 713 714
        else:
            self.fields.pop('register_machine')

    def clean_register_room(self):
        if self.cleaned_data['register_room']:
            if self.user.is_class_adherent:
                remove_user_room(self.new_room)
                user = self.user.adherent
                user.room = self.new_room
                user.save()
            if self.user.is_class_club:
                user = self.user.club
                user.room = self.new_room
                user.save()

    def clean_register_machine(self):
        if self.cleaned_data['register_machine']:
            if self.mac_address and self.nas_type:
                self.user.autoregister_machine(self.mac_address, self.nas_type)