kb: add basic elements of a knowledge base

This commit is contained in:
Frédéric Péters 2015-07-12 15:03:01 +02:00
parent f93dcc82d5
commit f6c514864a
15 changed files with 237 additions and 6 deletions

View File

@ -1,3 +1,4 @@
Django>=1.7
gadjo
django-select2
django-ckeditor

View File

@ -100,6 +100,7 @@ setup(
install_requires=['django>=1.7',
'gadjo',
'django-select2',
'django-ckeditor',
],
zip_safe=False,
cmdclass={

0
welco/kb/__init__.py Normal file
View File

33
welco/kb/models.py Normal file
View File

@ -0,0 +1,33 @@
# welco - multichannel request processing
# Copyright (C) 2015 Entr'ouvert
#
# This program is free software: you can redistribute it and/or modify it
# under the terms of the GNU Affero General Public License as 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 Affero General Public License for more details.
#
# You should have received a copy of the GNU Affero General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
from django.core.urlresolvers import reverse
from django.db import models
from django.utils.translation import ugettext_lazy as _
from ckeditor.fields import RichTextField
class Page(models.Model):
title = models.CharField(_('Title'), max_length=200)
slug = models.SlugField(_('Slug'))
content = RichTextField(_('Text'))
class Meta:
ordering = ['title']
def get_absolute_url(self):
return reverse('kb-page-view', kwargs={'slug': self.slug})

View File

@ -0,0 +1,13 @@
{% extends "welco/base.html" %}
{% load i18n static %}
{% block breadcrumb %}
{{ block.super }}
<a href="{% url 'kb-home' %}">{% trans 'Knowledge Base' %}</a>
{% endblock %}
{% block extrascripts %}
{{ block.super }}
<script src="{% static "ckeditor/ckeditor/ckeditor.js" %}"></script>
<script type="text/javascript" src="{% static "ckeditor/ckeditor-init.js" %}"></script>
{% endblock %}

View File

@ -0,0 +1,17 @@
{% extends "kb/base.html" %}
{% load i18n %}
{% block appbar %}
<h2>{{ view.model.get_verbose_name }}</h2>
{% endblock %}
{% block content %}
<form method="post">
{% csrf_token %}
{% blocktrans %}Are you sure you want to delete this?{% endblocktrans %}
<div class="buttons">
<button>{% trans 'Confirm Deletion' %}</button>
<a class="cancel" href="{{ object.get_absolute_url }}">{% trans 'Cancel' %}</a>
</div>
</form>
{% endblock %}

View File

@ -0,0 +1,14 @@
{% extends "kb/base.html" %}
{% load i18n %}
{% block appbar %}
<h2>{% trans 'Knowledge Base' %} - {{ object.title }}</h2>
<a rel="popup" href="{% url 'kb-page-delete' slug=object.slug %}">{% trans 'Delete' %}</a>
<a href="{% url 'kb-page-edit' slug=object.slug %}">{% trans 'Edit' %}</a>
{% endblock %}
{% block content %}
{{ object.content|safe }}
{% endblock %}

View File

@ -0,0 +1,26 @@
{% extends "kb/base.html" %}
{% load i18n %}
{% block appbar %}
{% if object.id %}
<h2>{% trans "Edit Page" %}</h2>
{% else %}
<h2>{% trans "New Page" %}</h2>
{% endif %}
{% endblock %}
{% block content %}
<form method="post" enctype="multipart/form-data">
{% csrf_token %}
{{ form.as_p }}
<div class="buttons">
<button>{% trans "Save" %}</button>
{% if object.id %}
<a class="cancel" href="{{ object.get_absolute_url }}">{% trans 'Cancel' %}</a>
{% else %}
<a class="cancel" href="{% url 'kb-home' %}">{% trans 'Cancel' %}</a>
{% endif %}
</div>
</form>
{% endblock %}

View File

@ -0,0 +1,28 @@
{% extends "kb/base.html" %}
{% load i18n %}
{% block appbar %}
<h2>{% trans 'Knowledge Base' %}</h2>
<a href="{% url 'kb-page-add' %}">{% trans 'New' %}</a>
{% endblock %}
{% block content %}
{% if object_list %}
<div class="objects-list">
{% for page in object_list %}
<div>
<a href="{% url 'kb-page-view' slug=page.slug %}">{{ page.title }}</a>
</div>
{% endfor %}
</div>
{% else %}
<div class="big-msg-info">
{% blocktrans %}
The knowledge base is currently empty. Click on the "New" button in the top
right corner to add a first page.
{% endblocktrans %}
</div>
{% endif %}
{% endblock %}

52
welco/kb/views.py Normal file
View File

@ -0,0 +1,52 @@
# welco - multichannel request processing
# Copyright (C) 2015 Entr'ouvert
#
# This program is free software: you can redistribute it and/or modify it
# under the terms of the GNU Affero General Public License as 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 Affero General Public License for more details.
#
# You should have received a copy of the GNU Affero General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
from django.core.urlresolvers import reverse_lazy
from django.views.generic import (DetailView, CreateView, UpdateView,
ListView, DeleteView)
from .models import Page
class PageListView(ListView):
model = Page
page_list = PageListView.as_view()
class PageAddView(CreateView):
model = Page
page_add = PageAddView.as_view()
class PageEditView(UpdateView):
model = Page
page_edit = PageEditView.as_view()
class PageDetailView(DetailView):
model = Page
page_detail = PageDetailView.as_view()
class PageDeleteView(DeleteView):
model = Page
success_url = reverse_lazy('kb-home')
page_delete = PageDeleteView.as_view()

View File

@ -39,8 +39,10 @@ INSTALLED_APPS = (
'django.contrib.messages',
'django.contrib.staticfiles',
'django_select2',
'ckeditor',
'welco.sources.mail',
'welco.qualif',
'welco.kb',
'gadjo',
)
@ -102,6 +104,20 @@ TEMPLATE_DIRS = (
os.path.join(BASE_DIR, 'welco', 'templates'),
)
CKEDITOR_UPLOAD_PATH = 'uploads/'
CKEDITOR_CONFIGS = {
'default': {
'toolbar_Own': [['Source', 'Format', '-', 'Bold', 'Italic'],
['NumberedList', 'BulletedList'],
['JustifyLeft', 'JustifyCenter', 'JustifyRight', 'JustifyBlock'],
['Link', 'Unlink'],
['Image',],
['RemoveFormat',]],
'toolbar': 'Own',
},
}
# Authentication settings
try:
import mellon

View File

@ -1,15 +1,15 @@
div#main-content {
body.welco-home div#main-content {
width: 100%;
border: 0;
padding: 0;
height: calc(100vh - 8em);
}
div#more-user-links {
body.welco-home div#more-user-links {
display: none;
}
div#content {
body.welco-home div#content {
margin: 0;
padding: 0;
height: 100%;
@ -119,3 +119,25 @@ div#content .cell.qualif .select2-container,
div#content .cell.qualif select {
width: 98%;
}
div.objects-list > div {
border: 1px solid #bcbcbc;
border-collapse: collapse;
margin-top: -1px;
}
div.objects-list > div a {
padding: 1em 1ex;
display: block;
border-bottom: none;
}
div.objects-list > div:hover {
background: #ccc;
}
div.objects-list > div.level-1 {
margin-left: 25px;
}

