mirror of
https://github.com/ae-utbm/sith.git
synced 2024-11-22 14:13:21 +00:00
Merge branch 'clubs' into 'master'
Club tools enhacement See merge request ae/Sith!108
This commit is contained in:
commit
0bef8d33d3
@ -58,6 +58,6 @@ def FetchMailingLists(request):
|
||||
if key != settings.SITH_MAILING_FETCH_KEY:
|
||||
raise PermissionDenied
|
||||
data = ''
|
||||
for mailing in Mailing.objects.filter(is_moderated=True).all():
|
||||
for mailing in Mailing.objects.filter(is_moderated=True, club__is_active=True).all():
|
||||
data += mailing.fetch_format() + "\n"
|
||||
return Response(data)
|
||||
|
45
club/migrations/0010_auto_20170912_2028.py
Normal file
45
club/migrations/0010_auto_20170912_2028.py
Normal file
@ -0,0 +1,45 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
from __future__ import unicode_literals
|
||||
|
||||
from django.db import migrations, models
|
||||
|
||||
from club.models import Club
|
||||
from core.operations import PsqlRunOnly
|
||||
|
||||
|
||||
def generate_club_pages(apps, schema_editor):
|
||||
def recursive_generate_club_page(club):
|
||||
club.make_page()
|
||||
for child in Club.objects.filter(parent=club).all():
|
||||
recursive_generate_club_page(child)
|
||||
for club in Club.objects.filter(parent=None).all():
|
||||
recursive_generate_club_page(club)
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('core', '0024_auto_20170906_1317'),
|
||||
('club', '0010_club_logo'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.AddField(
|
||||
model_name='club',
|
||||
name='is_active',
|
||||
field=models.BooleanField(default=True, verbose_name='is active'),
|
||||
),
|
||||
migrations.AddField(
|
||||
model_name='club',
|
||||
name='page',
|
||||
field=models.OneToOneField(related_name='club', blank=True, null=True, to='core.Page'),
|
||||
),
|
||||
migrations.AddField(
|
||||
model_name='club',
|
||||
name='short_description',
|
||||
field=models.CharField(verbose_name='short description', max_length=1000, default='', blank=True, null=True),
|
||||
),
|
||||
PsqlRunOnly('SET CONSTRAINTS ALL IMMEDIATE', reverse_sql=migrations.RunSQL.noop),
|
||||
migrations.RunPython(generate_club_pages),
|
||||
PsqlRunOnly(migrations.RunSQL.noop, reverse_sql='SET CONSTRAINTS ALL IMMEDIATE'),
|
||||
]
|
@ -32,12 +32,13 @@ from django.db import transaction
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.utils import timezone
|
||||
from django.core.validators import RegexValidator, validate_email
|
||||
from django.utils.functional import cached_property
|
||||
|
||||
from core.models import User, MetaGroup, Group, SithFile, RealGroup, Notification
|
||||
|
||||
from core.models import User, MetaGroup, Group, SithFile, RealGroup, Notification, Page
|
||||
|
||||
# Create your models here.
|
||||
|
||||
|
||||
class Club(models.Model):
|
||||
"""
|
||||
The Club class, made as a tree to allow nice tidy organization
|
||||
@ -58,6 +59,8 @@ class Club(models.Model):
|
||||
},
|
||||
)
|
||||
logo = models.ImageField(upload_to='club_logos', verbose_name=_('logo'), null=True, blank=True)
|
||||
is_active = models.BooleanField(_('is active'), default=True)
|
||||
short_description = models.CharField(_('short description'), max_length=1000, default='', blank=True, null=True)
|
||||
address = models.CharField(_('address'), max_length=254)
|
||||
# email = models.EmailField(_('email address'), unique=True) # This should, and will be generated automatically
|
||||
owner_group = models.ForeignKey(Group, related_name="owned_club",
|
||||
@ -66,10 +69,15 @@ class Club(models.Model):
|
||||
view_groups = models.ManyToManyField(Group, related_name="viewable_club", blank=True)
|
||||
home = models.OneToOneField(SithFile, related_name='home_of_club', verbose_name=_("home"), null=True, blank=True,
|
||||
on_delete=models.SET_NULL)
|
||||
page = models.OneToOneField(Page, related_name="club", blank=True, null=True)
|
||||
|
||||
class Meta:
|
||||
ordering = ['name', 'unix_name']
|
||||
|
||||
@cached_property
|
||||
def president(self):
|
||||
return self.members.filter(role=settings.SITH_CLUB_ROLES_ID['President'], end_date=None).first()
|
||||
|
||||
def check_loop(self):
|
||||
"""Raise a validation error when a loop is found within the parent list"""
|
||||
objs = []
|
||||
@ -102,6 +110,31 @@ class Club(models.Model):
|
||||
self.home = home
|
||||
self.save()
|
||||
|
||||
def make_page(self):
|
||||
root = User.objects.filter(username="root").first()
|
||||
if not self.page:
|
||||
club_root = Page.objects.filter(name=settings.SITH_CLUB_ROOT_PAGE).first()
|
||||
if root and club_root:
|
||||
public = Group.objects.filter(id=settings.SITH_GROUP_PUBLIC_ID).first()
|
||||
p = Page(name=self.unix_name)
|
||||
p.parent = club_root
|
||||
p.save(force_lock=True)
|
||||
if public:
|
||||
p.view_groups.add(public)
|
||||
p.save(force_lock=True)
|
||||
if self.parent and self.parent.page:
|
||||
p.parent = self.parent.page
|
||||
self.page = p
|
||||
self.save()
|
||||
elif self.page and self.page.name != self.unix_name:
|
||||
self.page.unset_lock()
|
||||
self.page.name = self.unix_name
|
||||
self.page.save(force_lock=True)
|
||||
elif self.page and self.parent and self.parent.page and self.page.parent != self.parent.page:
|
||||
self.page.unset_lock()
|
||||
self.page.parent = self.parent.page
|
||||
self.page.save(force_lock=True)
|
||||
|
||||
def save(self, *args, **kwargs):
|
||||
with transaction.atomic():
|
||||
creation = False
|
||||
@ -122,6 +155,7 @@ class Club(models.Model):
|
||||
self.home.edit_groups = [board]
|
||||
self.home.view_groups = [member, subscribers]
|
||||
self.home.save()
|
||||
self.make_page()
|
||||
|
||||
def __str__(self):
|
||||
return self.name
|
||||
@ -313,8 +347,14 @@ class MailingSubscription(models.Model):
|
||||
def can_be_edited_by(self, user):
|
||||
return (self.user is not None and user.id == self.user.id)
|
||||
|
||||
@property
|
||||
def get_email(self):
|
||||
if self.user and not self.email:
|
||||
return self.user.email
|
||||
return self.email
|
||||
|
||||
def fetch_format(self):
|
||||
return self.email + ' '
|
||||
return self.get_email + ' '
|
||||
|
||||
def __str__(self):
|
||||
if self.user:
|
||||
|
@ -2,7 +2,16 @@
|
||||
{% from 'core/macros.jinja' import user_profile_link %}
|
||||
|
||||
{% block content %}
|
||||
<h3>{% trans %}Club{% endtrans %}</h3>
|
||||
<div id="club_detail">
|
||||
{% if club.logo %}
|
||||
<div class="club_logo"><img src="{{ club.logo.url }}" alt="{{ club.unix_name }}"></div>
|
||||
{% endif %}
|
||||
{% if page_revision %}
|
||||
{{ page_revision|markdown }}
|
||||
{% else %}
|
||||
<h3>{% trans %}Club{% endtrans %}</h3>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endblock %}
|
||||
|
||||
|
||||
|
@ -5,7 +5,20 @@
|
||||
{% endblock %}
|
||||
|
||||
{% macro display_club(club) -%}
|
||||
<li><a href="{{ url('club:club_view', club_id=club.id) }}">{{ club.name }}</a>
|
||||
|
||||
{% if club.is_active or user.is_root %}
|
||||
|
||||
<li><a href="{{ url('club:club_view', club_id=club.id) }}">{{ club.name }}</a>
|
||||
|
||||
{% if not club.is_active %}
|
||||
({% trans %}inactive{% endtrans %})
|
||||
{% endif %}
|
||||
|
||||
{% if club.president %} - <a href="{{ url('core:user_profile', user_id=club.president.user.id) }}">{{ club.president.user }}</a>{% endif %}
|
||||
{% if club.short_description %}<p>{{ club.short_description|markdown }}</p>{% endif %}
|
||||
|
||||
{% endif %}
|
||||
|
||||
{%- if club.children.all()|length != 0 %}
|
||||
<ul>
|
||||
{%- for c in club.children.order_by('name') %}
|
||||
@ -23,7 +36,7 @@
|
||||
{% if club_list %}
|
||||
<h3>{% trans %}Club list{% endtrans %}</h3>
|
||||
<ul>
|
||||
{%- for c in club_list.order_by('name') if c.parent is none %}
|
||||
{%- for c in club_list.all().order_by('name') if c.parent is none %}
|
||||
{{ display_club(c) }}
|
||||
{%- endfor %}
|
||||
</ul>
|
||||
|
@ -16,6 +16,12 @@
|
||||
<a href="{{ url('club:mailing_delete', mailing_id=mailing.id) }}"> - {% trans %}Delete{% endtrans %}</a>
|
||||
{%- endif -%}
|
||||
</h2>
|
||||
<form method="GET" action="{{ url('club:mailing_generate', mailing_id=mailing.id) }}" style="display:inline-block;">
|
||||
<input type="submit" name="generateMalingList" value="{% trans %}Generate mailing list{% endtrans %}">
|
||||
</form>
|
||||
<form method="GET" action="{{ url('club:mailing_clean', mailing_id=mailing.id) }}" style="display:inline-block;">
|
||||
<input type="submit" name="cleanMailingList" value="{% trans %}Clean mailing list{% endtrans %}">
|
||||
</form>
|
||||
<hr>
|
||||
<table>
|
||||
<tr>
|
||||
@ -29,7 +35,7 @@
|
||||
{% else %}
|
||||
<td>{% trans %}Unregistered user{% endtrans %}</td>
|
||||
{% endif %}
|
||||
<td>{{ subscriber.email }}</td>
|
||||
<td>{{ subscriber.get_email }}</td>
|
||||
<td><a href="{{ url('club:mailing_subscription_delete', mailing_subscription_id=subscriber.id) }}">{% trans %}Delete{% endtrans %}</a></td>
|
||||
</tr>
|
||||
{% endfor %}
|
||||
|
13
club/templates/club/page_history.jinja
Normal file
13
club/templates/club/page_history.jinja
Normal file
@ -0,0 +1,13 @@
|
||||
{% extends "core/base.jinja" %}
|
||||
{% from 'core/macros_pages.jinja' import page_history %}
|
||||
|
||||
{% block content %}
|
||||
{% if club.page %}
|
||||
{{ page_history(club.page) }}
|
||||
{% else %}
|
||||
{% trans %}No page existing for this club{% endtrans %}
|
||||
{% endif %}
|
||||
{% endblock %}
|
||||
|
||||
|
||||
|
14
club/templates/club/pagerev_edit.jinja
Normal file
14
club/templates/club/pagerev_edit.jinja
Normal file
@ -0,0 +1,14 @@
|
||||
{% extends "core/base.jinja" %}
|
||||
{% from 'core/macros_pages.jinja' import markdown_preview_script, page_edit_form %}
|
||||
|
||||
{% block head %}
|
||||
{{ super() }}
|
||||
{{ markdown_preview_script(csrf_token) }}
|
||||
{% endblock %}
|
||||
|
||||
{% block content %}
|
||||
{{ page_edit_form(page, form, url('club:club_edit_page', club_id=page.club.id), csrf_token) }}
|
||||
{% endblock %}
|
||||
|
||||
|
||||
|
@ -32,7 +32,10 @@ urlpatterns = [
|
||||
url(r'^new$', ClubCreateView.as_view(), name='club_new'),
|
||||
url(r'^stats$', ClubStatView.as_view(), name='club_stats'),
|
||||
url(r'^(?P<club_id>[0-9]+)/$', ClubView.as_view(), name='club_view'),
|
||||
url(r'^(?P<club_id>[0-9]+)/rev/(?P<rev_id>[0-9]+)/$', ClubRevView.as_view(), name='club_view_rev'),
|
||||
url(r'^(?P<club_id>[0-9]+)/hist$', ClubPageHistView.as_view(), name='club_hist'),
|
||||
url(r'^(?P<club_id>[0-9]+)/edit$', ClubEditView.as_view(), name='club_edit'),
|
||||
url(r'^(?P<club_id>[0-9]+)/edit/page$', ClubPageEditView.as_view(), name='club_edit_page'),
|
||||
url(r'^(?P<club_id>[0-9]+)/members$', ClubMembersView.as_view(), name='club_members'),
|
||||
url(r'^(?P<club_id>[0-9]+)/elderlies$', ClubOldMembersView.as_view(), name='club_old_members'),
|
||||
url(r'^(?P<club_id>[0-9]+)/sellings$', ClubSellingView.as_view(), name='club_sellings'),
|
||||
@ -42,6 +45,8 @@ urlpatterns = [
|
||||
url(r'^(?P<club_id>[0-9]+)/mailing$', ClubMailingView.as_view(action="display"), name='mailing'),
|
||||
url(r'^(?P<club_id>[0-9]+)/mailing/new/mailing$', ClubMailingView.as_view(action="add_mailing"), name='mailing_create'),
|
||||
url(r'^(?P<club_id>[0-9]+)/mailing/new/subscription$', ClubMailingView.as_view(action="add_member"), name='mailing_subscription_create'),
|
||||
url(r'^(?P<mailing_id>[0-9]+)/mailing/generate$', MailingAutoGenerationView.as_view(), name='mailing_generate'),
|
||||
url(r'^(?P<mailing_id>[0-9]+)/mailing/clean$', MailingAutoCleanView.as_view(), name='mailing_clean'),
|
||||
url(r'^(?P<mailing_id>[0-9]+)/mailing/delete$', MailingDeleteView.as_view(), name='mailing_delete'),
|
||||
url(r'^(?P<mailing_subscription_id>[0-9]+)/mailing/delete/subscription$', MailingSubscriptionDeleteView.as_view(), name='mailing_subscription_delete'),
|
||||
url(r'^membership/(?P<membership_id>[0-9]+)/set_old$', MembershipSetOldView.as_view(), name='membership_set_old'),
|
||||
|
139
club/views.py
139
club/views.py
@ -24,25 +24,25 @@
|
||||
#
|
||||
|
||||
from django import forms
|
||||
from django.views.generic import ListView, DetailView, TemplateView
|
||||
from django.views.generic import ListView, DetailView, TemplateView, View
|
||||
from django.views.generic.edit import DeleteView
|
||||
from django.views.generic.detail import SingleObjectMixin
|
||||
from django.views.generic.edit import UpdateView, CreateView
|
||||
from django.http import HttpResponseRedirect, HttpResponse
|
||||
from django.http import HttpResponseRedirect, HttpResponse, Http404
|
||||
from django.core.urlresolvers import reverse, reverse_lazy
|
||||
from django.utils import timezone
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
from django.utils.translation import ugettext as _t
|
||||
from ajax_select.fields import AutoCompleteSelectField
|
||||
from django.core.exceptions import PermissionDenied
|
||||
from django.shortcuts import get_object_or_404
|
||||
from django.shortcuts import get_object_or_404, redirect
|
||||
|
||||
from core.views import CanViewMixin, CanEditMixin, CanEditPropMixin, TabedViewMixin
|
||||
from core.views import CanViewMixin, CanEditMixin, CanEditPropMixin, TabedViewMixin, PageEditViewBase
|
||||
from core.views.forms import SelectDate, SelectDateTime
|
||||
from club.models import Club, Membership, Mailing, MailingSubscription
|
||||
from sith.settings import SITH_MAXIMUM_FREE_ROLE
|
||||
from counter.models import Selling, Counter
|
||||
from core.models import User
|
||||
from core.models import User, PageRev
|
||||
|
||||
from django.conf import settings
|
||||
|
||||
@ -86,6 +86,8 @@ class MailingSubscriptionForm(forms.ModelForm):
|
||||
|
||||
class ClubTabsMixin(TabedViewMixin):
|
||||
def get_tabs_title(self):
|
||||
if isinstance(self.object, PageRev):
|
||||
self.object = self.object.page.club
|
||||
return self.object.get_display_name()
|
||||
|
||||
def get_list_of_tabs(self):
|
||||
@ -106,6 +108,12 @@ class ClubTabsMixin(TabedViewMixin):
|
||||
'slug': 'elderlies',
|
||||
'name': _("Old members"),
|
||||
})
|
||||
if self.object.page:
|
||||
tab_list.append({
|
||||
'url': reverse('club:club_hist', kwargs={'club_id': self.object.id}),
|
||||
'slug': 'history',
|
||||
'name': _("History"),
|
||||
})
|
||||
if self.request.user.can_edit(self.object):
|
||||
tab_list.append({
|
||||
'url': reverse('club:tools', kwargs={'club_id': self.object.id}),
|
||||
@ -117,6 +125,12 @@ class ClubTabsMixin(TabedViewMixin):
|
||||
'slug': 'edit',
|
||||
'name': _("Edit"),
|
||||
})
|
||||
if self.object.page and self.request.user.can_edit(self.object.page):
|
||||
tab_list.append({
|
||||
'url': reverse('core:page_edit', kwargs={'page_name': self.object.page.get_full_name()}),
|
||||
'slug': 'page_edit',
|
||||
'name': _('Edit club page')
|
||||
})
|
||||
tab_list.append({
|
||||
'url': reverse('club:club_sellings', kwargs={'club_id': self.object.id}),
|
||||
'slug': 'sellings',
|
||||
@ -153,6 +167,55 @@ class ClubView(ClubTabsMixin, DetailView):
|
||||
template_name = 'club/club_detail.jinja'
|
||||
current_tab = "infos"
|
||||
|
||||
def get_context_data(self, **kwargs):
|
||||
kwargs = super(ClubView, self).get_context_data(**kwargs)
|
||||
if self.object.page and self.object.page.revisions.exists():
|
||||
kwargs['page_revision'] = self.object.page.revisions.last().content
|
||||
return kwargs
|
||||
|
||||
|
||||
class ClubRevView(ClubView):
|
||||
"""
|
||||
Display a specific page revision
|
||||
"""
|
||||
def dispatch(self, request, *args, **kwargs):
|
||||
obj = self.get_object()
|
||||
self.revision = get_object_or_404(PageRev, pk=kwargs['rev_id'], page__club=obj)
|
||||
return super(ClubRevView, self).dispatch(request, *args, **kwargs)
|
||||
|
||||
def get_context_data(self, **kwargs):
|
||||
kwargs = super(ClubRevView, self).get_context_data(**kwargs)
|
||||
kwargs['page_revision'] = self.revision.content
|
||||
return kwargs
|
||||
|
||||
|
||||
class ClubPageEditView(ClubTabsMixin, PageEditViewBase):
|
||||
template_name = 'club/pagerev_edit.jinja'
|
||||
current_tab = "page_edit"
|
||||
|
||||
def dispatch(self, request, *args, **kwargs):
|
||||
self.club = get_object_or_404(Club, pk=kwargs['club_id'])
|
||||
if not self.club.page:
|
||||
raise Http404
|
||||
return super(ClubPageEditView, self).dispatch(request, *args, **kwargs)
|
||||
|
||||
def get_object(self):
|
||||
self.page = self.club.page
|
||||
return self._get_revision()
|
||||
|
||||
def get_success_url(self, **kwargs):
|
||||
return reverse_lazy('club:club_view', kwargs={'club_id': self.club.id})
|
||||
|
||||
|
||||
class ClubPageHistView(ClubTabsMixin, CanViewMixin, DetailView):
|
||||
"""
|
||||
Modification hostory of the page
|
||||
"""
|
||||
model = Club
|
||||
pk_url_kwarg = "club_id"
|
||||
template_name = 'club/page_history.jinja'
|
||||
current_tab = "history"
|
||||
|
||||
|
||||
class ClubToolsView(ClubTabsMixin, CanEditMixin, DetailView):
|
||||
"""
|
||||
@ -209,29 +272,31 @@ class ClubMembersView(ClubTabsMixin, CanViewMixin, UpdateView):
|
||||
form.instance = Membership(club=self.object, user=self.request.user)
|
||||
if not self.request.user.is_root:
|
||||
form.fields.pop('start_date', None)
|
||||
# form.initial = {'user': self.request.user}
|
||||
# form._user = self.request.user
|
||||
return form
|
||||
|
||||
def post(self, request, *args, **kwargs):
|
||||
def form_valid(self, form):
|
||||
"""
|
||||
Check user rights
|
||||
"""
|
||||
self.object = self.get_object()
|
||||
form = self.get_form()
|
||||
if form.is_valid():
|
||||
ms = self.object.get_membership_for(request.user)
|
||||
if (form.cleaned_data['role'] <= SITH_MAXIMUM_FREE_ROLE or
|
||||
(ms is not None and ms.role >= form.cleaned_data['role']) or
|
||||
request.user.is_board_member or
|
||||
request.user.is_root):
|
||||
return self.form_valid(form)
|
||||
else:
|
||||
form.add_error(None, _("You do not have the permission to do that"))
|
||||
return self.form_invalid(form)
|
||||
user = self.request.user
|
||||
ms = self.object.get_membership_for(user)
|
||||
if (form.cleaned_data['role'] <= SITH_MAXIMUM_FREE_ROLE or
|
||||
(ms is not None and ms.role >= form.cleaned_data['role']) or
|
||||
user.is_board_member or user.is_root):
|
||||
form.save()
|
||||
form = self.form_class()
|
||||
return super(ModelFormMixin, self).form_valid(form)
|
||||
else:
|
||||
form.add_error(None, _("You do not have the permission to do that"))
|
||||
return self.form_invalid(form)
|
||||
|
||||
def dispatch(self, request, *args, **kwargs):
|
||||
self.request = request
|
||||
return super(ClubMembersView, self).dispatch(request, *args, **kwargs)
|
||||
|
||||
def get_success_url(self, **kwargs):
|
||||
return reverse_lazy('club:club_members', kwargs={'club_id': self.club.id})
|
||||
|
||||
|
||||
class ClubOldMembersView(ClubTabsMixin, CanViewMixin, DetailView):
|
||||
"""
|
||||
@ -337,7 +402,7 @@ class ClubEditView(ClubTabsMixin, CanEditMixin, UpdateView):
|
||||
"""
|
||||
model = Club
|
||||
pk_url_kwarg = "club_id"
|
||||
fields = ['address', 'logo']
|
||||
fields = ['address', 'logo', 'short_description']
|
||||
template_name = 'core/edit.jinja'
|
||||
current_tab = "edit"
|
||||
|
||||
@ -348,7 +413,7 @@ class ClubEditPropView(ClubTabsMixin, CanEditPropMixin, UpdateView):
|
||||
"""
|
||||
model = Club
|
||||
pk_url_kwarg = "club_id"
|
||||
fields = ['name', 'unix_name', 'parent']
|
||||
fields = ['name', 'unix_name', 'parent', 'is_active']
|
||||
template_name = 'core/edit.jinja'
|
||||
current_tab = "props"
|
||||
|
||||
@ -497,3 +562,33 @@ class MailingSubscriptionDeleteView(CanEditMixin, DeleteView):
|
||||
|
||||
def get_success_url(self, **kwargs):
|
||||
return reverse_lazy('club:mailing', kwargs={'club_id': self.club_id})
|
||||
|
||||
|
||||
class MailingAutoGenerationView(View):
|
||||
|
||||
def dispatch(self, request, *args, **kwargs):
|
||||
self.mailing = get_object_or_404(Mailing, pk=kwargs['mailing_id'])
|
||||
if not request.user.can_edit(self.mailing):
|
||||
raise PermissionDenied
|
||||
return super(MailingAutoGenerationView, self).dispatch(request, *args, **kwargs)
|
||||
|
||||
def get(self, request, *args, **kwargs):
|
||||
club = self.mailing.club
|
||||
self.mailing.subscriptions.all().delete()
|
||||
members = club.members.filter(role__gte=settings.SITH_CLUB_ROLES_ID['Board member']).exclude(end_date__lte=timezone.now())
|
||||
for member in members.all():
|
||||
MailingSubscription(user=member.user, mailing=self.mailing).save()
|
||||
return redirect('club:mailing', club_id=club.id)
|
||||
|
||||
|
||||
class MailingAutoCleanView(View):
|
||||
|
||||
def dispatch(self, request, *args, **kwargs):
|
||||
self.mailing = get_object_or_404(Mailing, pk=kwargs['mailing_id'])
|
||||
if not request.user.can_edit(self.mailing):
|
||||
raise PermissionDenied
|
||||
return super(MailingAutoCleanView, self).dispatch(request, *args, **kwargs)
|
||||
|
||||
def get(self, request, *args, **kwargs):
|
||||
self.mailing.subscriptions.all().delete()
|
||||
return redirect('club:mailing', club_id=self.mailing.club.id)
|
||||
|
@ -85,6 +85,12 @@ class Command(BaseCommand):
|
||||
profiles_root.save()
|
||||
home_root = SithFile(parent=None, name="users", is_folder=True, owner=root)
|
||||
home_root.save()
|
||||
|
||||
# Page needed for club creation
|
||||
p = Page(name=settings.SITH_CLUB_ROOT_PAGE)
|
||||
p.set_lock(root)
|
||||
p.save()
|
||||
|
||||
club_root = SithFile(parent=None, name="clubs", is_folder=True, owner=root)
|
||||
club_root.save()
|
||||
SithFile(parent=None, name="SAS", is_folder=True, owner=root).save()
|
||||
@ -97,6 +103,7 @@ class Command(BaseCommand):
|
||||
launderette_club = Club(id=84, name=settings.SITH_LAUNDERETTE_MANAGER['name'],
|
||||
unix_name=settings.SITH_LAUNDERETTE_MANAGER['unix_name'],
|
||||
address=settings.SITH_LAUNDERETTE_MANAGER['address'])
|
||||
|
||||
launderette_club.save()
|
||||
self.reset_index("club")
|
||||
for b in settings.SITH_COUNTER_BARS:
|
||||
|
20
core/migrations/0025_auto_20170919_1521.py
Normal file
20
core/migrations/0025_auto_20170919_1521.py
Normal file
@ -0,0 +1,20 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
from __future__ import unicode_literals
|
||||
|
||||
from django.db import migrations, models
|
||||
import django.core.validators
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('core', '0024_auto_20170906_1317'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.AlterField(
|
||||
model_name='page',
|
||||
name='name',
|
||||
field=models.CharField(max_length=30, verbose_name='page unix name', validators=[django.core.validators.RegexValidator('^[a-zA-Z0-9][a-zA-Z0-9._-]*[a-zA-Z0-9]$', 'Enter a valid page name. This value may contain only unaccented letters, numbers and ./+/-/_ characters.')]),
|
||||
),
|
||||
]
|
19
core/migrations/0026_auto_20170926_1512.py
Normal file
19
core/migrations/0026_auto_20170926_1512.py
Normal file
@ -0,0 +1,19 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
from __future__ import unicode_literals
|
||||
|
||||
from django.db import migrations, models
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('core', '0025_auto_20170919_1521'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.AlterField(
|
||||
model_name='notification',
|
||||
name='type',
|
||||
field=models.CharField(choices=[('MAILING_MODERATION', 'A new mailing list needs to be moderated'), ('NEWS_MODERATION', 'There are %s fresh news to be moderated'), ('FILE_MODERATION', 'New files to be moderated'), ('SAS_MODERATION', 'There are %s pictures to be moderated in the SAS'), ('NEW_PICTURES', "You've been identified on some pictures"), ('REFILLING', 'You just refilled of %s €'), ('SELLING', 'You just bought %s'), ('GENERIC', 'You have a notification')], verbose_name='type', max_length=32, default='GENERIC'),
|
||||
),
|
||||
]
|
@ -841,7 +841,7 @@ class Page(models.Model):
|
||||
name = models.CharField(_('page unix name'), max_length=30,
|
||||
validators=[
|
||||
validators.RegexValidator(
|
||||
r'^[A-z.+-]+$',
|
||||
r'^[a-zA-Z0-9][a-zA-Z0-9._-]*[a-zA-Z0-9]$',
|
||||
_('Enter a valid page name. This value may contain only '
|
||||
'unaccented letters, numbers ' 'and ./+/-/_ characters.')
|
||||
), ],
|
||||
@ -892,6 +892,19 @@ class Page(models.Model):
|
||||
code='loop',
|
||||
)
|
||||
|
||||
def can_be_edited_by(self, user):
|
||||
if hasattr(self, 'club') and self.club.can_be_edited_by(user):
|
||||
# Override normal behavior for clubs
|
||||
return True
|
||||
if self.name == settings.SITH_CLUB_ROOT_PAGE and user.is_board_member:
|
||||
return True
|
||||
return False
|
||||
|
||||
def can_be_viewed_by(self, user):
|
||||
if self.is_club_page:
|
||||
return True
|
||||
return False
|
||||
|
||||
def get_parent_list(self):
|
||||
l = []
|
||||
p = self.parent
|
||||
@ -999,6 +1012,15 @@ class Page(models.Model):
|
||||
except:
|
||||
return self.name
|
||||
|
||||
@cached_property
|
||||
def is_club_page(self):
|
||||
club_root_page = Page.objects.filter(name=settings.SITH_CLUB_ROOT_PAGE).first()
|
||||
return club_root_page is not None and (self == club_root_page or club_root_page in self.get_parent_list())
|
||||
|
||||
@cached_property
|
||||
def need_club_redirection(self):
|
||||
return self.is_club_page and self.name != settings.SITH_CLUB_ROOT_PAGE
|
||||
|
||||
def delete(self):
|
||||
self.unset_lock_recursive()
|
||||
self.set_lock_recursive(User.objects.get(id=0))
|
||||
@ -1048,6 +1070,9 @@ class PageRev(models.Model):
|
||||
else:
|
||||
return object.__getattribute__(self, attr)
|
||||
|
||||
def can_be_edited_by(self, user):
|
||||
return self.page.can_be_edited_by(user)
|
||||
|
||||
def save(self, *args, **kwargs):
|
||||
if self.revision is None:
|
||||
self.revision = self.page.revisions.all().count() + 1
|
||||
|
50
core/operations.py
Normal file
50
core/operations.py
Normal file
@ -0,0 +1,50 @@
|
||||
# -*- coding:utf-8 -*
|
||||
#
|
||||
# Copyright 2016,2017
|
||||
# - Sli <antoine@bartuccio.fr>
|
||||
#
|
||||
# Ce fichier fait partie du site de l'Association des Étudiants de l'UTBM,
|
||||
# http://ae.utbm.fr.
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify it under
|
||||
# the terms of the GNU General Public License a published by the Free Software
|
||||
# Foundation; either version 3 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 Sofware Foundation, Inc., 59 Temple
|
||||
# Place - Suite 330, Boston, MA 02111-1307, USA.
|
||||
#
|
||||
#
|
||||
|
||||
"""
|
||||
This page is useful for custom migration tricks.
|
||||
Sometimes, when you need to have a migration hack and you think it can be
|
||||
useful again, put it there, we never know if we might need the hack again.
|
||||
"""
|
||||
|
||||
from django.db import connection, migrations
|
||||
|
||||
|
||||
class PsqlRunOnly(migrations.RunSQL):
|
||||
"""
|
||||
This is an SQL runner that will launch the given command only if
|
||||
the used DBMS is PostgreSQL.
|
||||
It may be useful to run Postgres' specific SQL, or to take actions
|
||||
that would be non-senses with backends other than Postgre, such
|
||||
as disabling particular constraints that would prevent the migration
|
||||
to run successfully.
|
||||
|
||||
See `club/migrations/0010_auto_20170912_2028.py` as an example.
|
||||
Some explanations can be found here too:
|
||||
https://stackoverflow.com/questions/28429933/django-migrations-using-runpython-to-commit-changes
|
||||
"""
|
||||
|
||||
def _run_sql(self, schema_editor, sqls):
|
||||
if connection.vendor == 'postgresql':
|
||||
super(PsqlRunOnly, self)._run_sql(schema_editor, sqls)
|
@ -1224,3 +1224,15 @@ label {
|
||||
.ui-corner-left {
|
||||
border-radius: 0px;
|
||||
}
|
||||
|
||||
#club_detail {
|
||||
.club_logo {
|
||||
float: right;
|
||||
img {
|
||||
display: block;
|
||||
max-height: 10em;
|
||||
max-width: 10em;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -150,6 +150,7 @@
|
||||
{% if not popup %}
|
||||
<nav>
|
||||
<a href="{{ url('core:index') }}">{% trans %}Main{% endtrans %}</a>
|
||||
<a href="{{ url('core:page', page_name='clubs') }}">{% trans %}Clubs{% endtrans %}</a>
|
||||
<a href="{{ url('matmat:search_clear') }}">{% trans %}Matmatronch{% endtrans %}</a>
|
||||
<a href="{{ url('core:page', page_name="Index") }}">{% trans %}Wiki{% endtrans %}</a>
|
||||
<a href="{{ url('sas:main') }}">{% trans %}SAS{% endtrans %}</a>
|
||||
|
@ -125,4 +125,4 @@
|
||||
{% else %}
|
||||
<span class="disabled">{% trans %}Next{% endtrans %}</span>
|
||||
{% endif %}
|
||||
{% endmacro %}
|
||||
{% endmacro %}
|
||||
|
50
core/templates/core/macros_pages.jinja
Normal file
50
core/templates/core/macros_pages.jinja
Normal file
@ -0,0 +1,50 @@
|
||||
{% from "core/macros.jinja" import user_profile_link %}
|
||||
|
||||
{% macro page_history(page) %}
|
||||
<p>{% trans page_name=page.name %}You're seeing the history of page "{{ page_name }}"{% endtrans %}</p>
|
||||
<ul>
|
||||
{% for r in (page.revisions.all()|sort(attribute='date', reverse=True)) %}
|
||||
{% if loop.index < 2 %}
|
||||
<li><a href="{{ url('core:page', page_name=page.get_full_name()) }}">{% trans %}last{% endtrans %}</a> -
|
||||
{{ user_profile_link(page.revisions.last().author) }} -
|
||||
{{ page.revisions.last().date|localtime|date(DATETIME_FORMAT) }} {{ page.revisions.last().date|localtime|time(DATETIME_FORMAT) }}</a></li>
|
||||
{% else %}
|
||||
<li><a href="{{ url('core:page_rev', page_name=page.get_full_name(), rev=r['id']) }}">{{ r.revision }}</a> -
|
||||
{{ user_profile_link(r.author) }} -
|
||||
{{ r.date|localtime|date(DATETIME_FORMAT) }} {{ r.date|localtime|time(DATETIME_FORMAT) }}</a></li>
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
</ul>
|
||||
{% endmacro %}
|
||||
|
||||
{% macro page_edit_form(page, form, url, token) %}
|
||||
<h2>{% trans %}Edit page{% endtrans %}</h2>
|
||||
<form action="{{ url }}" method="post">
|
||||
<input type="hidden" name="csrfmiddlewaretoken" value="{{ token }}">
|
||||
{{ form.as_p() }}
|
||||
{{ markdown_preview_button() }}
|
||||
<p><input type="submit" value="{% trans %}Save{% endtrans %}" /></p>
|
||||
</form>
|
||||
<div id="preview" class="page_content">
|
||||
</div>
|
||||
{% endmacro %}
|
||||
|
||||
{% macro markdown_preview_script(token) %}
|
||||
<script>
|
||||
function make_preview() {
|
||||
text = $("#id_content").val();
|
||||
console.log("Rendering text: " + text);
|
||||
$.ajax({
|
||||
url: "{{ url('api:api_markdown') }}",
|
||||
method: "POST",
|
||||
data: { text: text, csrfmiddlewaretoken: "{{ token }}"}
|
||||
}).done(function (msg) {
|
||||
$("#preview").html(msg);
|
||||
});
|
||||
}
|
||||
</script>
|
||||
{% endmacro %}
|
||||
|
||||
{% macro markdown_preview_button() %}
|
||||
<p><input type="button" value="{% trans %}Preview{% endtrans %}" onclick="javascript:make_preview();" /></p>
|
||||
{% endmacro %}
|
@ -25,12 +25,16 @@
|
||||
<div class="tool_bar">
|
||||
<div class="tools">
|
||||
{% if page %}
|
||||
{% if page.club %}
|
||||
<a href="{{ url('club:club_view', club_id=page.club.id) }}">{% trans %}Return to club management{% endtrans %}</a>
|
||||
{% else %}
|
||||
<a href="{{ url('core:page', page.get_full_name()) }}">{% trans %}View{% endtrans %}</a>
|
||||
{% endif %}
|
||||
<a href="{{ url('core:page_hist', page_name=page.get_full_name()) }}">{% trans %}History{% endtrans %}</a>
|
||||
{% if can_edit(page, user) %}
|
||||
<a href="{{ url('core:page_edit', page_name=page.get_full_name()) }}">{% trans %}Edit{% endtrans %}</a>
|
||||
{% endif %}
|
||||
{% if can_edit_prop(page, user) %}
|
||||
{% if can_edit_prop(page, user) and not page.is_club_page %}
|
||||
<a href="{{ url('core:page_prop', page_name=page.get_full_name()) }}">{% trans %}Prop{% endtrans %}</a>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
|
@ -1,23 +1,10 @@
|
||||
{% extends "core/page.jinja" %}
|
||||
|
||||
{% from "core/macros.jinja" import user_profile_link %}
|
||||
{% from "core/macros_pages.jinja" import page_history %}
|
||||
|
||||
{% block page %}
|
||||
<h3>{% trans %}Page history{% endtrans %}</h3>
|
||||
<p>{% trans page_name=page.name %}You're seeing the history of page "{{ page_name }}"{% endtrans %}</p>
|
||||
<ul>
|
||||
{% for r in (page.revisions.all()|sort(attribute='date', reverse=True)) %}
|
||||
{% if loop.index < 2 %}
|
||||
<li><a href="{{ url('core:page', page_name=page.get_full_name()) }}">{% trans %}last{% endtrans %}</a> -
|
||||
{{ user_profile_link(page.revisions.last().author) }} -
|
||||
{{ page.revisions.last().date|localtime|date(DATETIME_FORMAT) }} {{ page.revisions.last().date|localtime|time(DATETIME_FORMAT) }}</a></li>
|
||||
{% else %}
|
||||
<li><a href="{{ url('core:page_rev', page_name=page.get_full_name(), rev=r['id']) }}">{{ r.revision }}</a> -
|
||||
{{ user_profile_link(r.author) }} -
|
||||
{{ r.date|localtime|date(DATETIME_FORMAT) }} {{ r.date|localtime|time(DATETIME_FORMAT) }}</a></li>
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
</ul>
|
||||
{{ page_history(page) }}
|
||||
{% endblock %}
|
||||
|
||||
|
||||
|
@ -1,12 +1,18 @@
|
||||
{% extends "core/page.jinja" %}
|
||||
|
||||
{% block content %}
|
||||
{% if page %}
|
||||
{{ super() }}
|
||||
{% endif %}
|
||||
<h2>{% trans %}Page properties{% endtrans %}</h2>
|
||||
<form action="" method="post">
|
||||
{% csrf_token %}
|
||||
{{ form.as_p() }}
|
||||
<p><input type="submit" value="{% trans %}Save{% endtrans %}" /></p>
|
||||
</form>
|
||||
{% if page %}
|
||||
<a href="{{ url('core:page_delete', page_id=page.id)}}">{% trans %}Delete{% endtrans %}</a>
|
||||
{% endif %}
|
||||
{% endblock %}
|
||||
|
||||
|
||||
|
@ -1,33 +1,13 @@
|
||||
{% extends "core/page.jinja" %}
|
||||
{% from 'core/macros_pages.jinja' import markdown_preview_script, page_edit_form %}
|
||||
|
||||
{% block head %}
|
||||
{{ super() }}
|
||||
<script>
|
||||
function make_preview() {
|
||||
text = $("#id_content").val();
|
||||
console.log("Rendering text: " + text);
|
||||
$.ajax({
|
||||
url: "{{ url('api:api_markdown') }}",
|
||||
method: "POST",
|
||||
data: { text: text, csrfmiddlewaretoken: "{{ csrf_token }}"}
|
||||
}).done(function (msg) {
|
||||
$("#preview").html(msg);
|
||||
});
|
||||
}
|
||||
</script>
|
||||
{{ markdown_preview_script(csrf_token) }}
|
||||
{% endblock %}
|
||||
|
||||
{% block page %}
|
||||
<h2>{% trans %}Edit page{% endtrans %}</h2>
|
||||
<form action="{{ url('core:page_edit', page_name=page.get_full_name()) }}" method="post">
|
||||
{% csrf_token %}
|
||||
{{ form.as_p() }}
|
||||
<p><input type="button" value="{% trans %}Preview{% endtrans %}" onclick="javascript:make_preview();" /></p>
|
||||
<p><input type="submit" value="{% trans %}Save{% endtrans %}" /></p>
|
||||
</form>
|
||||
<a href="{{ url('core:page_delete', page_id=page.id)}}">{% trans %}Delete{% endtrans %}</a>
|
||||
<div id="preview" class="page_content">
|
||||
</div>
|
||||
{{ page_edit_form(page, form, url('core:page_edit', page_name=page.get_full_name()), csrf_token) }}
|
||||
{% endblock %}
|
||||
|
||||
|
||||
|
10
core/urls.py
10
core/urls.py
@ -87,9 +87,9 @@ urlpatterns = [
|
||||
url(r'^page/$', PageListView.as_view(), name='page_list'),
|
||||
url(r'^page/create$', PageCreateView.as_view(), name='page_new'),
|
||||
url(r'^page/(?P<page_id>[0-9]*)/delete$', PageDeleteView.as_view(), name='page_delete'),
|
||||
url(r'^page/(?P<page_name>[a-z0-9/-_]*)/edit$', PageEditView.as_view(), name='page_edit'),
|
||||
url(r'^page/(?P<page_name>[a-z0-9/-_]*)/prop$', PagePropView.as_view(), name='page_prop'),
|
||||
url(r'^page/(?P<page_name>[a-z0-9/-_]*)/hist$', PageHistView.as_view(), name='page_hist'),
|
||||
url(r'^page/(?P<page_name>[a-z0-9/-_]*)/rev/(?P<rev>[0-9]+)/', PageRevView.as_view(), name='page_rev'),
|
||||
url(r'^page/(?P<page_name>[a-z0-9/-_]*)/$', PageView.as_view(), name='page'),
|
||||
url(r'^page/(?P<page_name>([/a-zA-Z0-9][a-zA-Z0-9._-]*[a-zA-Z0-9])+)/edit$', PageEditView.as_view(), name='page_edit'),
|
||||
url(r'^page/(?P<page_name>([/a-zA-Z0-9][a-zA-Z0-9._-]*[a-zA-Z0-9])+)/prop$', PagePropView.as_view(), name='page_prop'),
|
||||
url(r'^page/(?P<page_name>([/a-zA-Z0-9][a-zA-Z0-9._-]*[a-zA-Z0-9])+)/hist$', PageHistView.as_view(), name='page_hist'),
|
||||
url(r'^page/(?P<page_name>([/a-zA-Z0-9][a-zA-Z0-9._-]*[a-zA-Z0-9])+)/rev/(?P<rev>[0-9]+)/', PageRevView.as_view(), name='page_rev'),
|
||||
url(r'^page/(?P<page_name>([/a-zA-Z0-9][a-zA-Z0-9._-]*[a-zA-Z0-9])+)/$', PageView.as_view(), name='page'),
|
||||
]
|
||||
|
@ -269,3 +269,17 @@ class PagePropForm(forms.ModelForm):
|
||||
super(PagePropForm, self).__init__(*arg, **kwargs)
|
||||
self.fields['edit_groups'].required = False
|
||||
self.fields['view_groups'].required = False
|
||||
|
||||
|
||||
class PageForm(forms.ModelForm):
|
||||
class Meta:
|
||||
model = Page
|
||||
fields = ['parent', 'name', 'owner_group', 'edit_groups', 'view_groups']
|
||||
widgets = {
|
||||
'edit_groups': CheckboxSelectMultiple,
|
||||
'view_groups': CheckboxSelectMultiple,
|
||||
}
|
||||
|
||||
def __init__(self, *args, **kwargs):
|
||||
super(PageForm, self).__init__(*args, **kwargs)
|
||||
self.fields['parent'].queryset = self.fields['parent'].queryset.exclude(name=settings.SITH_CLUB_ROOT_PAGE).filter(club=None)
|
||||
|
@ -27,13 +27,23 @@ from django.core.urlresolvers import reverse_lazy
|
||||
from django.views.generic import ListView, DetailView
|
||||
from django.views.generic.edit import UpdateView, CreateView, DeleteView
|
||||
from django.forms.models import modelform_factory
|
||||
from django.forms import CheckboxSelectMultiple
|
||||
from django.http import Http404
|
||||
from django.shortcuts import redirect
|
||||
|
||||
from core.models import Page, PageRev, LockError
|
||||
from core.views.forms import MarkdownInput
|
||||
from core.views.forms import MarkdownInput, PageForm, PagePropForm
|
||||
from core.views import CanViewMixin, CanEditMixin, CanEditPropMixin, CanCreateMixin
|
||||
|
||||
|
||||
class CanEditPagePropMixin(CanEditPropMixin):
|
||||
|
||||
def dispatch(self, request, *args, **kwargs):
|
||||
res = super(CanEditPagePropMixin, self).dispatch(request, *args, **kwargs)
|
||||
if self.object.is_club_page:
|
||||
raise Http404
|
||||
return res
|
||||
|
||||
|
||||
class PageListView(CanViewMixin, ListView):
|
||||
model = Page
|
||||
template_name = 'core/page_list.jinja'
|
||||
@ -43,6 +53,12 @@ class PageView(CanViewMixin, DetailView):
|
||||
model = Page
|
||||
template_name = 'core/page_detail.jinja'
|
||||
|
||||
def dispatch(self, request, *args, **kwargs):
|
||||
res = super(PageView, self).dispatch(request, *args, **kwargs)
|
||||
if self.object and self.object.need_club_redirection:
|
||||
return redirect('club:club_view', club_id=self.object.club.id)
|
||||
return res
|
||||
|
||||
def get_object(self):
|
||||
self.page = Page.get_page_by_full_name(self.kwargs['page_name'])
|
||||
return self.page
|
||||
@ -58,6 +74,12 @@ class PageHistView(CanViewMixin, DetailView):
|
||||
model = Page
|
||||
template_name = 'core/page_hist.jinja'
|
||||
|
||||
def dispatch(self, request, *args, **kwargs):
|
||||
res = super(PageHistView, self).dispatch(request, *args, **kwargs)
|
||||
if self.object.need_club_redirection:
|
||||
return redirect('club:club_hist', club_id=self.object.club.id)
|
||||
return res
|
||||
|
||||
def get_object(self):
|
||||
self.page = Page.get_page_by_full_name(self.kwargs['page_name'])
|
||||
return self.page
|
||||
@ -67,6 +89,12 @@ class PageRevView(CanViewMixin, DetailView):
|
||||
model = Page
|
||||
template_name = 'core/page_detail.jinja'
|
||||
|
||||
def dispatch(self, request, *args, **kwargs):
|
||||
res = super(PageRevView, self).dispatch(request, *args, **kwargs)
|
||||
if self.object.need_club_redirection:
|
||||
return redirect('club:club_view_rev', club_id=self.object.club.id, rev_id=kwargs['rev'])
|
||||
return res
|
||||
|
||||
def get_object(self):
|
||||
self.page = Page.get_page_by_full_name(self.kwargs['page_name'])
|
||||
return self.page
|
||||
@ -88,12 +116,7 @@ class PageRevView(CanViewMixin, DetailView):
|
||||
|
||||
class PageCreateView(CanCreateMixin, CreateView):
|
||||
model = Page
|
||||
form_class = modelform_factory(Page,
|
||||
fields=['parent', 'name', 'owner_group', 'edit_groups', 'view_groups', ],
|
||||
widgets={
|
||||
'edit_groups': CheckboxSelectMultiple,
|
||||
'view_groups': CheckboxSelectMultiple,
|
||||
})
|
||||
form_class = PageForm
|
||||
template_name = 'core/page_prop.jinja'
|
||||
|
||||
def get_initial(self):
|
||||
@ -118,14 +141,9 @@ class PageCreateView(CanCreateMixin, CreateView):
|
||||
return ret
|
||||
|
||||
|
||||
class PagePropView(CanEditPropMixin, UpdateView):
|
||||
class PagePropView(CanEditPagePropMixin, UpdateView):
|
||||
model = Page
|
||||
form_class = modelform_factory(Page,
|
||||
fields=['parent', 'name', 'owner_group', 'edit_groups', 'view_groups', ],
|
||||
widgets={
|
||||
'edit_groups': CheckboxSelectMultiple,
|
||||
'view_groups': CheckboxSelectMultiple,
|
||||
})
|
||||
form_class = PagePropForm
|
||||
template_name = 'core/page_prop.jinja'
|
||||
slug_field = '_full_name'
|
||||
slug_url_kwarg = 'page_name'
|
||||
@ -149,17 +167,20 @@ class PagePropView(CanEditPropMixin, UpdateView):
|
||||
return self.page
|
||||
|
||||
|
||||
class PageEditView(CanEditMixin, UpdateView):
|
||||
class PageEditViewBase(CanEditMixin, UpdateView):
|
||||
model = PageRev
|
||||
form_class = modelform_factory(model=PageRev, fields=['title', 'content', ], widgets={'content': MarkdownInput})
|
||||
template_name = 'core/pagerev_edit.jinja'
|
||||
|
||||
def get_object(self):
|
||||
self.page = Page.get_page_by_full_name(self.kwargs['page_name'])
|
||||
return self._get_revision()
|
||||
|
||||
def _get_revision(self):
|
||||
if self.page is not None:
|
||||
# First edit
|
||||
if self.page.revisions.all() is None:
|
||||
rev = PageRev(author=request.user)
|
||||
rev = PageRev(author=self.request.user)
|
||||
rev.save()
|
||||
self.page.revisions.add(rev)
|
||||
try:
|
||||
@ -170,7 +191,7 @@ class PageEditView(CanEditMixin, UpdateView):
|
||||
return None
|
||||
|
||||
def get_context_data(self, **kwargs):
|
||||
context = super(PageEditView, self).get_context_data(**kwargs)
|
||||
context = super(PageEditViewBase, self).get_context_data(**kwargs)
|
||||
if self.page is not None:
|
||||
context['page'] = self.page
|
||||
else:
|
||||
@ -186,10 +207,19 @@ class PageEditView(CanEditMixin, UpdateView):
|
||||
new_rev.author = self.request.user
|
||||
new_rev.page = self.page
|
||||
form.instance = new_rev
|
||||
return super(PageEditView, self).form_valid(form)
|
||||
return super(PageEditViewBase, self).form_valid(form)
|
||||
|
||||
|
||||
class PageDeleteView(CanEditPropMixin, DeleteView):
|
||||
class PageEditView(PageEditViewBase):
|
||||
|
||||
def dispatch(self, request, *args, **kwargs):
|
||||
res = super(PageEditView, self).dispatch(request, *args, **kwargs)
|
||||
if self.object.page.need_club_redirection:
|
||||
return redirect('club:club_edit_page', club_id=self.object.page.club.id)
|
||||
return res
|
||||
|
||||
|
||||
class PageDeleteView(CanEditPagePropMixin, DeleteView):
|
||||
model = Page
|
||||
template_name = 'core/delete_confirm.jinja'
|
||||
pk_url_kwarg = 'page_id'
|
||||
|
File diff suppressed because it is too large
Load Diff
17
migrate.py
17
migrate.py
@ -1375,6 +1375,20 @@ def migrate_mailings():
|
||||
MailingSubscription(mailing=mailing, email=to_unicode(mailing_sub['email'])).save()
|
||||
|
||||
|
||||
def migrate_club_again():
|
||||
cur = db.cursor(MySQLdb.cursors.SSDictCursor)
|
||||
cur.execute("SELECT * FROM asso")
|
||||
|
||||
print("Migrating club is_active")
|
||||
|
||||
for club in cur:
|
||||
try:
|
||||
c = Club.objects.get(unix_name=club['nom_unix_asso'])
|
||||
c.is_active = club['hidden'] == 0
|
||||
c.save()
|
||||
except: pass
|
||||
|
||||
|
||||
def main():
|
||||
print("Start at %s" % start)
|
||||
# Core
|
||||
@ -1396,7 +1410,8 @@ def main():
|
||||
# reset_sas_moderators()
|
||||
# migrate_forum()
|
||||
# reset_index('forum')
|
||||
migrate_mailings()
|
||||
# migrate_mailings()
|
||||
migrate_club_again()
|
||||
end = datetime.datetime.now()
|
||||
print("End at %s" % end)
|
||||
print("Running time: %s" % (end - start))
|
||||
|
@ -296,6 +296,9 @@ SITH_LAUNDERETTE_MANAGER = {
|
||||
'address': "6 Boulevard Anatole France, 90000 Belfort"
|
||||
}
|
||||
|
||||
# Main root for club pages
|
||||
SITH_CLUB_ROOT_PAGE = "clubs"
|
||||
|
||||
# Define the date in the year serving as reference for the subscriptions calendar
|
||||
# (month, day)
|
||||
SITH_START_DATE = (8, 15) # 15th August
|
||||
|
Loading…
Reference in New Issue
Block a user