"!==m[1]||ha.test(g)?0:i:i.firstChild,f=g&&g.childNodes.length;while(f--)n.nodeName(k=g.childNodes[f],"tbody")&&!k.childNodes.length&&g.removeChild(k)}n.merge(q,i.childNodes),i.textContent="";while(i.firstChild)i.removeChild(i.firstChild);i=p.lastChild}else q.push(b.createTextNode(g));i&&p.removeChild(i),l.appendChecked||n.grep(ea(q,"input"),ia),r=0;while(g=q[r++])if(d&&n.inArray(g,d)>-1)e&&e.push(g);else if(h=n.contains(g.ownerDocument,g),i=ea(p.appendChild(g),"script"),h&&fa(i),c){f=0;while(g=i[f++])_.test(g.type||"")&&c.push(g)}return i=null,p}!function(){var b,c,e=d.createElement("div");for(b in{submit:!0,change:!0,focusin:!0})c="on"+b,(l[b]=c in a)||(e.setAttribute(c,"t"),l[b]=e.attributes[c].expando===!1);e=null}();var ka=/^(?:input|select|textarea)$/i,la=/^key/,ma=/^(?:mouse|pointer|contextmenu|drag|drop)|click/,na=/^(?:focusinfocus|focusoutblur)$/,oa=/^([^.]*)(?:\.(.+)|)/;function pa(){return!0}function qa(){return!1}function ra(){try{return d.activeElement}catch(a){}}function sa(a,b,c,d,e,f){var g,h;if("object"==typeof b){"string"!=typeof c&&(d=d||c,c=void 0);for(h in b)sa(a,h,c,d,b[h],f);return a}if(null==d&&null==e?(e=c,d=c=void 0):null==e&&("string"==typeof c?(e=d,d=void 0):(e=d,d=c,c=void 0)),e===!1)e=qa;else if(!e)return a;return 1===f&&(g=e,e=function(a){return n().off(a),g.apply(this,arguments)},e.guid=g.guid||(g.guid=n.guid++)),a.each(function(){n.event.add(this,b,e,d,c)})}n.event={global:{},add:function(a,b,c,d,e){var f,g,h,i,j,k,l,m,o,p,q,r=n._data(a);if(r){c.handler&&(i=c,c=i.handler,e=i.selector),c.guid||(c.guid=n.guid++),(g=r.events)||(g=r.events={}),(k=r.handle)||(k=r.handle=function(a){return"undefined"==typeof n||a&&n.event.triggered===a.type?void 0:n.event.dispatch.apply(k.elem,arguments)},k.elem=a),b=(b||"").match(G)||[""],h=b.length;while(h--)f=oa.exec(b[h])||[],o=q=f[1],p=(f[2]||"").split(".").sort(),o&&(j=n.event.special[o]||{},o=(e?j.delegateType:j.bindType)||o,j=n.event.special[o]||{},l=n.extend({type:o,origType:q,data:d,handler:c,guid:c.guid,selector:e,needsContext:e&&n.expr.match.needsContext.test(e),namespace:p.join(".")},i),(m=g[o])||(m=g[o]=[],m.delegateCount=0,j.setup&&j.setup.call(a,d,p,k)!==!1||(a.addEventListener?a.addEventListener(o,k,!1):a.attachEvent&&a.attachEvent("on"+o,k))),j.add&&(j.add.call(a,l),l.handler.guid||(l.handler.guid=c.guid)),e?m.splice(m.delegateCount++,0,l):m.push(l),n.event.global[o]=!0);a=null}},remove:function(a,b,c,d,e){var f,g,h,i,j,k,l,m,o,p,q,r=n.hasData(a)&&n._data(a);if(r&&(k=r.events)){b=(b||"").match(G)||[""],j=b.length;while(j--)if(h=oa.exec(b[j])||[],o=q=h[1],p=(h[2]||"").split(".").sort(),o){l=n.event.special[o]||{},o=(d?l.delegateType:l.bindType)||o,m=k[o]||[],h=h[2]&&new RegExp("(^|\\.)"+p.join("\\.(?:.*\\.|)")+"(\\.|$)"),i=f=m.length;while(f--)g=m[f],!e&&q!==g.origType||c&&c.guid!==g.guid||h&&!h.test(g.namespace)||d&&d!==g.selector&&("**"!==d||!g.selector)||(m.splice(f,1),g.selector&&m.delegateCount--,l.remove&&l.remove.call(a,g));i&&!m.length&&(l.teardown&&l.teardown.call(a,p,r.handle)!==!1||n.removeEvent(a,o,r.handle),delete k[o])}else for(o in k)n.event.remove(a,o+b[j],c,d,!0);n.isEmptyObject(k)&&(delete r.handle,n._removeData(a,"events"))}},trigger:function(b,c,e,f){var g,h,i,j,l,m,o,p=[e||d],q=k.call(b,"type")?b.type:b,r=k.call(b,"namespace")?b.namespace.split("."):[];if(i=m=e=e||d,3!==e.nodeType&&8!==e.nodeType&&!na.test(q+n.event.triggered)&&(q.indexOf(".")>-1&&(r=q.split("."),q=r.shift(),r.sort()),h=q.indexOf(":")<0&&"on"+q,b=b[n.expando]?b:new n.Event(q,"object"==typeof b&&b),b.isTrigger=f?2:3,b.namespace=r.join("."),b.rnamespace=b.namespace?new RegExp("(^|\\.)"+r.join("\\.(?:.*\\.|)")+"(\\.|$)"):null,b.result=void 0,b.target||(b.target=e),c=null==c?[b]:n.makeArray(c,[b]),l=n.event.special[q]||{},f||!l.trigger||l.trigger.apply(e,c)!==!1)){if(!f&&!l.noBubble&&!n.isWindow(e)){for(j=l.delegateType||q,na.test(j+q)||(i=i.parentNode);i;i=i.parentNode)p.push(i),m=i;m===(e.ownerDocument||d)&&p.push(m.defaultView||m.parentWindow||a)}o=0;while((i=p[o++])&&!b.isPropagationStopped())b.type=o>1?j:l.bindType||q,g=(n._data(i,"events")||{})[b.type]&&n._data(i,"handle"),g&&g.apply(i,c),g=h&&i[h],g&&g.apply&&M(i)&&(b.result=g.apply(i,c),b.result===!1&&b.preventDefault());if(b.type=q,!f&&!b.isDefaultPrevented()&&(!l._default||l._default.apply(p.pop(),c)===!1)&&M(e)&&h&&e[q]&&!n.isWindow(e)){m=e[h],m&&(e[h]=null),n.event.triggered=q;try{e[q]()}catch(s){}n.event.triggered=void 0,m&&(e[h]=m)}return b.result}},dispatch:function(a){a=n.event.fix(a);var b,c,d,f,g,h=[],i=e.call(arguments),j=(n._data(this,"events")||{})[a.type]||[],k=n.event.special[a.type]||{};if(i[0]=a,a.delegateTarget=this,!k.preDispatch||k.preDispatch.call(this,a)!==!1){h=n.event.handlers.call(this,a,j),b=0;while((f=h[b++])&&!a.isPropagationStopped()){a.currentTarget=f.elem,c=0;while((g=f.handlers[c++])&&!a.isImmediatePropagationStopped())a.rnamespace&&!a.rnamespace.test(g.namespace)||(a.handleObj=g,a.data=g.data,d=((n.event.special[g.origType]||{}).handle||g.handler).apply(f.elem,i),void 0!==d&&(a.result=d)===!1&&(a.preventDefault(),a.stopPropagation()))}return k.postDispatch&&k.postDispatch.call(this,a),a.result}},handlers:function(a,b){var c,d,e,f,g=[],h=b.delegateCount,i=a.target;if(h&&i.nodeType&&("click"!==a.type||isNaN(a.button)||a.button<1))for(;i!=this;i=i.parentNode||this)if(1===i.nodeType&&(i.disabled!==!0||"click"!==a.type)){for(d=[],c=0;h>c;c++)f=b[c],e=f.selector+" ",void 0===d[e]&&(d[e]=f.needsContext?n(e,this).index(i)>-1:n.find(e,this,null,[i]).length),d[e]&&d.push(f);d.length&&g.push({elem:i,handlers:d})}return h]","i"),va=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:-]+)[^>]*)\/>/gi,wa=/
+
{% if request.user.is_authenticated %}
+
+
+{% endblock %}
+
+{% block content %}
+ Ajouter un stage
+
+{% endblock %}
diff --git a/avisstage/templates/avisstage/perso.html b/avisstage/templates/avisstage/perso.html
index 69d424b..960ce31 100644
--- a/avisstage/templates/avisstage/perso.html
+++ b/avisstage/templates/avisstage/perso.html
@@ -3,12 +3,12 @@
{% block content %}
Mon espace personnel
- {{ user.nom }} Modifier mes infos
+ {{ user.profil.nom }} Modifier mes infos
Mes stages
- {% for stage in user.profil.stages %}
+ {% for stage in user.profil.stages.all %}
-
{{ stage.sujet }}
@@ -16,7 +16,7 @@
{% endfor %}
-
-
+
Ajouter un stage
diff --git a/avisstage/urls.py b/avisstage/urls.py
index 2d61037..1dd50d4 100644
--- a/avisstage/urls.py
+++ b/avisstage/urls.py
@@ -4,7 +4,12 @@ from . import views
urlpatterns = [
url(r'^$', views.index, name='index'),
url(r'^perso/$', views.perso, name='perso'),
- url(r'^profil/show/(?P\w+)/$', views.profil, name='profil'),
+ url(r'^stage/nouveau/$', views.StageAjout.as_view(), name='stage_ajout'),
+ url(r'^stage/(?P\w+)/$', views.StageView.as_view(), name='stage'),
+
+ url(r'^profil/show/(?P\w+)/$', views.ProfilView.as_view(),
+ name='profil'),
+ url(r'^profil/edit/$', views.ProfilEdit.as_view(), name='profil_edit'),
url(r'^recherche/$', views.recherche, name='recherche'),
url(r'^feedback/$', views.feedback, name='feedback'),
]
diff --git a/avisstage/views.py b/avisstage/views.py
index d87321c..2b0fc60 100644
--- a/avisstage/views.py
+++ b/avisstage/views.py
@@ -1,14 +1,78 @@
from django.shortcuts import render
+from django.views.generic import DetailView
+from django.views.generic.edit import UpdateView, CreateView
+from django import forms
+from django.urls import reverse
+from django.contrib.auth.decorators import login_required
+from braces.views import LoginRequiredMixin
+
+from avisstage.models import Normalien, Stage
+
+# Page d'accueil
def index(request):
return render(request, 'avisstage/index.html')
+# Espace personnel
+@login_required
def perso(request):
return render(request, 'avisstage/perso.html')
-def profil(request, profil_id):
- return render(request, 'avisstage/profil.html')
+# Profil
+class ProfilEdit(UpdateView, LoginRequiredMixin):
+ model = Normalien
+ fields = ['nom', 'promotion', 'mail']
+ template_name = 'avisstage/formulaires/profil.html'
+ def get_object(self):
+ return self.request.user.profil
+
+ def get_context_data(self, **kwargs):
+ print kwargs
+ return super(ProfilEdit, self).get_context_data(**kwargs)
+
+ def get_success_url(self):
+ return reverse('avisstage:perso')
+
+class ProfilView(DetailView, LoginRequiredMixin):
+ model = Normalien
+ template_name = 'avisstage/detail/profil.html'
+
+ def get_object(self):
+ return Normalien.objects.get(user__username=self.kwargs.get('username'))
+
+# Stages
+class StageForm(forms.ModelForm):
+ date_widget = forms.DateInput(attrs={"class":"datepicker"})
+ date_debut = forms.DateField(input_formats=["%d/%m/%Y"], widget=date_widget)
+ date_fin = forms.DateField(input_formats=["%d/%m/%Y"], widget=date_widget)
+
+ class Meta:
+ model = Stage
+ fields = ['sujet', 'date_debut', 'date_fin', 'type_stage', 'thematiques', 'matieres', 'encadrants']
+
+ def __init__(self, *args, **kwargs):
+ self.request = kwargs.pop("request")
+ super(StageForm, self).__init__(*args, **kwargs)
+
+ def save(self, commit=True):
+ self.instance.auteur = self.request.user.profil
+ super(StageForm, self).save(commit=commit)
+
+class StageAjout(CreateView, LoginRequiredMixin):
+ model = Stage
+ form_class = StageForm
+ template_name = 'avisstage/formulaires/stage.html'
+
+ def get_form_kwargs(self):
+ kwargs = super(StageAjout, self).get_form_kwargs()
+ kwargs.update({'request': self.request})
+ return kwargs
+
+class StageView(DetailView, LoginRequiredMixin):
+ model = Stage
+ template_name = 'avisstage/detail/stage.html'
+
def recherche(request):
return render(request, 'avisstage/recherche.html')
diff --git a/experiENS/settings_base.py b/experiENS/settings_base.py
index 02d0cf8..3dfee32 100644
--- a/experiENS/settings_base.py
+++ b/experiENS/settings_base.py
@@ -10,6 +10,8 @@ https://docs.djangoproject.com/en/1.7/ref/settings/
# Build paths inside the project like this: os.path.join(BASE_DIR, ...)
import os
+from django.core.urlresolvers import reverse_lazy
+
BASE_DIR = os.path.dirname(os.path.dirname(__file__))
# Quick-start development settings - unsuitable for production
@@ -29,8 +31,10 @@ INSTALLED_APPS = (
'django.contrib.gis',
'django_cas_ng',
+ 'braces',
'djrichtextfield',
'taggit',
+ 'taggit_autosuggest',
'avisstage'
)
@@ -109,3 +113,5 @@ AUTHENTICATION_BACKENDS = (
)
CAS_SERVER_URL = "https://cas.eleves.ens.fr/"
+
+LOGIN_URL = reverse_lazy('login')
diff --git a/experiENS/settings_dev.py b/experiENS/settings_dev.py
index e886954..e9abd38 100644
--- a/experiENS/settings_dev.py
+++ b/experiENS/settings_dev.py
@@ -20,3 +20,5 @@ MIDDLEWARE_CLASSES += (
)
SPATIALITE_LIBRARY_PATH = 'mod_spatialite'
+
+STATIC_ROOT = "/home/evarin/Bureau/experiENS/static/"
diff --git a/experiENS/urls.py b/experiENS/urls.py
index d944017..ff796dc 100644
--- a/experiENS/urls.py
+++ b/experiENS/urls.py
@@ -9,5 +9,6 @@ urlpatterns = [
url(r'^login/$', django_cas_views.login, name = "login"),
url(r'^logout/$', django_cas_views.logout, name = "logout"),
url(r'^djrichtextfield/', include('djrichtextfield.urls')),
+ url(r'^taggit_autosuggest/', include('taggit_autosuggest.urls')),
url(r'^admin/', include(admin.site.urls)),
]
diff --git a/requirements.txt b/requirements.txt
index 10aa196..7426d53 100644
--- a/requirements.txt
+++ b/requirements.txt
@@ -3,3 +3,5 @@ django-cas-ng
django-taggit
python-ldap
django-richtextfield
+django-braces
+django-taggit-autosuggest