Commit 4e087247935b7fbb7a1aae7d4ef784740c26ce80
1 parent
290a294d
Exists in
master
and in
3 other branches
index url for courses was created, category model added and views are ready
Showing
17 changed files
with
327 additions
and
7 deletions
Show diff stats
amadeus/settings.py
amadeus/templates/base.html
@@ -73,7 +73,7 @@ | @@ -73,7 +73,7 @@ | ||
73 | </div> | 73 | </div> |
74 | <div class="navbar-collapse collapse navbar-responsive-collapse"> | 74 | <div class="navbar-collapse collapse navbar-responsive-collapse"> |
75 | <div class="col-md-5 cards-content" id= 'NavBarSearch'> | 75 | <div class="col-md-5 cards-content" id= 'NavBarSearch'> |
76 | - <form id="SearchForm" action="{% url 'users:search' %}" method="get" accept-charset="utf-8"> | 76 | + <form id="SearchForm" action="#" method="get" accept-charset="utf-8"> |
77 | <div class="input-group"> | 77 | <div class="input-group"> |
78 | <div class="form-group is-empty" > | 78 | <div class="form-group is-empty" > |
79 | <input type="text" class="form-control" placeholder="{% trans 'Search Files (.pdf, others) and/or activities' %}" name="search"> | 79 | <input type="text" class="form-control" placeholder="{% trans 'Search Files (.pdf, others) and/or activities' %}" name="search"> |
@@ -107,10 +107,10 @@ | @@ -107,10 +107,10 @@ | ||
107 | <li> | 107 | <li> |
108 | <a href="" data-toggle="dropdown">{{ user }}</a> | 108 | <a href="" data-toggle="dropdown">{{ user }}</a> |
109 | <ul class="dropdown-menu pull-right"> | 109 | <ul class="dropdown-menu pull-right"> |
110 | - <li><a href="{% url 'users:profile' %}">{% trans 'Perfil' %}</a></li> | ||
111 | - <li><a href="{% url 'users:update_profile' %}">{% trans 'Edit Profile' %}</a></li> | ||
112 | - <li><a href="{% url 'users:change_password' %}">{% trans 'Change password' %}</a></li> | ||
113 | - <li><a href="{% url 'users:remove_account' %}">{% trans 'Remove account' %}</a></li> | 110 | + <li><a href="#">{% trans 'Perfil' %}</a></li> |
111 | + <li><a href="#">{% trans 'Edit Profile' %}</a></li> | ||
112 | + <li><a href="#">{% trans 'Change password' %}</a></li> | ||
113 | + <li><a href="#">{% trans 'Remove account' %}</a></li> | ||
114 | </ul> | 114 | </ul> |
115 | </li> | 115 | </li> |
116 | <li data-toggle="tooltip" data-placement="bottom" title data-original-title="log out"> <a href="#"><i class="fa fa-sign-out" aria-hidden="true"></i></a></li> | 116 | <li data-toggle="tooltip" data-placement="bottom" title data-original-title="log out"> <a href="#"><i class="fa fa-sign-out" aria-hidden="true"></i></a></li> |
amadeus/urls.py
@@ -25,6 +25,7 @@ urlpatterns = [ | @@ -25,6 +25,7 @@ urlpatterns = [ | ||
25 | url(r'^users/', include('users.urls', namespace = 'users')), | 25 | url(r'^users/', include('users.urls', namespace = 'users')), |
26 | url(r'^admin/', admin.site.urls), | 26 | url(r'^admin/', admin.site.urls), |
27 | url(r'^$', index), | 27 | url(r'^$', index), |
28 | + url(r'^courses/', include('courses.urls', namespace = 'courses')), | ||
28 | #API | 29 | #API |
29 | url(r'^o/', include('oauth2_provider.urls', namespace='oauth2_provider')), | 30 | url(r'^o/', include('oauth2_provider.urls', namespace='oauth2_provider')), |
30 | #S3Direct | 31 | #S3Direct |
@@ -0,0 +1,38 @@ | @@ -0,0 +1,38 @@ | ||
1 | +# -*- coding: utf-8 -*- | ||
2 | +# Generated by Django 1.10 on 2016-12-21 03:51 | ||
3 | +from __future__ import unicode_literals | ||
4 | + | ||
5 | +import autoslug.fields | ||
6 | +from django.conf import settings | ||
7 | +from django.db import migrations, models | ||
8 | +import django.db.models.deletion | ||
9 | + | ||
10 | + | ||
11 | +class Migration(migrations.Migration): | ||
12 | + | ||
13 | + initial = True | ||
14 | + | ||
15 | + dependencies = [ | ||
16 | + migrations.swappable_dependency(settings.AUTH_USER_MODEL), | ||
17 | + ] | ||
18 | + | ||
19 | + operations = [ | ||
20 | + migrations.CreateModel( | ||
21 | + name='Category', | ||
22 | + fields=[ | ||
23 | + ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), | ||
24 | + ('name', models.CharField(max_length=100, verbose_name='Name')), | ||
25 | + ('slug', autoslug.fields.AutoSlugField(editable=False, populate_from='name', unique=True, verbose_name='Slug')), | ||
26 | + ('description', models.CharField(max_length=300, verbose_name='description')), | ||
27 | + ('visible', models.BooleanField(verbose_name='visible')), | ||
28 | + ('create_date', models.DateTimeField(auto_now_add=True, verbose_name='Creation Date')), | ||
29 | + ('modified_date', models.DateTimeField(auto_now_add=True, verbose_name='Modified Date')), | ||
30 | + ('category_father', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='category_parent', to='courses.Category')), | ||
31 | + ('coordinators', models.ManyToManyField(related_name='coordinators', to=settings.AUTH_USER_MODEL)), | ||
32 | + ], | ||
33 | + options={ | ||
34 | + 'verbose_name_plural': 'Categories', | ||
35 | + 'verbose_name': 'Category', | ||
36 | + }, | ||
37 | + ), | ||
38 | + ] |
@@ -0,0 +1,23 @@ | @@ -0,0 +1,23 @@ | ||
1 | +from django.db import models | ||
2 | +from autoslug.fields import AutoSlugField | ||
3 | +from django.utils.translation import ugettext_lazy as _ | ||
4 | +from users.models import User | ||
5 | + | ||
6 | +class Category(models.Model): | ||
7 | + """Represents a Course """ | ||
8 | + | ||
9 | + category_father = models.ForeignKey('Category', related_name =_("category_parent"), on_delete = models.CASCADE) | ||
10 | + name = models.CharField(_("Name"), max_length = 100) | ||
11 | + slug = AutoSlugField(_("Slug"),populate_from='name',unique=True) | ||
12 | + description = models.CharField(_("description"), max_length = 300) | ||
13 | + visible = models.BooleanField(_("visible")) | ||
14 | + coordinators = models.ManyToManyField(User, related_name = _("coordinators")) | ||
15 | + create_date = models.DateTimeField(_('Creation Date'), auto_now_add = True) | ||
16 | + modified_date = models.DateTimeField(_('Modified Date'), auto_now_add = True) | ||
17 | + | ||
18 | + class Meta: | ||
19 | + verbose_name = _('Category') | ||
20 | + verbose_name_plural = _('Categories') | ||
21 | + | ||
22 | + def __str__(self): | ||
23 | + return self.name | ||
0 | \ No newline at end of file | 24 | \ No newline at end of file |
@@ -0,0 +1,86 @@ | @@ -0,0 +1,86 @@ | ||
1 | +{% extends 'base.html' %} | ||
2 | + | ||
3 | +{% load static i18n django_bootstrap_breadcrumbs permission_tags %} | ||
4 | + | ||
5 | + | ||
6 | + | ||
7 | +{% block breadcrumbs %} | ||
8 | + {% clear_breadcrumbs %} | ||
9 | + {% breadcrumb 'Home' 'app:index' %} | ||
10 | +{% endblock %} | ||
11 | + | ||
12 | + | ||
13 | +{% block render_breadcrumbs %} | ||
14 | + {% render_breadcrumbs %} | ||
15 | +{% endblock %} | ||
16 | + | ||
17 | +{% block sidebar %} | ||
18 | + <div class="panel panel-primary"> | ||
19 | + <div class="panel-heading"> | ||
20 | + <h4>{% trans 'Menu' %}</h4> | ||
21 | + </div> | ||
22 | + <div class="panel-body menu-lateral"> | ||
23 | + <ul class="nav nav-pills nav-stacked"> | ||
24 | + <li> | ||
25 | + <a href="#menu_courses" class="accordion" data-toggle="collapse">{% trans 'Courses' %}<span class="pull-right glyphicon glyphicon-chevron-down"></span></a> | ||
26 | + <div id="menu_courses" class="collapse"> | ||
27 | + <ul class="nav nav-pill nav-stacked accordion_list"> | ||
28 | + <li><a href="#"><i class="fa fa-book" aria-hidden="true"></i> {% trans 'My Courses' %} </a></li> | ||
29 | + <li><a href="#"><i class="fa fa-globe" aria-hidden="true"></i> {% trans 'All Courses' %} </a></li> | ||
30 | + {% if user|has_role:'system_admin' or user|has_role:'professor'%} | ||
31 | + <li><a href="#"><i class="fa fa-list" aria-hidden="true"></i> {% trans 'List Category' %}</a></li> | ||
32 | + <li><a href="#">{% trans 'Create Course' %}</a></li> | ||
33 | + <li><a href="#">{% trans 'Create Category' %}</a></li> | ||
34 | + {% endif %} | ||
35 | + </ul> | ||
36 | + </div> | ||
37 | + </li> | ||
38 | + {% block menu %} | ||
39 | + | ||
40 | + {% endblock %} | ||
41 | + {% if user|has_role:'system_admin' %} | ||
42 | + | ||
43 | + <li> | ||
44 | + <a href="#menu_users" class="accordion" data-toggle="collapse">{% trans 'Users' %}<span class="pull-right glyphicon glyphicon-chevron-down"></span></a> | ||
45 | + <div id="menu_users" class="collapse"> | ||
46 | + <ul class="nav nav-pill nav-stacked accordion_list"> | ||
47 | + <li> <a href="#"><i class="fa fa-users" aria-hidden="true"></i> {% trans 'Manage Users' %}</a></li> | ||
48 | + <li> <a href="#"><i class="fa fa-user-plus" aria-hidden="true"></i> {% trans 'Create User' %}</a></li> | ||
49 | + </ul> | ||
50 | + </div> | ||
51 | + </li> | ||
52 | + <li> | ||
53 | + <a href="#menu_settings" class="accordion" data-toggle="collapse">{% trans 'Settings' %}<span class="pull-right glyphicon glyphicon-chevron-down"></span></a> | ||
54 | + <div id="menu_settings" class="collapse"> | ||
55 | + <ul class="nav nav-pill nav-stacked accordion_list"> | ||
56 | + | ||
57 | + <li> <a href="#"><i class="fa fa-cog" aria-hidden="true"></i> {% trans "System" %}</a></li> | ||
58 | + | ||
59 | + <li> <a href="#"><i class="fa fa-envelope" aria-hidden="true"></i> {% trans "Mail Sender" %}</a></li> | ||
60 | + <li> <a href="#"><i class="fa fa-shield" aria-hidden="true"></i> {% trans "Security" %}</a></li> | ||
61 | + </ul> | ||
62 | + </div> | ||
63 | + </li> | ||
64 | + {% endif %} | ||
65 | + </ul> | ||
66 | + </div> | ||
67 | + </div> | ||
68 | +{% endblock %} | ||
69 | + | ||
70 | +{% block content %} | ||
71 | + {% if user|has_role:'system_admin' %} | ||
72 | + <h3>{% trans 'Courses' %}</h3> | ||
73 | + <div id="timeline"> | ||
74 | + {% include page_template %} | ||
75 | + </div> | ||
76 | + {% else %} | ||
77 | + <div id="timeline"> | ||
78 | + {% include page_template %} | ||
79 | + </div> | ||
80 | + {% endif %} | ||
81 | + <div id="loading" class="alert alert-primary" role="alert" style="display: none"> | ||
82 | + <center> | ||
83 | + <span class="fa fa-spin fa-circle-o-notch"></span> | ||
84 | + </center> | ||
85 | + </div> | ||
86 | +{% endblock %} |
courses/templates/courses/home_teacher_student_content.html
0 → 100755
@@ -0,0 +1,20 @@ | @@ -0,0 +1,20 @@ | ||
1 | +{% load static i18n %} | ||
2 | + | ||
3 | +{% for notification in objects %} | ||
4 | + | ||
5 | + | ||
6 | + <div class="well timeLine"> | ||
7 | + | ||
8 | + <div class="row"> | ||
9 | + <div class="col-xs-2 col-md-1"> | ||
10 | + <img class="imgTimeLine" src="{{ notification.actor.image_url }}"> | ||
11 | + </div> | ||
12 | + <div class="col-xs-10 col-md-11"> | ||
13 | + <h4 class="resource_inline"><b>{{ notification.actor.username }}</b></h4> | ||
14 | + <p class="resource_inline">{{notification.message}} {% trans 'at' %} : <a href="#">{{ notification.action_resource.resource.name }}</a></p> | ||
15 | + <p class="timePost"><i> {{ notification.datetime|timesince }} {% trans "ago" %} </i></p> | ||
16 | + </div> | ||
17 | + </div> | ||
18 | +</div> | ||
19 | +{% endfor %} | ||
20 | + |
@@ -0,0 +1,66 @@ | @@ -0,0 +1,66 @@ | ||
1 | +{% extends 'home.html' %} | ||
2 | + | ||
3 | +{% load static i18n permission_tags %} | ||
4 | +{% load django_bootstrap_breadcrumbs %} | ||
5 | + | ||
6 | +{% block javascript%} | ||
7 | + {{ block.super }} | ||
8 | +{% endblock%} | ||
9 | + | ||
10 | +{% block breadcrumbs %} | ||
11 | + | ||
12 | +{{ block.super }} | ||
13 | +{% breadcrumb 'Courses' 'course:manage' %} | ||
14 | + | ||
15 | +{% endblock %} | ||
16 | + | ||
17 | +{% block content %} | ||
18 | +{% if messages %} | ||
19 | +{% for message in messages %} | ||
20 | + <script type="text/javascript"> | ||
21 | + alertify.success('{{message}}'); | ||
22 | + </script> | ||
23 | +{% endfor %} | ||
24 | +{% endif %} | ||
25 | + | ||
26 | +<div class="col-md-12 cards-content"> | ||
27 | + <form id="searchform" method="get" accept-charset="utf-8"> | ||
28 | + <div class="input-group"> | ||
29 | + <div class="form-group is-empty"> | ||
30 | + <input type="text" class="form-control" placeholder="{% trans 'Search for Courses' %}" name="q"> | ||
31 | + </div> | ||
32 | + <span class="input-group-btn input-group-sm"> | ||
33 | + <button type="submit" class="btn btn-fab btn-fab-mini"> | ||
34 | + <i class="fa fa-search" aria-hidden="true"></i> | ||
35 | + </button> | ||
36 | + </span> | ||
37 | + </div> | ||
38 | + </form> | ||
39 | +</div> | ||
40 | +<div class="col-md-12 cards-content"> | ||
41 | + {% for category in categorys_courses %} | ||
42 | + <div class="panel-group course-card-group"> | ||
43 | + <div class="panel panel-default"> | ||
44 | + <div class="panel-heading"> | ||
45 | + <div class="row"> | ||
46 | + <div class="col-md-12"> | ||
47 | + <h4 class="panel-title"> | ||
48 | + <a class="category-course-link" data-toggle="collapse" href="#{{category.slug}}">{{category.name}}</a> | ||
49 | + </h4> | ||
50 | + </div> | ||
51 | + </div> | ||
52 | + </div> | ||
53 | + <div id="{{category.slug}}" class="panel-collapse collapse"> | ||
54 | + {% for course in category.course_category %} | ||
55 | + {% include "course/course_card.html" %} | ||
56 | + {% endfor %} | ||
57 | + </div> | ||
58 | + </div> | ||
59 | + </div> | ||
60 | + {% endfor %} | ||
61 | +</div> | ||
62 | +<div id="modal_course"> | ||
63 | + | ||
64 | +</div> | ||
65 | +<script type="text/javascript" src="{% static 'js/course.js' %}"></script> | ||
66 | +{% endblock %} |
@@ -0,0 +1,60 @@ | @@ -0,0 +1,60 @@ | ||
1 | +from django.shortcuts import render | ||
2 | +from django.views.generic import ListView | ||
3 | +from .models import Category | ||
4 | +from django.core.urlresolvers import reverse_lazy | ||
5 | +from rolepermissions.verifications import has_role | ||
6 | + | ||
7 | +from django.utils.translation import ugettext_lazy as _ | ||
8 | + | ||
9 | +from django.contrib.auth.mixins import LoginRequiredMixin | ||
10 | + | ||
11 | +class IndexView(LoginRequiredMixin, ListView): | ||
12 | + | ||
13 | + login_url = reverse_lazy("users:login") | ||
14 | + redirect_field_name = 'next' | ||
15 | + queryset = Category.objects.all() | ||
16 | + template_name = 'courses/home.html' | ||
17 | + context_object_name = 'categories' | ||
18 | + | ||
19 | + | ||
20 | + def get_queryset(self): | ||
21 | + result = super(IndexView, self).get_queryset() | ||
22 | + | ||
23 | + | ||
24 | + return result | ||
25 | + | ||
26 | + def render_to_response(self, context, **response_kwargs): | ||
27 | + if self.request.user.is_staff: | ||
28 | + context['page_template'] = "courses/home_admin_content.html" | ||
29 | + else: | ||
30 | + context['page_template'] = "courses/home_teacher_student_content.html" | ||
31 | + | ||
32 | + context['title'] = _('Home') | ||
33 | + | ||
34 | + if self.request.is_ajax(): | ||
35 | + if self.request.user.is_staff: | ||
36 | + self.template_name = "home_admin_content.html" | ||
37 | + else: | ||
38 | + self.template_name = "home_teacher_student_content.html" | ||
39 | + | ||
40 | + return self.response_class(request = self.request, template = self.template_name, context = context, using = self.template_engine, **response_kwargs) | ||
41 | + | ||
42 | + def get_context_data(self, **kwargs): | ||
43 | + context = super(IndexView, self).get_context_data(**kwargs) | ||
44 | + list_courses = None | ||
45 | + if has_role(self.request.user,'system_admin'): | ||
46 | + list_courses = self.get_queryset().order_by('name') | ||
47 | + # categorys_courses = CourseCategory.objects.all() | ||
48 | + elif has_role(self.request.user,'professor'): | ||
49 | + pass | ||
50 | + #list_courses = self.get_queryset().filter(professors__in = [self.request.user]).order_by('name') | ||
51 | + # categorys_courses = CourseCategory.objects.filter(course_category__professors__name = self.request.user.name).distinct() | ||
52 | + elif has_role(self.request.user, 'student'): | ||
53 | + pass | ||
54 | + #list_courses = self.get_queryset().filter(students__in = [self.request.user]).order_by('name') | ||
55 | + | ||
56 | + | ||
57 | + context['title'] = _('Categories') | ||
58 | + | ||
59 | + return context | ||
60 | + |
users/views.py
@@ -258,7 +258,7 @@ def login(request): | @@ -258,7 +258,7 @@ def login(request): | ||
258 | messages.add_message(request, messages.ERROR, _('E-mail or password are incorrect.')) | 258 | messages.add_message(request, messages.ERROR, _('E-mail or password are incorrect.')) |
259 | context["username"] = username | 259 | context["username"] = username |
260 | elif request.user.is_authenticated: | 260 | elif request.user.is_authenticated: |
261 | - raise Http404('<h1>Page not found</h1>') | 261 | + return redirect('courses:index') |
262 | 262 | ||
263 | return render(request,"users/login.html",context) | 263 | return render(request,"users/login.html",context) |
264 | 264 |