diff --git a/README.md b/README.md index 1a3d575e..b6017577 100644 --- a/README.md +++ b/README.md @@ -177,7 +177,7 @@ Charger les mails indispensables au bon fonctionnement de GestioCOF : Une base de donnée pré-remplie est disponible en lançant les commandes : - python manage.py loaddata gestion sites accounts groups articles + python manage.py loaddata gestion sites articles python manage.py loaddevdata Vous êtes prêts à développer ! Lancer GestioCOF en faisant diff --git a/cof/settings/common.py b/cof/settings/common.py index 261760d6..f7c7bba6 100644 --- a/cof/settings/common.py +++ b/cof/settings/common.py @@ -56,6 +56,22 @@ INSTALLED_APPS = [ 'widget_tweaks', 'custommail', 'djconfig', + 'wagtail.wagtailforms', + 'wagtail.wagtailredirects', + 'wagtail.wagtailembeds', + 'wagtail.wagtailsites', + 'wagtail.wagtailusers', + 'wagtail.wagtailsnippets', + 'wagtail.wagtaildocs', + 'wagtail.wagtailimages', + 'wagtail.wagtailsearch', + 'wagtail.wagtailadmin', + 'wagtail.wagtailcore', + 'wagtail.contrib.modeladmin', + 'wagtailmenus', + 'modelcluster', + 'taggit', + 'kfet.cms', ] MIDDLEWARE_CLASSES = [ @@ -69,6 +85,8 @@ MIDDLEWARE_CLASSES = [ 'django.middleware.clickjacking.XFrameOptionsMiddleware', 'django.middleware.security.SecurityMiddleware', 'djconfig.middleware.DjConfigMiddleware', + 'wagtail.wagtailcore.middleware.SiteMiddleware', + 'wagtail.wagtailredirects.middleware.RedirectMiddleware', ] ROOT_URLCONF = 'cof.urls' @@ -87,6 +105,7 @@ TEMPLATES = [ 'django.core.context_processors.i18n', 'django.core.context_processors.media', 'django.core.context_processors.static', + 'wagtailmenus.context_processors.wagtailmenus', 'djconfig.context_processors.config', 'gestioncof.shared.context_processor', 'kfet.context_processors.auth', @@ -143,9 +162,12 @@ LOGIN_URL = "cof-login" LOGIN_REDIRECT_URL = "home" CAS_SERVER_URL = 'https://cas.eleves.ens.fr/' +CAS_VERSION = '3' +CAS_LOGIN_MSG = None CAS_IGNORE_REFERER = True CAS_REDIRECT_URL = '/' CAS_EMAIL_FORMAT = "%s@clipper.ens.fr" + AUTHENTICATION_BACKENDS = ( 'django.contrib.auth.backends.ModelBackend', 'gestioncof.shared.COFCASBackend', @@ -171,3 +193,9 @@ CHANNEL_LAYERS = { } FORMAT_MODULE_PATH = 'cof.locale' + +# Wagtail settings + +WAGTAIL_SITE_NAME = 'GestioCOF' +WAGTAIL_ENABLE_UPDATE_CHECK = False +TAGGIT_CASE_INSENSITIVE = True diff --git a/cof/settings/dev.py b/cof/settings/dev.py index a3a17f99..ffd34c7d 100644 --- a/cof/settings/dev.py +++ b/cof/settings/dev.py @@ -28,6 +28,26 @@ MEDIA_URL = '/media/' # Debug tool bar # --- +# "Versions" panel of django-debug-toolbar <=1.8 is not compatible with +# wagtailmenus. +# See https://github.com/jazzband/django-debug-toolbar/issues/922 +# TODO: Bug should be fixed in ddt 1.9 (not released yet). When fixed, this +# declaration may be removed. +DEBUG_TOOLBAR_PANELS = [ + 'debug_toolbar.panels.timer.TimerPanel', + 'debug_toolbar.panels.settings.SettingsPanel', + 'debug_toolbar.panels.headers.HeadersPanel', + 'debug_toolbar.panels.request.RequestPanel', + 'debug_toolbar.panels.sql.SQLPanel', + 'debug_toolbar.panels.staticfiles.StaticFilesPanel', + 'debug_toolbar.panels.templates.TemplatesPanel', + 'debug_toolbar.panels.cache.CachePanel', + 'debug_toolbar.panels.signals.SignalsPanel', + 'debug_toolbar.panels.logging.LoggingPanel', + 'debug_toolbar.panels.redirects.RedirectsPanel', +] + + def show_toolbar(request): """ On ne veut pas la vérification de INTERNAL_IPS faite par la debug-toolbar diff --git a/cof/urls.py b/cof/urls.py index 06b1087a..886070e9 100644 --- a/cof/urls.py +++ b/cof/urls.py @@ -14,6 +14,10 @@ from django.views.generic.base import TemplateView from django.contrib.auth import views as django_views from django_cas_ng import views as django_cas_views +from wagtail.wagtailadmin import urls as wagtailadmin_urls +from wagtail.wagtailcore import urls as wagtail_urls +from wagtail.wagtaildocs import urls as wagtaildocs_urls + from gestioncof import views as gestioncof_views, csv_views from gestioncof.urls import export_patterns, petitcours_patterns, \ surveys_patterns, events_patterns, calendar_patterns, \ @@ -48,7 +52,7 @@ urlpatterns = [ url(r'^outsider/login$', gestioncof_views.login_ext), url(r'^outsider/logout$', django_views.logout, {'next_page': 'home'}), url(r'^login$', gestioncof_views.login, name="cof-login"), - url(r'^logout$', gestioncof_views.logout), + url(r'^logout$', gestioncof_views.logout, name="cof-logout"), # Infos persos url(r'^profile$', gestioncof_views.profile), url(r'^outsider/password-change$', django_views.password_change), @@ -82,6 +86,8 @@ urlpatterns = [ url(r'^utile_cof/diff_cof$', gestioncof_views.liste_diffcof), url(r'^utile_bda/bda_revente$', gestioncof_views.liste_bdarevente), url(r'^k-fet/', include('kfet.urls')), + url(r'^cms/', include(wagtailadmin_urls)), + url(r'^documents/', include(wagtaildocs_urls)), ] if 'debug_toolbar' in settings.INSTALLED_APPS: @@ -90,7 +96,13 @@ if 'debug_toolbar' in settings.INSTALLED_APPS: url(r'^__debug__/', include(debug_toolbar.urls)), ] +if settings.DEBUG: # Si on est en production, MEDIA_ROOT est servi par Apache. # Il faut dire à Django de servir MEDIA_ROOT lui-même en développement. urlpatterns += static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT) + +# Wagtail for uncatched +urlpatterns += [ + url(r'', include(wagtail_urls)), +] diff --git a/gestioncof/__init__.py b/gestioncof/__init__.py index e69de29b..b77fdb94 100644 --- a/gestioncof/__init__.py +++ b/gestioncof/__init__.py @@ -0,0 +1 @@ +default_app_config = 'gestioncof.apps.GestioncofConfig' diff --git a/gestioncof/apps.py b/gestioncof/apps.py new file mode 100644 index 00000000..6e24b050 --- /dev/null +++ b/gestioncof/apps.py @@ -0,0 +1,8 @@ +from django.apps import AppConfig + + +class GestioncofConfig(AppConfig): + name = 'gestioncof' + + def ready(self): + import gestioncof.signals diff --git a/gestioncof/shared.py b/gestioncof/shared.py index e4180b49..fabcacb9 100644 --- a/gestioncof/shared.py +++ b/gestioncof/shared.py @@ -1,62 +1,26 @@ -from django.contrib.sites.models import Site from django.conf import settings +from django.contrib.sites.models import Site + from django_cas_ng.backends import CASBackend -from django_cas_ng.utils import get_cas_client -from django.contrib.auth import get_user_model from gestioncof.models import CofProfile -User = get_user_model() - class COFCASBackend(CASBackend): - def authenticate_cas(self, ticket, service, request): - """Verifies CAS ticket and gets or creates User object""" - - client = get_cas_client(service_url=service) - username, attributes, _ = client.verify_ticket(ticket) - if attributes: - request.session['attributes'] = attributes - if not username: - return None + def clean_username(self, username): # Le CAS de l'ENS accepte les logins avec des espaces au début # et à la fin, ainsi qu’avec une casse variable. On normalise pour # éviter les doublons. - username = username.strip().lower() + return username.strip().lower() - profiles = CofProfile.objects.filter(login_clipper=username) - if len(profiles) > 0: - profile = profiles.order_by('-is_cof')[0] - user = profile.user - return user - try: - user = User.objects.get(username=username) - except User.DoesNotExist: - # user will have an "unusable" password - user = User.objects.create_user(username, '') - user.save() - return user - - def authenticate(self, ticket, service, request): - """Authenticates CAS ticket and retrieves user data""" - user = self.authenticate_cas(ticket, service, request) - if user is None: - return user - try: - profile = user.profile - except CofProfile.DoesNotExist: - profile, created = CofProfile.objects.get_or_create(user=user) - profile.save() - if not profile.login_clipper: - profile.login_clipper = user.username - profile.save() - if not user.email: - user.email = settings.CAS_EMAIL_FORMAT % profile.login_clipper - user.save() - if profile.is_buro and not user.is_staff: - user.is_staff = True - user.save() + def configure_user(self, user): + # cannot use "defaults" arg + profile, _ = CofProfile.objects.get_or_create(user=user) + profile.login_clipper = user.username + profile.save() + user.email = settings.CAS_EMAIL_FORMAT % profile.login_clipper + user.save() return user diff --git a/gestioncof/signals.py b/gestioncof/signals.py new file mode 100644 index 00000000..11cb55fc --- /dev/null +++ b/gestioncof/signals.py @@ -0,0 +1,23 @@ +from django.contrib import messages +from django.contrib.auth.signals import user_logged_in +from django.dispatch import receiver +from django.utils.translation import ugettext_lazy as _ + +from django_cas_ng.signals import cas_user_authenticated + + +@receiver(user_logged_in) +def messages_on_out_login(request, user, **kwargs): + if user.backend.startswith('django.contrib.auth'): + msg = _('Connexion à GestioCOF réussie. Bienvenue {}.').format( + user.get_short_name(), + ) + messages.success(request, msg) + + +@receiver(cas_user_authenticated) +def mesagges_on_cas_login(request, user, **kwargs): + msg = _('Connexion à GestioCOF par CAS réussie. Bienvenue {}.').format( + user.get_short_name(), + ) + messages.success(request, msg) diff --git a/gestioncof/templates/home.html b/gestioncof/templates/home.html index 5f783a48..acc04f30 100644 --- a/gestioncof/templates/home.html +++ b/gestioncof/templates/home.html @@ -1,4 +1,5 @@ {% extends "gestioncof/base_header.html" %} +{% load wagtailcore_tags %} {% block homelink %} {% endblock %} @@ -55,7 +56,8 @@
\n Eh bien la K-F\u00eat, c'est le bar des \u00e9l\u00e8ves de l'\u00c9cole normale\n sup\u00e9rieure. Elle est situ\u00e9e dans les locaux de l'\u00c9cole, au pied de\n l'escalier C (plan). On y trouve \u00e0 boire, bien s\u00fbr,\n des bi\u00e8res en nombre pl\u00e9thorique mais aussi caf\u00e9s, th\u00e9s, softs et de quoi\n grignoter. Ah oui un point important, on ne va pas \u00e0 la K-F\u00eat, on va EN K-F\u00eat.\n
\n\n\n Que nenni, \u00f4 jeune et innocent conscrit-e ! La K-F\u00eat n'est pas un bouge\n sordide o\u00f9 des piliers de bar passent leurs journ\u00e9es \u00e0 picoler. Enfin pas\n uniquement. C'est aussi un lieu de divertissement avec\n son flipper (la mythique, la seule, l'unique,\n la g\u00e9niale Amazon Hunt), son baby-foot et le lieu d'\u00e9lection des \nbridgeur-se-s, du club jeux, des joueur-se-s de poker voire des quelques\n irr\u00e9ductibles du boulot qui y viennent bosser en profitant du point \nd'acc\u00e8s wifi. \n
\n\n\n L'\u00e9quipe d'\u00e9l\u00e8ves motiv\u00e9-e-s qui s'occupent de la K-F\u00eat s'appelle, en toute logique, l'\u00e9quipe K-F\u00eat.\n Elle est men\u00e9e par un-e leader charismatique et bien-aim\u00e9-e, \naccompagn\u00e9-e de ses troupes de fid\u00e8les, les K-F\u00eat wo-men, boys et girls.\n Le local de la K-F\u00eat n'est ouvert que si un-e K-F\u00eat wo-man est \npr\u00e9sente. \u00c0 savoir la plupart du temps entre 12h et 3h du matin.\n
\n\n\n Oui et non. Nous ne sommes pas ta grand-m\u00e8re et nous n'allons\n certainement pas t'emp\u00eacher de faire la f\u00eate, ni de d\u00e9guster des pintes\n jusqu'au petit p\u00f4t. Par contre nous attendons de toi que tu ne sois pas\n un-e gros-se con-ne. A priori pas de raison de le croire, mais jette tout de m\u00eame\n un \u0153il sur le mode d'emploi de la K-F\u00eat, \u00e7a\n pourrait t'\u00e9viter de perdre un genoux ou deux...\n
\n\n\n Bien s\u00fbr\u00a0! Pour cela commence par lire ce petit\n guide histoire de savoir dans quoi tu t'engages puis contacte ton-ta chef-fe K-F\u00eat ador\u00e9-e pour v\u00e9rifier que la date de ta\n soir\u00e9e n'est pas d\u00e9j\u00e0 prise par une autre f\u00eate et obtenir son\n accord.\n
\n\n\n Commence d\u00e9j\u00e0 par jeter un oeil sur le mode\n d'emploi de la K-F\u00eat. Si la r\u00e9ponse \u00e0 tes interrogations ne s'y\n trouve pas, rien n'est perdu. En effet le service informatique de \nl'\u00c9cole, dans sa grande mansu\u00e9tude, a mis \u00e0 disposition de l'\u00e9quipe \nK-F\u00eat une adresse e-mail, k-fet@ens.fr. Mais sinon, passe en K-F\u00eat, il y aura sans doute un K-F\u00eat wo-man qui saura r\u00e9pondre \u00e0 ta question.\n
" + }, + "pk": 3 +}, +{ + "model": "kfetcms.kfetpage", + "fields": { + "custom_template": "", + "no_header": false, + "content": "Article 0 : La K-F\u00eat n'existe pas.
La K-F\u00eat n'a rien de magique, il n'y a pas de petits d\u00e9mons qui font le m\u00e9nage, pas plus que d'arbustes g\u00e9n\u00e9tiquement modifi\u00e9s aux OGM sur lesquels poussent les bouteilles de bi\u00e8res. La K-F\u00eat c'est avant tout une \u00e9quipe qui sacrifie une partie de son temps libre pour que tout se passe pour le mieux.
D\u00e9j\u00e0 ne pas poser de probl\u00e8mes, c'est \u00e0 dire ne pas r\u00e9veiller tout l'internat en sortant, essayer de ne pas finir dans un \u00e9tat trop avanc\u00e9 d'alcoolisation, etc... Mine de rien \u00e7a nous \u00e9viterait quelques probl\u00e8mes.
Ensuite, comme tu le sais s\u00fbrement les bi\u00e8res sont consign\u00e9es, il est donc pr\u00e9f\u00e9rable pour nous que tu n'embarques pas les bouteilles en souvenir dans ta thurne. Mieux, tu peux nous faire gagner du temps de rangement en les ramenant au bar en partant. Et encore mieux, tu peux jeter tes d\u00e9chets (gobelets, boite de pringles, etc...). Si tu fais d\u00e9j\u00e0 tout \u00e7a tu nous simplifieras grandement la vie.
En bon \u00e9tat souverain et ind\u00e9pendant, la K-F\u00eat a sa propre monnaie : l'unit\u00e9 K-F\u00eat (UKF). Elle vaut 10 centimes d'euro. La K-F\u00eat ne battant pas monnaie, les UKF que tu poss\u00e8des sont not\u00e9es sur ton compte, identifi\u00e9 par un trigramme (une suite de trois caract\u00e8res) et que tu peux recharger en liquide ou par ch\u00e8que. Note que si tu y tiens vraiment, tu peux payer en liquide, mais poss\u00e9der un compte est bien plus pratique.
Pour commander \u00e0 boire ou \u00e0 manger, il suffit de demander \u00e0 un membre de l'\u00e9quipe K-F\u00eat. Et \u00e7a marche encore mieux si la demande est effectu\u00e9e avec le sourire au d\u00e9but et un merci \u00e0 la fin : l'\u00e9quipe est constitu\u00e9e de volontaires b\u00e9n\u00e9voles, et mieux vaut ne pas les prendre pour des chiens. EN AUCUN CAS on ne passe derri\u00e8re le bar si on n'est pas membre de l'\u00e9quipe K-F\u00eat.
Non ! Imagine-toi les jours de soir\u00e9es, la K-F\u00eat remplie et tout le monde qui fume... On finirait tous avec des poumons aussi crades que le sol de la K-F\u00eat. Ce serait quand m\u00eame dommage pour la recherche fran\u00e7aise qu'on cr\u00e8ve tous avant 30 ans, non ?
Par contre tu peux fumer dehors, il y a m\u00eame des cendriers juste pour toi, par contre tu remarqueras que les chambres de l'internat se trouvent juste au dessus de toi. T\u00e2che donc de ne pas faire trop de bruit.
D\u00e9j\u00e0 c'est apporter, enfin en tout cas avant de la boire. Ensuite la K-F\u00eat est un lieu de convivialit\u00e9 o\u00f9 les bi\u00e8res te sont vendues au prix co\u00fbtant,\n franchement ce serait pas fair-play de te la jouer solo. Alors \u00e9videment il y a des exceptions, par exemple si tu reviens de Belgique et que tu veux faire go\u00fbter de la Wesvleteren \u00e0 tes amis de l'\u00e9quipe K-F\u00eat, ou si tu veux organiser une d\u00e9gustation de vins avec la charcuterie qui va bien. Tu comprendras qu'un pack de Kro c'est quand m\u00eame pas la m\u00eame classe...
Bien s\u00fbr, nous sommes tr\u00e8s loin de penser tout conna\u00eetre en mati\u00e8re de musique. Mais comme nous sommes entre gens civilis\u00e9s, et que je te rappelle que tu n'as pas le droit de passer derri\u00e8re le bar, il convient de demander \u00e0 un-e membre de l'\u00e9quipe K-F\u00eat afin qu'ille t'indique qui est \u00e0 l'origine de ces chansons que tu n'appr\u00e9cies apparemment pas. Apr\u00e8s avoir obtenu son accord tu peux demander \u00e0 quelqu'un de mettre ta playlist, qui peut-\u00eatre sur un lecteur mp3, sur Deezer ou juste sur l'ordi, mais dans ce dernier cas ce sera plus dur puisque tu n'y aura pas acc\u00e8s directement.
Le plus simple pour toi (et pour nous) est donc de pr\u00e9voir des playlists sur Deezer d'avance et de nous les proposer. Par contre, sois gentil-le, n'insiste pas si nous ne voulons pas de ta musique traditionnelle hongroise. Par ailleurs, si un trop grand nombre de personnes nous demande de passer de la musique, l'\u00e9quipe K-F\u00eat peut ne pas acc\u00e9der \u00e0 ta requ\u00eate.
Tout membre du COF peut organiser une soir\u00e9e en K-F\u00eat \u00e0 la condition qu'elle soit publique et annonc\u00e9e une semaine \u00e0 l'avance par des affiches dans l'\u00e9cole et un mot dans le BOcal. Il faut bien sur aussi l'accord du COF qui s'occupe de voir si \u00e7a ne pose pas de probl\u00e8me \u00e0 l'admin, celui de la K-F\u00eat team pour qu'il y ait des K-F\u00eat wo-men pour servir et s\u00fbrement du BOUM pour qu'il s'occupe de la musique. Nous t'avons tout r\u00e9sum\u00e9 ici ; merci qui ? Une fois que tu as accompli ces formalit\u00e9s, il ne te reste plus qu'\u00e0 imprimer et coller des affiches pour que ta soir\u00e9e soit un succ\u00e8s !
Des tonnes, en voici quelques unes :
Les K-F\u00eat boys and girls font de main d'\u0153uvre bon march\u00e9 pour la \nK-F\u00eat, illes peuvent passer derri\u00e8re le bar, prendre vos commandes et \nrecharger votre compte si par malheur il est \u00e0 sec. La liste de \ncelleux-ci est trop longue pour tou-te-s les citer, pour les reconna\u00eetre\n regarde les gens qui passent derri\u00e8re le bar tout en conservant leur \nint\u00e9grit\u00e9 physique.
\n\nGrande question que tout le monde se pose un jour ou l'autre. Pour \nacc\u00e9der au titre prestigieux de K-F\u00eat boy-girl, il est n\u00e9cessaire mais \npas suffisant d'\u00eatre assid\u00fbment pr\u00e9sent-e en K-F\u00eat, et d'\u00eatre pr\u00eat-e \u00e0 \ntrimer pour elle. Si tu es souvent en K-F\u00eat, que tu es sympathique et \nmotiv\u00e9-e, et surtout en fin de compte si le-la chef-fe le veut bien, tu \npourras devenir K-F\u00eat boy-girl et passer derri\u00e8re le bar pour servir. \nEnsuite, si tu es motiv\u00e9-e et efficace, ou simplement si t'es un-e pote \ndu-de la chef-fe et qu'ille n'a aucun scrupule, tu pourras devenir K-F\u00eat\n wo-man et avoir la cl\u00e9.
\n\nEt comme la K-F\u00eat c'est avant tout beaucoup d'emmerdes on a pas envie\n de te forcer la main, on veut que cela vienne de toi. Donc si tu te \nsens pr\u00eat-e \u00e0 participer \u00e0 la vie mouvement\u00e9e de la K-F\u00eat fais-en part \nau-\u00e0 la chef-fe. Ille ne va pas te manger.
" + }, + "pk": 5 +}, +{ + "model": "kfetcms.kfetpage", + "fields": { + "custom_template": "kfetcms/carte.html", + "no_header": false, + "content": "\n\tLe service de la bi\u00e8re est, historiquement, la mission et le sacerdoce \ndu K-F\u00eat people. Ille y est d\u00e9vou\u00e9-e corps et \u00e2me, et accomplit sa t\u00e2che\n avec ardeur et passion. Voyons comment se d\u00e9clinent les occasions \nd'approcher du nirvana brassicole. Les prix donn\u00e9s sont en UKF. Si tu \nn'as pas compris, va voir par ici.
" + }, + "pk": 6 +}, +{ + "model": "kfetcms.kfetpage", + "fields": { + "custom_template": "", + "no_header": false, + "content": "\n Tu veux organiser une soir\u00e9e en K-F\u00eat ? Pas de probl\u00e8me !\n
\n\n\n Tu peux organiser une soir\u00e9e le jour que tu souhaites, \u00e0 condition que la\n date ne soit pas d\u00e9j\u00e0 prise par quelqu'un d'autre. Sache par contre que la\n K-F\u00eat ne te sera pas enti\u00e8rement d\u00e9di\u00e9e et que les utilisateur-rice-s habituel-le-s\n continueront de la fr\u00e9quenter (et risquent fortement de squatter ta\n soir\u00e9e). Donc si tu veux un peu d'intimit\u00e9 les soir\u00e9es du week-end sont plus\n conseill\u00e9es (mais l'\u00e9quipe risque de ne pas \u00eatre pr\u00e9sente), mais aussi\n plus pris\u00e9es, d\u00e9p\u00eache-toi de r\u00e9server la tienne.\n
\n\n\n D\u00e9j\u00e0 pr\u00e9venir poliment l'\u00e9quipe K-F\u00eat, et\n surtout le-la chef-fe pour v\u00e9rifier que la date est encore libre, et qu'il y\n aura au moins quelqu'un pour t'ouvrir la K-F\u00eat. Ensuite, si ta soir\u00e9e\n n'est pas une simple bouffe qui finit avant minuit il faut pr\u00e9venir les\n vigiles via l'administration au moyen d'une demande d'autorisation de\n soir\u00e9e qui se trouve sur la section du p\u00f4le Pr\u00e9vention et S\u00e9curit\u00e9 sur l'intranet : demande d'autorisation de soir\u00e9e.\n \u00c0 faire au moins une semaine avant ta soir\u00e9e.\n
\n\n Si en plus tu as besoin que le BOUM s'occupe de la musique et/ou PLS des\n lumi\u00e8res c'est elleux qu'il faut contacter. Histoire de t'\u00e9viter\n d'avoir \u00e0 chercher voici leur adresse\u00a0: boum (at) ens (point) fr\n et pls (at) ens (point) fr.\n
\n\n\n D\u00e9j\u00e0 le m\u00e9nage, oui je sais c'est chiant mais c'est le prix \u00e0 payer pour\n profiter du local. Demande \u00e0 ce qu'un-e K-F\u00eat wo-man t'ouvre et tu devrais avoir\n \u00e0 ta disposition tout ce qu'il faut pour faire briller la K-F\u00eat (ou au moins on essaiera de\n trouver ce qu'il faut). Fais par\n contre attention aux bouteilles de bi\u00e8re qui sont consign\u00e9es, s'il n'y a\n personne pour les ranger contente-toi de les mettre sur le bar, quelqu'un\n s'en chargera plus tard. Les meubles peuvent \u00eatre d\u00e9plac\u00e9s dans une salle\n voisine si tu le souhaites, il faudra juste penser \u00e0 les remettre en place.\n
\n\n Ensuite dans l'id\u00e9al tu connais tous tes potes, donc en donner une liste \u00e0\n la loge permet d'\u00e9viter quelques probl\u00e8mes et quelques aller-retours.\n Au-del\u00e0 de 21h, les ext\u00e9rieur-e-s ne peuvent rentrer qu'avec un-e Ulmien-ne ayant sa carte\n sur lui-elle.\n
\n\n\n Si le BOUM est pr\u00e9sent, faut voir avec elleux : boum (at) ens (point) fr
\n Sinon, pr\u00e9pare ta musique sur un lecteur mp3 ou une playlist\n Deezer. Lors de la soir\u00e9e,\n demande \u00e0 un-e K-F\u00eat wo-man de passer ce que tu as pr\u00e9par\u00e9.\n
\n Tu peux apporter toute la nourriture que tu souhaites\u00a0; pr\u00e9vois assez\n large, il y a beaucoup de K-F\u00eat people \u00e0 nourrir. Pour ce qui est de la\n boisson, il faut te limiter aux boissons de cat\u00e9gorie 2, c'est \u00e0 dire\n bi\u00e8res, vins et boissons \u00e0 base de vin, champagne et bien s\u00fbr les boissons sans alcool.\n
\n\n\n Ce soir c'est ton soir, il est donc bien s\u00fbr \u00e9vident que tu dois\n rester pr\u00e9sent-e et joignable du d\u00e9but \u00e0 la fin de la soir\u00e9e. Id\u00e9alement ce\n doit aussi \u00eatre le cas de tes \"Responsables ordre et discipline\". Vous ne serez pas\n trop de deux ou trois pour r\u00e9gler les probl\u00e8mes qui pourraient survenir,\n tes potes bourr\u00e9-e-s, tes potes qui fument, tes potes qui font du bordel dans la cage d'escalier,\n etc... Tous les probl\u00e8mes qui pourraient survenir te seront imput\u00e9s donc\n pr\u00e9viens-les, c'est tes potes apr\u00e8s tout, non ?\n
\n\n\n Eh non, pas encore, apr\u00e8s (ou le lendemain de) ta soir\u00e9e il te faudra encore ranger,\n faire le m\u00e9nage et passer un coup de javel. Oui encore, mais bon, pense \u00e0 toutes les fois o\u00f9\n c'est nous qui le faisons pour le bien de tou-te-s. Une fois n'est pas\n coutume demande \u00e0 un-e K-F\u00eat wo-man de t'ouvrir et de te fournir tout le\n mat\u00e9riel dont tu pourrais avoir besoin, et l\u00e0 o\u00f9 c'est vraiment classe\n c'est que tu peux m\u00eame faire \u00e7a en musique si tu le souhaites. N'oublie\n pas non plus de rapporter les meubles que tu pourrais avoir sortis et que\n les poubelles ne disparaissent pas toutes seules.\n
\n\n\n Ouais, la K-F\u00eat c'est pas chez m\u00e9m\u00e9, alors c'est peut-\u00eatre ta soir\u00e9e mais\n si un-e membre de l'\u00e9quipe K-F\u00eat te dit quelque\n chose (de baisser le son, de virer telle ou telle personne...) tu acceptes avec le sourire.\n En particulier tu ne passes pas derri\u00e8re le bar.\n
\n\n\n Organiser ta soir\u00e9e c'est facile :\n
\n\n Voila, facile, non ?\n
" + }, + "pk": 7 +}, +{ + "model": "kfetcms.kfetpage", + "fields": { + "custom_template": "", + "no_header": false, + "content": "Et le baby-foot
\n\n\n\t
\n\t\n
\n\n\n\n\n\n\nCette machine n'est plus. Mais elle reste dans le coeur de ceux qui \nl'ont connue. C'est pourquoi cette section n'a pas \u00e9t\u00e9 retir\u00e9e.
" + }, + "pk": 8 +}, +{ + "model": "kfetcms.kfetpage", + "fields": { + "custom_template": "", + "no_header": false, + "content": "Les ancien-ne-s Chef-fe-s K-F\u00eat doivent bien \u00eatre pr\u00e9sent\u00e9-e-s avant \nl'\u00e9quipe actuelle. C'est gr\u00e2ce \u00e0 elleux qu'elle tourne encore, gr\u00e2ce \u00e0 \nelleux qu'elle a bien tourn\u00e9, et puis, de pr\u00e8s comme de loin, illes \nveillent encore sur nous. Ce sont les diff\u00e9rentes facettes de la K-F\u00eat \nhistorique, bien que d'un certain point de vue, illes se ressemblent \ntou-te-s : les Chef-fe-s K-F\u00eat sont une dynastie, ils n'ont pas \u00e9t\u00e9 \nChef-fe-s apr\u00e8s avoir prouv\u00e9 quoi que ce soit, illes l'ont \u00e9t\u00e9 parce que\n ce r\u00f4le leur revenait de droit. On na\u00eet Chef-fe K-F\u00eat, on ne le devient\n pas. Et on le reste toujours, dans l'\u00e2me.
", + "sort_order": 0, + "page": 5, + "title": "Les ancien-ne-s Chef-fe-s K-F\u00eat", + "group": 3, + "show_only": 12 + }, + "pk": 1 +}, +{ + "model": "kfetcms.kfetpagegroupteam", + "fields": { + "content": "Le-la chef-fe K-F\u00eat, celui-celle qui a le droit de vie et de mort sur les \u00e2mes \u00e9gar\u00e9es qui fr\u00e9quentent la K-F\u00eat.
", + "sort_order": 1, + "page": 5, + "title": "Le chef", + "group": 1, + "show_only": null + }, + "pk": 2 +}, +{ + "model": "kfetcms.kfetpagegroupteam", + "fields": { + "content": "Les K-F\u00eat wo-men poss\u00e8dent les cl\u00e9s de la K-F\u00eat. Ce sont elleux qui peuvent d\u00e9cider ou non d'ouvrir la K-F\u00eat.
", + "sort_order": 2, + "page": 5, + "title": "Les K-F\u00eat Wo-Men", + "group": 2, + "show_only": null + }, + "pk": 3 +}, +{ + "model": "kfetcms.kfetpagegroupteam", + "fields": { + "content": "Les vieux-illes sont d'ancien-ne-s K-F\u00eat wo-men qui ne viennent plus \naussi souvent qu'avant, illes servent toujours, mais n'ont en g\u00e9n\u00e9ral \nplus les cl\u00e9s. Illes existent n\u00e9anmoins, et on les garde (pour \ncertain-e-s) parce qu'au fond, on les aime quand m\u00eame, et qu'en plus, \nilles en savent plus que n'importe qui sur la K-F\u00eat.
", + "sort_order": 3, + "page": 5, + "title": "Les Vieux-illes", + "group": 4, + "show_only": 12 + }, + "pk": 4 +}, +{ + "model": "kfetcms.groupteam", + "fields": { + "name": "Chef-fe-s" + }, + "pk": 1 +}, +{ + "model": "kfetcms.groupteam", + "fields": { + "name": "Wo-Men" + }, + "pk": 2 +}, +{ + "model": "kfetcms.groupteam", + "fields": { + "name": "Ancien-ne-s chef-fe-s" + }, + "pk": 3 +}, +{ + "model": "kfetcms.groupteam", + "fields": { + "name": "Ancien-ne-s wo-men" + }, + "pk": 4 +}, +{ + "pk": 1, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 0, + "first_name": "Hugo", + "group": 1, + "nick_name": "", + "photo": 3, + "last_name": "Manet" + } +}, +{ + "pk": 2, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 1, + "first_name": "Lisa", + "group": 1, + "nick_name": "", + "photo": 4, + "last_name": "Gourdon" + } +}, +{ + "pk": 3, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 0, + "first_name": "Pierre", + "group": 2, + "nick_name": "", + "photo": 5, + "last_name": "Quesselaire" + } +}, +{ + "pk": 4, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 1, + "first_name": "Thibault", + "group": 2, + "nick_name": "", + "photo": 6, + "last_name": "Scoquard" + } +}, +{ + "pk": 5, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 2, + "first_name": "Arnaud", + "group": 2, + "nick_name": "", + "photo": 7, + "last_name": "Fanthomme" + } +}, +{ + "pk": 6, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 3, + "first_name": "Vincent", + "group": 2, + "nick_name": "", + "photo": 8, + "last_name": "Balerdi" + } +}, +{ + "pk": 7, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 4, + "first_name": "Nathana\u00ebl", + "group": 2, + "nick_name": "", + "photo": 9, + "last_name": "Willaime" + } +}, +{ + "pk": 8, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 5, + "first_name": "\u00c9lisabeth", + "group": 2, + "nick_name": "", + "photo": 10, + "last_name": "Miller" + } +}, +{ + "pk": 9, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 6, + "first_name": "Arthur", + "group": 2, + "nick_name": "B2O", + "photo": 11, + "last_name": "Lesage" + } +}, +{ + "pk": 10, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 7, + "first_name": "Sarah", + "group": 2, + "nick_name": "", + "photo": 12, + "last_name": "Asset" + } +}, +{ + "pk": 11, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 8, + "first_name": "Alexandre", + "group": 2, + "nick_name": "", + "photo": 13, + "last_name": "Legrand" + } +}, +{ + "pk": 12, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 9, + "first_name": "\u00c9tienne", + "group": 2, + "nick_name": "", + "photo": 14, + "last_name": "Baudel" + } +}, +{ + "pk": 13, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 0, + "first_name": "Marine", + "group": 3, + "nick_name": "", + "photo": 15, + "last_name": "Snape" + } +}, +{ + "pk": 14, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 1, + "first_name": "Anatole", + "group": 3, + "nick_name": "", + "photo": 16, + "last_name": "Gosset" + } +}, +{ + "pk": 15, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 2, + "first_name": "Jacko", + "group": 3, + "nick_name": "", + "photo": 17, + "last_name": "Rastikian" + } +}, +{ + "pk": 16, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 3, + "first_name": "Alexandre", + "group": 3, + "nick_name": "", + "photo": 18, + "last_name": "Jannaud" + } +}, +{ + "pk": 17, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 4, + "first_name": "Aur\u00e9lien", + "group": 3, + "nick_name": "", + "photo": 19, + "last_name": "Delobelle" + } +}, +{ + "pk": 18, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 5, + "first_name": "Sylvain", + "group": 3, + "nick_name": "", + "photo": 20, + "last_name": "Douteau" + } +}, +{ + "pk": 19, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 6, + "first_name": "Rapha\u00ebl", + "group": 3, + "nick_name": "", + "photo": 21, + "last_name": "Lescanne" + } +}, +{ + "pk": 20, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 7, + "first_name": "Romain", + "group": 3, + "nick_name": "", + "photo": 22, + "last_name": "Gourvil" + } +}, +{ + "pk": 21, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 8, + "first_name": "Marie", + "group": 3, + "nick_name": "", + "photo": 23, + "last_name": "Labeye" + } +}, +{ + "pk": 22, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 9, + "first_name": "Oscar", + "group": 3, + "nick_name": "", + "photo": 24, + "last_name": "Blumberg" + } +}, +{ + "pk": 23, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 10, + "first_name": "Za\u00efd", + "group": 3, + "nick_name": "", + "photo": 25, + "last_name": "Allybokus" + } +}, +{ + "pk": 24, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 11, + "first_name": "Damien", + "group": 3, + "nick_name": "", + "photo": 26, + "last_name": "Garreau" + } +}, +{ + "pk": 25, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 12, + "first_name": "Andr\u00e9a", + "group": 3, + "nick_name": "", + "photo": 27, + "last_name": "Londonez-Lopez" + } +}, +{ + "pk": 26, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 13, + "first_name": "Tristan", + "group": 3, + "nick_name": "", + "photo": 28, + "last_name": "Roussel" + } +}, +{ + "pk": 27, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 14, + "first_name": "Guillaume", + "group": 3, + "nick_name": "", + "photo": 29, + "last_name": "Vernade" + } +}, +{ + "pk": 28, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 15, + "first_name": "Lucas", + "group": 3, + "nick_name": "", + "photo": 30, + "last_name": "Mercier" + } +}, +{ + "pk": 29, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 16, + "first_name": "Fran\u00e7ois", + "group": 3, + "nick_name": "M\u00e9talleux", + "photo": 31, + "last_name": "Maillot" + } +}, +{ + "pk": 30, + "model": "kfetcms.memberteam", + "fields": { + "sort_order": 17, + "first_name": "Fabrice", + "group": 3, + "nick_name": "", + "photo": 32, + "last_name": "Catoire" + } +}, +{ + "model": "wagtaildocs.document", + "pk": 1, + "fields": { + "created_at": "2017-05-30T04:20:00.000Z", + "uploaded_by_user": [ + "root" + ], + "collection": 1, + "title": "K-F\u00eat - Plan d'acc\u00e8s", + "file": "documents/kfet_acces.pdf" + } +}, +{ + "model": "wagtaildocs.document", + "pk": 2, + "fields": { + "created_at": "2017-05-30T04:20:00.000Z", + "uploaded_by_user": [ + "root" + ], + "collection": 1, + "title": "K-F\u00eat - Demande d'autorisation", + "file": "documents/kfet_autorisation.pdf" + } +}, +{ + "model": "wagtaildocs.document", + "pk": 3, + "fields": { + "created_at": "2017-05-30T04:20:00.000Z", + "uploaded_by_user": [ + "root" + ], + "collection": 1, + "title": "K-F\u00eat - Trait\u00e9 de Flipper Th\u00e9orique", + "file": "documents/kfet_flipper.pdf" + } +}, +{ + "model": "wagtailimages.image", + "pk": 1, + "fields": { + "created_at": "2017-05-30T04:20:00.000Z", + "focal_point_width": null, + "height": 300, + "file": "original_images/kfet_amazon.jpg", + "collection": 1, + "focal_point_x": null, + "file_size": null, + "focal_point_height": null, + "focal_point_y": null, + "title": "K-F\u00eat - Amazon Hunt", + "width": 200, + "uploaded_by_user": [ + "root" + ] + } +}, +{ + "model": "wagtailimages.image", + "pk": 2, + "fields": { + "created_at": "2017-05-30T04:20:00.000Z", + "focal_point_width": null, + "height": 300, + "file": "original_images/kfet_funmachine.jpg", + "collection": 1, + "focal_point_x": null, + "file_size": null, + "focal_point_height": null, + "focal_point_y": null, + "title": "K-F\u00eat - Fun Machine", + "width": 200, + "uploaded_by_user": [ + "root" + ] + } +}, +{ + "fields": { + "width": 3020, + "file_size": null, + "file": "original_images/hugo_manet.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 3020, + "focal_point_width": null, + "focal_point_y": null, + "title": "Hugo Manet", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 3 +}, +{ + "fields": { + "width": 1566, + "file_size": null, + "file": "original_images/lisa_gourdon.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 1634, + "focal_point_width": null, + "focal_point_y": null, + "title": "Lisa Gourdon", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 4 +}, +{ + "fields": { + "width": 117, + "file_size": null, + "file": "original_images/pierre_quesselaire.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 153, + "focal_point_width": null, + "focal_point_y": null, + "title": "Pierre Quesselaire", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 5 +}, +{ + "fields": { + "width": 606, + "file_size": null, + "file": "original_images/thibault_scoquart.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 487, + "focal_point_width": null, + "focal_point_y": null, + "title": "Thibault Scoquard", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 6 +}, +{ + "fields": { + "width": 640, + "file_size": null, + "file": "original_images/arnaud_fanthomme.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 320, + "focal_point_width": null, + "focal_point_y": null, + "title": "Arnaud Fanthomme", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 7 +}, +{ + "fields": { + "width": 125, + "file_size": null, + "file": "original_images/vincent_balerdi.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 163, + "focal_point_width": null, + "focal_point_y": null, + "title": "Vincent Balerdi", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 8 +}, +{ + "fields": { + "width": 125, + "file_size": null, + "file": "original_images/nathanel_willaime.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 176, + "focal_point_width": null, + "focal_point_y": null, + "title": "Nathana\u00ebl Willaime", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 9 +}, +{ + "fields": { + "width": 125, + "file_size": null, + "file": "original_images/elisabeth_miller.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 146, + "focal_point_width": null, + "focal_point_y": null, + "title": "\u00c9lisabeth Miller", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 10 +}, +{ + "fields": { + "width": 720, + "file_size": null, + "file": "original_images/arthur_lesage.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 720, + "focal_point_width": null, + "focal_point_y": null, + "title": "Arthur Lesage", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 11 +}, +{ + "fields": { + "width": 445, + "file_size": null, + "file": "original_images/sarah_asset.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 436, + "focal_point_width": null, + "focal_point_y": null, + "title": "Sarah Asset", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 12 +}, +{ + "fields": { + "width": 480, + "file_size": null, + "file": "original_images/alexandre_legrand.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 360, + "focal_point_width": null, + "focal_point_y": null, + "title": "Alexandre Legrand", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 13 +}, +{ + "fields": { + "width": 4608, + "file_size": null, + "file": "original_images/etienne_baudel.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 3456, + "focal_point_width": null, + "focal_point_y": null, + "title": "\u00c9tienne Baudel", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 14 +}, +{ + "fields": { + "width": 358, + "file_size": null, + "file": "original_images/marine_snape.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 435, + "focal_point_width": null, + "focal_point_y": null, + "title": "Marine Snape", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 15 +}, +{ + "fields": { + "width": 121, + "file_size": null, + "file": "original_images/anatole_gosset.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 200, + "focal_point_width": null, + "focal_point_y": null, + "title": "Anatole Gosset", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 16 +}, +{ + "fields": { + "width": 253, + "file_size": null, + "file": "original_images/jacko_rastikian.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 338, + "focal_point_width": null, + "focal_point_y": null, + "title": "Jacko Rastikian", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 17 +}, +{ + "fields": { + "width": 285, + "file_size": null, + "file": "original_images/alexandre_jannaud.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 380, + "focal_point_width": null, + "focal_point_y": null, + "title": "Alexandre Jannaud", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 18 +}, +{ + "fields": { + "width": 283, + "file_size": null, + "file": "original_images/aurelien_delobelle.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 371, + "focal_point_width": null, + "focal_point_y": null, + "title": "Aur\u00e9lien Delobelle", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 19 +}, +{ + "fields": { + "width": 125, + "file_size": null, + "file": "original_images/sylvain_douteau.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 161, + "focal_point_width": null, + "focal_point_y": null, + "title": "Sylvain Douteau", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 20 +}, +{ + "fields": { + "width": 125, + "file_size": null, + "file": "original_images/raphael_lescanne.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 176, + "focal_point_width": null, + "focal_point_y": null, + "title": "Rapha\u00ebl Lescanne", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 21 +}, +{ + "fields": { + "width": 124, + "file_size": null, + "file": "original_images/romain_gourvil.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 157, + "focal_point_width": null, + "focal_point_y": null, + "title": "Romain Gourvil", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 22 +}, +{ + "fields": { + "width": 133, + "file_size": null, + "file": "original_images/marie_labeye.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 163, + "focal_point_width": null, + "focal_point_y": null, + "title": "Marie Labeye", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 23 +}, +{ + "fields": { + "width": 127, + "file_size": null, + "file": "original_images/oscar_blumberg.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 159, + "focal_point_width": null, + "focal_point_y": null, + "title": "Oscar Blumberg", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 24 +}, +{ + "fields": { + "width": 210, + "file_size": null, + "file": "original_images/zaid_allybokus.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 311, + "focal_point_width": null, + "focal_point_y": null, + "title": "Za\u00efd Allybokus", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 25 +}, +{ + "fields": { + "width": 495, + "file_size": null, + "file": "original_images/damien_garreau.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 548, + "focal_point_width": null, + "focal_point_y": null, + "title": "Damien Garreau", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 26 +}, +{ + "fields": { + "width": 323, + "file_size": null, + "file": "original_images/andrea_londono.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 458, + "focal_point_width": null, + "focal_point_y": null, + "title": "Andr\u00e9a Londono-Lopez", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 27 +}, +{ + "fields": { + "width": 120, + "file_size": null, + "file": "original_images/tristan_roussel.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 155, + "focal_point_width": null, + "focal_point_y": null, + "title": "Tristan Roussel", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 28 +}, +{ + "fields": { + "width": 427, + "file_size": null, + "file": "original_images/guillaume_vernade.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 640, + "focal_point_width": null, + "focal_point_y": null, + "title": "Guillaume Vernade", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 29 +}, +{ + "fields": { + "width": 2304, + "file_size": null, + "file": "original_images/lucas_mercier.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 3020, + "focal_point_width": null, + "focal_point_y": null, + "title": "Lucas Mercier", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 30 +}, +{ + "fields": { + "width": 199, + "file_size": null, + "file": "original_images/francois_maillot.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 240, + "focal_point_width": null, + "focal_point_y": null, + "title": "Fran\u00e7ois Maillot", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 31 +}, +{ + "fields": { + "width": 965, + "file_size": null, + "file": "original_images/fabrice_catoire.jpg", + "focal_point_height": null, + "focal_point_x": null, + "height": 1255, + "focal_point_width": null, + "focal_point_y": null, + "title": "Fabrice Catoire", + "collection": 1, + "uploaded_by_user": [ + "root" + ], + "created_at": "2017-05-30T04:20:00.000Z" + }, + "model": "wagtailimages.image", + "pk": 32 +}, +{ + "pk": 1, + "fields": { + "site": [ + "localhost", + 8000 + ], + "use_specific": 1, + "max_levels": 2 + }, + "model": "wagtailmenus.mainmenu" +}, +{ + "pk": 1, + "fields": { + "link_page": 3, + "menu": 1, + "allow_subnav": true, + "handle": "", + "link_text": "Accueil", + "link_url": "", + "sort_order": 0, + "url_append": "" + }, + "model": "wagtailmenus.mainmenuitem" +}, +{ + "pk": 2, + "fields": { + "link_page": 4, + "menu": 1, + "allow_subnav": true, + "handle": "", + "link_text": "", + "link_url": "", + "sort_order": 1, + "url_append": "" + }, + "model": "wagtailmenus.mainmenuitem" +}, +{ + "pk": 3, + "fields": { + "link_page": 5, + "menu": 1, + "allow_subnav": true, + "handle": "", + "link_text": "", + "link_url": "", + "sort_order": 2, + "url_append": "" + }, + "model": "wagtailmenus.mainmenuitem" +}, +{ + "pk": 4, + "fields": { + "link_page": 6, + "menu": 1, + "allow_subnav": true, + "handle": "", + "link_text": "", + "link_url": "", + "sort_order": 3, + "url_append": "" + }, + "model": "wagtailmenus.mainmenuitem" +}, +{ + "pk": 5, + "fields": { + "link_page": 7, + "menu": 1, + "allow_subnav": true, + "handle": "", + "link_text": "", + "link_url": "", + "sort_order": 4, + "url_append": "" + }, + "model": "wagtailmenus.mainmenuitem" +}, +{ + "pk": 6, + "fields": { + "link_page": 8, + "menu": 1, + "allow_subnav": true, + "handle": "", + "link_text": "", + "link_url": "", + "sort_order": 5, + "url_append": "" + }, + "model": "wagtailmenus.mainmenuitem" +} +] diff --git a/kfet/cms/management/commands/kfet_loadwagtail.py b/kfet/cms/management/commands/kfet_loadwagtail.py new file mode 100644 index 00000000..86b94d3e --- /dev/null +++ b/kfet/cms/management/commands/kfet_loadwagtail.py @@ -0,0 +1,35 @@ +from django.contrib.auth.models import Group +from django.core.management import call_command +from django.core.management.base import BaseCommand + +from wagtail.wagtailcore.models import Page, Site + + +class Command(BaseCommand): + help = "Importe des données pour Wagtail" + + def add_arguments(self, parser): + parser.add_argument('--file', default='kfet_wagtail_17_05') + + def handle(self, *args, **options): + + self.stdout.write("Import des données wagtail") + + # Nettoyage des données initiales posées par Wagtail dans la migration + # wagtailcore/0002 + + Group.objects.filter(name__in=('Moderators', 'Editors')).delete() + + try: + homepage = Page.objects.get( + title="Welcome to your new Wagtail site!" + ) + homepage.delete() + Site.objects.filter(root_page=homepage).delete() + except Page.DoesNotExist: + pass + + # Import des données + # Par défaut, il s'agit d'une copie du site K-Fêt (17-05) + + call_command('loaddata', options['file']) diff --git a/kfet/cms/migrations/0001_initial.py b/kfet/cms/migrations/0001_initial.py new file mode 100644 index 00000000..6798aecc --- /dev/null +++ b/kfet/cms/migrations/0001_initial.py @@ -0,0 +1,75 @@ +# -*- coding: utf-8 -*- +from __future__ import unicode_literals + +from django.db import migrations, models +import modelcluster.fields +import wagtail.wagtailcore.fields +import django.db.models.deletion + + +class Migration(migrations.Migration): + + dependencies = [ + ('wagtailcore', '0033_remove_golive_expiry_help_text'), + ('wagtailimages', '0019_delete_filter'), + ] + + operations = [ + migrations.CreateModel( + name='GroupTeam', + fields=[ + ('id', models.AutoField(primary_key=True, verbose_name='ID', auto_created=True, serialize=False)), + ('name', models.CharField(max_length=255, verbose_name='Nom')), + ], + options={ + 'verbose_name': 'Groupe de K-Fêt-eux-ses', + 'verbose_name_plural': 'Groupes de K-Fêt-eux-ses', + }, + ), + migrations.CreateModel( + name='KFetPage', + fields=[ + ('page_ptr', models.OneToOneField(primary_key=True, to='wagtailcore.Page', parent_link=True, auto_created=True, serialize=False)), + ('no_header', models.BooleanField(verbose_name='Sans en-tête', help_text="Coché, l'en-tête (avec le titre) de la page n'est pas affiché.", default=False)), + ('content', wagtail.wagtailcore.fields.RichTextField(verbose_name='Contenu')), + ('custom_template', models.CharField(max_length=255, verbose_name='Template personnalisé', blank=True)), + ], + options={ + 'verbose_name': 'page K-Fêt', + 'verbose_name_plural': 'pages K-Fêt', + }, + bases=('wagtailcore.page',), + ), + migrations.CreateModel( + name='KFetPageGroupTeam', + fields=[ + ('id', models.AutoField(primary_key=True, verbose_name='ID', auto_created=True, serialize=False)), + ('sort_order', models.IntegerField(editable=False, null=True, blank=True)), + ('title', models.CharField(max_length=255, verbose_name='Titre du groupe', blank=True)), + ('content', wagtail.wagtailcore.fields.RichTextField(verbose_name='Texte de présentation du groupe')), + ('group', models.ForeignKey(related_name='+', verbose_name='Groupe de K-Fêt-eux-ses', to='kfetcms.GroupTeam')), + ('page', modelcluster.fields.ParentalKey(related_name='team_groups', to='kfetcms.KFetPage')), + ('show_only', models.IntegerField(default=None, verbose_name='Montrer seulement', blank=True, null=True, help_text='Nombre de membres du groupe affichés initialement. Laisser vide pour tou-te-s les afficher.')), + + ], + options={ + 'abstract': False, + 'ordering': ['sort_order'], + }, + ), + migrations.CreateModel( + name='MemberTeam', + fields=[ + ('id', models.AutoField(primary_key=True, verbose_name='ID', auto_created=True, serialize=False)), + ('sort_order', models.IntegerField(editable=False, null=True, blank=True)), + ('first_name', models.CharField(max_length=255, verbose_name='Prénom', blank=True, default='')), + ('last_name', models.CharField(max_length=255, verbose_name='Nom', blank=True, default='')), + ('nick_name', models.CharField(max_length=255, verbose_name='Alias', blank=True, default='')), + ('group', modelcluster.fields.ParentalKey(related_name='members', verbose_name='Groupe de K-Fêt-eux-ses', to='kfetcms.GroupTeam')), + ('photo', models.ForeignKey(related_name='+', on_delete=django.db.models.deletion.SET_NULL, blank=True, verbose_name='Photo', to='wagtailimages.Image', null=True)), + ], + options={ + 'verbose_name': 'K-Fêt-eux-se', + }, + ), + ] diff --git a/kfet/cms/migrations/__init__.py b/kfet/cms/migrations/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/kfet/cms/models.py b/kfet/cms/models.py new file mode 100644 index 00000000..8b80f175 --- /dev/null +++ b/kfet/cms/models.py @@ -0,0 +1,165 @@ +from django.db import models +from django.utils.translation import ugettext_lazy as _ + +from modelcluster.models import ClusterableModel, ParentalKey +from wagtail.wagtailadmin.edit_handlers import FieldPanel, InlinePanel +from wagtail.wagtailcore.fields import RichTextField +from wagtail.wagtailcore.models import Orderable, Page +from wagtail.wagtailimages.edit_handlers import ImageChooserPanel +from wagtail.wagtailsnippets.edit_handlers import SnippetChooserPanel +from wagtail.wagtailsnippets.models import register_snippet + +from kfet.cms.context_processors import get_articles + + +class KFetPage(Page): + no_header = models.BooleanField( + verbose_name=_('Sans en-tête'), + default=False, + help_text=_( + "Coché, l'en-tête (avec le titre) de la page n'est pas affiché." + ), + ) + content = RichTextField(verbose_name=_('Contenu')) + custom_template = models.CharField( + verbose_name=_('Template personnalisé'), + max_length=255, + blank=True, + ) + + content_panels = Page.content_panels + [ + FieldPanel('no_header'), + FieldPanel('content', classname='full'), + InlinePanel('team_groups', label=_("Groupes de K-Fêt-eux-ses")), + ] + + settings_panels = Page.settings_panels + [ + FieldPanel('custom_template'), + ] + + class Meta: + verbose_name = _('page K-Fêt') + verbose_name_plural = _('pages K-Fêt') + + def __init__(self, *args, **kwargs): + super().__init__(*args, **kwargs) + self.template = "kfetcms/base.html" + + def get_context(self, request, *args, **kwargs): + context = super().get_context(request, *args, **kwargs) + + page = context['page'] + + if not page.seo_title: + page.seo_title = page.title + + if self.slug == "carte": + context.update(get_articles(request)) + + return context + + def get_template(self, request, *args, **kwargs): + return self.custom_template or ( + super().get_template(request, *args, **kwargs)) + + +class KFetPageGroupTeam(Orderable, models.Model): + page = ParentalKey(KFetPage, related_name='team_groups') + group = models.ForeignKey( + 'kfetcms.GroupTeam', + verbose_name=_('Groupe de K-Fêt-eux-ses'), + related_name='+', + ) + title = models.CharField( + verbose_name=_('Titre du groupe'), + max_length=255, + blank=True, + ) + content = RichTextField( + verbose_name=_('Texte de présentation du groupe'), + ) + show_only = models.IntegerField( + verbose_name=_('Montrer seulement'), + blank=True, null=True, default=None, + help_text=_( + 'Nombre de membres du groupe affichés initialement. Laisser vide ' + 'pour tou-te-s les afficher.' + ), + ) + + panels = [ + FieldPanel('title', classname='full'), + FieldPanel('show_only', classname='full'), + FieldPanel('content', classname='full'), + SnippetChooserPanel('group'), + ] + + +@register_snippet +class GroupTeam(ClusterableModel): + name = models.CharField( + verbose_name=_('Nom'), + max_length=255, + ) + + class Meta: + verbose_name = _('Groupe de K-Fêt-eux-ses') + verbose_name_plural = _('Groupes de K-Fêt-eux-ses') + + def __str__(self): + return self.name + + panels = [ + FieldPanel('name', classname='full'), + InlinePanel('members', label=_('Membres du groupe')), + ] + + +@register_snippet +class MemberTeam(Orderable, models.Model): + group = ParentalKey( + GroupTeam, + verbose_name=_("Groupe de K-Fêt-eux-ses"), + on_delete=models.CASCADE, + related_name='members', + ) + first_name = models.CharField( + verbose_name=_('Prénom'), + max_length=255, + blank=True, default='', + ) + last_name = models.CharField( + verbose_name=_('Nom'), + max_length=255, + blank=True, default='', + ) + nick_name = models.CharField( + verbose_name=_('Alias'), + max_length=255, + blank=True, default='', + ) + photo = models.ForeignKey( + 'wagtailimages.Image', + verbose_name=_('Photo'), + on_delete=models.SET_NULL, + null=True, blank=True, + related_name='+', + ) + + class Meta: + verbose_name = _('K-Fêt-eux-se') + + def __str__(self): + return self.get_full_name() + + panels = [ + FieldPanel('first_name'), + FieldPanel('last_name'), + FieldPanel('nick_name'), + FieldPanel('group'), + ImageChooserPanel('photo'), + ] + + def get_full_name(self): + full_name = '{} {}'.format(self.first_name, self.last_name) + return full_name.strip() diff --git a/kfet/cms/static/kfetcms/css/index.css b/kfet/cms/static/kfetcms/css/index.css new file mode 100644 index 00000000..ff175df6 --- /dev/null +++ b/kfet/cms/static/kfetcms/css/index.css @@ -0,0 +1,155 @@ +.cms-content { + text-align: justify; + font-size: 1.1em; +} + +@media (min-width:768px) { + .cms-content { + font-size: 1.2em; + line-height: 1.6em; + } +} + +.cms-column { + column-gap: 45px; + + padding: 20px 15px; + background: white; +} + +@media (min-width: 768px) { + .cms-column { + padding: 35px 30px; + } +} + +@media (min-width: 992px) { + .cms-column { + margin: 0 15px; + } +} + + +/* Titles */ + +.cms-content h2, .cms-content h3 { + clear: both; + margin: 0 0 15px; + padding-bottom: 10px; + border-bottom: 1px solid #c8102e; + text-align: left; + font-weight: bold; +} + +@media (min-width: 768px) { + .cms-content h2, .cms-content h3 { + padding-bottom: 15px; + } +} + +/* Paragraphs */ + +.cms-content p { + margin-bottom: 20px; + text-indent: 2em; +} + +.cms-content p + :not(h2):not(h3):not(div) { + margin-top: -10px; +} + +@media (min-width: 768px) { + .cms-content p { + padding-bottom: 15px; + } + + .cms-content p + :not(h2):not(h3):not(div) { + margin-top: -30px; + } +} + + +/* Lists */ + +.cms-content ol, .cms-content ul { + padding: 0 0 0 15px; + margin: 0 0 10px; +} + +.cms-content ul { + list-style-type: square; +} + +.cms-content ol > li, .cms-content ul > li { + padding-left: 5px; +} + + +/* Images */ + +.cms-content .richtext-image { + max-height: 100%; + margin: 5px 0 15px; +} + +.cms-content .richtext-image.left { + float: left; + margin-right: 30px; +} + +.cms-content .richtext-image.right { + float: right; + margin-left: 30px; +} + + +/* Team groups & members */ + +.team-group { + margin-bottom: 20px; +} + +.team-group .col-btn { + margin-bottom: 20px; +} + +.team-group .member-more { + display: none; +} + +.team-member { + padding: 0; + margin-bottom: 20px; + min-height: 190px; + background-color: inherit; + border: 0; +} + +.team-member img { + max-width: 100%; + max-height: 125px; + width: auto; + height: auto; + display: block; +} + +.team-member .infos { + height: 50px; + margin-top: 15px; +} + +@media (min-width: 768px) { + .team-group { + margin-left: 20px; + margin-right: 20px; + } + + .team-member { + min-height: 215px; + } + + .team-member img { + max-height: 150px; + } +} + diff --git a/kfet/cms/templates/kfetcms/base.html b/kfet/cms/templates/kfetcms/base.html new file mode 100644 index 00000000..043c9ba5 --- /dev/null +++ b/kfet/cms/templates/kfetcms/base.html @@ -0,0 +1,68 @@ +{% extends "kfet/base.html" %} +{% load static %} +{% load wagtailuserbar %} +{% load wagtailcore_tags %} + +{% block extra_head %} + +{% endblock %} + +{% block title %}{{ page.seo_title }}{% endblock %} + +{% block header-class %}text-center{% endblock %} +{% block header-title %}{{ page.title }}{% endblock %} + +{% block content %} + + + +- | Trigramme | +Tri. | Nom | -Balance | -COF | +Balance | +COF | Dpt | -Promo | +Promo |
- + {{ account.trigramme }} | -{{ account.trigramme }} | {{ account.name }} | {{ account.balance }}€ | -{{ account.is_cof|yesno:"Oui,Non" }} | +{{ account.is_cof|yesno }} | {{ account.departement }} | -{{ account.promo|default_if_none:'' }} | +{{ account.promo|default_if_none:'' }} |