View File

@ -4,9 +4,6 @@
{% block page-title %}Welco{% endblock %}
{% block site-title %}Welco{% endblock %}
{% block more-user-links %}
{% endblock %}
{% block extrascripts %}
{{ block.super }}
<script src="{% static "js/welco.js" %}"></script>

View File

@ -1,6 +1,8 @@
{% extends "welco/base.html" %}
{% load i18n %}
{% block bodyargs %}class="welco-home"{% endblock %}
{% block content %}
<div class="all">
<div class="cell document source top">

View File

@ -23,9 +23,18 @@ from . import apps
urlpatterns = patterns('',
url(r'^$', 'welco.views.home', name='home'),
url(r'^ajax/qualification$', 'welco.views.qualification', name='qualification'),
url(r'^kb/$', 'welco.kb.views.page_list', name='kb-home'),
url(r'^kb/add/$', 'welco.kb.views.page_add', name='kb-page-add'),
url(r'^kb/(?P<slug>[\w-]+)/$', 'welco.kb.views.page_detail', name='kb-page-view'),
url(r'^kb/(?P<slug>[\w-]+)/edit$', 'welco.kb.views.page_edit', name='kb-page-edit'),
url(r'^kb/(?P<slug>[\w-]+)/delete$', 'welco.kb.views.page_delete', name='kb-page-delete'),
url(r'^admin/', include(admin.site.urls)),
url(r'^logout/$', 'welco.views.logout', name='auth_logout'),
url(r'^login/$', 'welco.views.login', name='auth_login'),
(r'^ckeditor/', include('ckeditor.urls')),
)
if 'mellon' in settings.INSTALLED_APPS: