start static pages
This commit is contained in:
parent
c457ce873c
commit
a59c4a3d5c
|
@ -1,6 +1,7 @@
|
|||
from .article import ArticleAdmin
|
||||
from .episode import DiffusionAdmin, EpisodeAdmin
|
||||
from .log import LogAdmin
|
||||
from .page import PageAdmin, StaticPageAdmin
|
||||
from .program import ProgramAdmin, ScheduleAdmin, StreamAdmin
|
||||
from .sound import SoundAdmin, TrackAdmin
|
||||
from .station import StationAdmin
|
||||
|
|
|
@ -11,8 +11,7 @@ __all__ = ['ArticleAdmin']
|
|||
|
||||
@admin.register(Article)
|
||||
class ArticleAdmin(PageAdmin):
|
||||
list_filter = PageAdmin.list_filter
|
||||
search_fields = PageAdmin.search_fields + ['parent__title']
|
||||
search_fields = PageAdmin.search_fields + ('parent__title',)
|
||||
# TODO: readonly field
|
||||
|
||||
|
||||
|
|
|
@ -56,7 +56,7 @@ class EpisodeAdmin(PageAdmin):
|
|||
form = EpisodeAdminForm
|
||||
list_display = PageAdmin.list_display
|
||||
list_filter = PageAdmin.list_filter
|
||||
search_fields = PageAdmin.search_fields + ['parent__title']
|
||||
search_fields = PageAdmin.search_fields + ('parent__title',)
|
||||
# readonly_fields = ('parent',)
|
||||
|
||||
inlines = [TracksInline, SoundInline, DiffusionInline]
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import urllib
|
||||
from copy import deepcopy
|
||||
|
||||
from django.contrib import admin
|
||||
from django.http import QueryDict
|
||||
|
@ -7,7 +7,7 @@ from django.utils.translation import gettext_lazy as _
|
|||
|
||||
from adminsortable2.admin import SortableInlineAdminMixin
|
||||
|
||||
from ..models import Category, NavItem, Page
|
||||
from ..models import Category, NavItem, Page, StaticPage
|
||||
|
||||
|
||||
__all__ = ['CategoryAdmin', 'PageAdmin', 'NavItemInline']
|
||||
|
@ -22,25 +22,24 @@ class CategoryAdmin(admin.ModelAdmin):
|
|||
prepopulated_fields = {"slug": ("title",)}
|
||||
|
||||
|
||||
# limit category choice
|
||||
class PageAdmin(admin.ModelAdmin):
|
||||
list_display = ('cover_thumb', 'title', 'status', 'category', 'parent')
|
||||
class BasePageAdmin(admin.ModelAdmin):
|
||||
list_display = ('cover_thumb', 'title', 'status', 'parent')
|
||||
list_display_links = ('cover_thumb', 'title')
|
||||
list_editable = ('status', 'category')
|
||||
list_filter = ('status', 'category')
|
||||
list_editable = ('status',)
|
||||
list_filter = ('status',)
|
||||
prepopulated_fields = {"slug": ("title",)}
|
||||
|
||||
# prepopulate fields using changelist's filters
|
||||
prepopulated_filters = ('parent',)
|
||||
|
||||
search_fields = ['title', 'category__title']
|
||||
search_fields = ('title',)
|
||||
fieldsets = [
|
||||
('', {
|
||||
'fields': ['title', 'slug', 'category', 'cover', 'content'],
|
||||
'fields': ['title', 'slug', 'cover', 'content'],
|
||||
}),
|
||||
(_('Publication Settings'), {
|
||||
'fields': ['featured', 'allow_comments', 'status', 'parent'],
|
||||
'classes': ('collapse',),
|
||||
'fields': ['status', 'parent'],
|
||||
# 'classes': ('collapse',),
|
||||
}),
|
||||
]
|
||||
|
||||
|
@ -59,10 +58,16 @@ class PageAdmin(admin.ModelAdmin):
|
|||
def get_common_context(self, query, extra_context=None):
|
||||
extra_context = extra_context or {}
|
||||
parent = query.get('parent', None)
|
||||
if parent is not None:
|
||||
extra_context['parent'] = Page.objects.get_subclass(id=parent)
|
||||
extra_context['parent'] = None if parent is None else \
|
||||
Page.objects.get_subclass(id=parent)
|
||||
|
||||
return extra_context
|
||||
|
||||
def render_change_form(self, request, context, *args, **kwargs):
|
||||
if context['original'] and not 'parent' in context:
|
||||
context['parent'] = context['original'].parent
|
||||
return super().render_change_form(request, context, *args, **kwargs)
|
||||
|
||||
def add_view(self, request, form_url='', extra_context=None):
|
||||
filters = QueryDict(request.GET.get('_changelist_filters', ''))
|
||||
extra_context = self.get_common_context(filters, extra_context)
|
||||
|
@ -73,6 +78,27 @@ class PageAdmin(admin.ModelAdmin):
|
|||
return super().changelist_view(request, extra_context)
|
||||
|
||||
|
||||
class PageAdmin(BasePageAdmin):
|
||||
list_display = BasePageAdmin.list_display + ('category',)
|
||||
list_editable = BasePageAdmin.list_editable + ('category',)
|
||||
list_filter = BasePageAdmin.list_editable + ('category',)
|
||||
search_fields = ('category__title',)
|
||||
fieldsets = deepcopy(BasePageAdmin.fieldsets)
|
||||
|
||||
fieldsets[0][1]['fields'].insert(fieldsets[0][1]['fields'].index('slug') + 1, 'category')
|
||||
fieldsets[1][1]['fields'] += ('featured', 'allow_comments')
|
||||
|
||||
|
||||
@admin.register(StaticPage)
|
||||
class StaticPageAdmin(BasePageAdmin):
|
||||
list_display = BasePageAdmin.list_display + ('view','menu_title')
|
||||
list_editable = BasePageAdmin.list_editable + ('menu_title',)
|
||||
fieldsets = deepcopy(BasePageAdmin.fieldsets)
|
||||
|
||||
fieldsets[0][1]['fields'].insert(fieldsets[0][1]['fields'].index('slug') + 1, 'menu_title')
|
||||
fieldsets[1][1]['fields'] += ('view',)
|
||||
|
||||
|
||||
class NavItemInline(SortableInlineAdminMixin, admin.TabularInline):
|
||||
model = NavItem
|
||||
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
from .article import Article
|
||||
from .page import Category, Page, Comment, NavItem
|
||||
from .page import Category, Page, StaticPage, Comment, NavItem
|
||||
from .program import Program, Stream, Schedule
|
||||
from .episode import Episode, Diffusion
|
||||
from .log import Log
|
||||
|
|
|
@ -29,7 +29,7 @@ class LogQuerySet(models.QuerySet):
|
|||
start = tz.datetime.combine(date, datetime.time())
|
||||
end = tz.datetime.combine(date, datetime.time(23, 59, 59, 999))
|
||||
return self.filter(date__range = (start, end))
|
||||
# this filter does not work with sql
|
||||
# this filter does not work with mysql
|
||||
# return self.filter(date__date=date)
|
||||
|
||||
def after(self, date):
|
||||
|
|
|
@ -54,7 +54,7 @@ class PageQuerySet(InheritanceQuerySet):
|
|||
self.filter(parent__id=id)
|
||||
|
||||
|
||||
class Page(models.Model):
|
||||
class BasePage(models.Model):
|
||||
""" Base class for publishable content """
|
||||
STATUS_DRAFT = 0x00
|
||||
STATUS_PUBLISHED = 0x10
|
||||
|
@ -72,30 +72,22 @@ class Page(models.Model):
|
|||
status = models.PositiveSmallIntegerField(
|
||||
_('status'), default=STATUS_DRAFT, choices=STATUS_CHOICES,
|
||||
)
|
||||
category = models.ForeignKey(
|
||||
Category, models.SET_NULL,
|
||||
verbose_name=_('category'), blank=True, null=True, db_index=True
|
||||
)
|
||||
cover = FilerImageField(
|
||||
on_delete=models.SET_NULL,
|
||||
verbose_name=_('Cover'), null=True, blank=True,
|
||||
verbose_name=_('cover'), null=True, blank=True,
|
||||
)
|
||||
content = RichTextField(
|
||||
_('content'), blank=True, null=True,
|
||||
)
|
||||
pub_date = models.DateTimeField(blank=True, null=True)
|
||||
featured = models.BooleanField(
|
||||
_('featured'), default=False,
|
||||
)
|
||||
allow_comments = models.BooleanField(
|
||||
_('allow comments'), default=True,
|
||||
)
|
||||
|
||||
objects = PageQuerySet.as_manager()
|
||||
|
||||
detail_url_name = None
|
||||
item_template_name = 'aircox/widgets/page_item.html'
|
||||
|
||||
class Meta:
|
||||
abstract = True
|
||||
|
||||
def __str__(self):
|
||||
return '{}'.format(self.title or self.pk)
|
||||
|
||||
|
@ -106,10 +98,6 @@ class Page(models.Model):
|
|||
count = Page.objects.filter(slug__startswith=self.slug).count()
|
||||
if count:
|
||||
self.slug += '-' + str(count)
|
||||
if self.is_published and self.pub_date is None:
|
||||
self.pub_date = tz.now()
|
||||
elif not self.is_published:
|
||||
self.pub_date = None
|
||||
|
||||
if not self.cover and self.parent:
|
||||
self.cover = self.parent.cover
|
||||
|
@ -150,9 +138,71 @@ class Page(models.Model):
|
|||
return cls(**cls.get_init_kwargs_from(page, **kwargs))
|
||||
|
||||
|
||||
class Page(BasePage):
|
||||
""" Base Page model used for articles and other dated content. """
|
||||
category = models.ForeignKey(
|
||||
Category, models.SET_NULL,
|
||||
verbose_name=_('category'), blank=True, null=True, db_index=True
|
||||
)
|
||||
pub_date = models.DateTimeField(blank=True, null=True)
|
||||
featured = models.BooleanField(
|
||||
_('featured'), default=False,
|
||||
)
|
||||
allow_comments = models.BooleanField(
|
||||
_('allow comments'), default=True,
|
||||
)
|
||||
|
||||
def save(self, *args, **kwargs):
|
||||
if self.is_published and self.pub_date is None:
|
||||
self.pub_date = tz.now()
|
||||
elif not self.is_published:
|
||||
self.pub_date = None
|
||||
super().save(*args, **kwargs)
|
||||
|
||||
|
||||
class StaticPage(Page):
|
||||
""" Static page that eventually can be attached to a specific view. """
|
||||
VIEW_HOME = 0x00
|
||||
VIEW_SCHEDULE = 0x01
|
||||
VIEW_LOG = 0x02
|
||||
VIEW_PROGRAMS = 0x03
|
||||
VIEW_EPISODES = 0x04
|
||||
VIEW_ARTICLES = 0x05
|
||||
|
||||
VIEW_CHOICES = (
|
||||
(VIEW_HOME, _('Home Page')),
|
||||
(VIEW_SCHEDULE, _('Schedule Page')),
|
||||
(VIEW_LOG, _('Log Page')),
|
||||
(VIEW_PROGRAMS, _('Programs list')),
|
||||
(VIEW_EPISODES, _('Episodes list')),
|
||||
(VIEW_ARTICLES, _('Articles list')),
|
||||
)
|
||||
|
||||
view = models.SmallIntegerField(
|
||||
_('attach to'), choices=VIEW_CHOICES, blank=True, null=True,
|
||||
help_text=_('display this page content to related element'),
|
||||
)
|
||||
menu_title = models.CharField(_('menu title'), max_length=64, blank=True, null=True)
|
||||
|
||||
is_active = False
|
||||
|
||||
def render_menu_item(self, request, css_class='', active_class=''):
|
||||
if active_class and request.path.startswith(self.url):
|
||||
css_class += ' ' + active_class
|
||||
|
||||
if not self.url:
|
||||
return self.text
|
||||
elif not css_class:
|
||||
return format_html('<a href="{}">{}</a>', self.url, self.text)
|
||||
else:
|
||||
return format_html('<a href="{}" class="{}">{}</a>', self.url,
|
||||
css_class, self.text)
|
||||
|
||||
|
||||
class Comment(models.Model):
|
||||
page = models.ForeignKey(
|
||||
Page, models.CASCADE, verbose_name=_('related page'),
|
||||
# TODO: allow_comment filter
|
||||
)
|
||||
nickname = models.CharField(_('nickname'), max_length=32)
|
||||
email = models.EmailField(_('email'), max_length=32)
|
||||
|
|
|
@ -8,11 +8,9 @@
|
|||
› <a href="{% url 'admin:app_list' app_label=opts.app_label %}">{{ opts.app_config.verbose_name }}</a>
|
||||
› {% if has_view_permission %}<a href="{% url opts|admin_urlname:'changelist' %}">{{ opts.verbose_name_plural|capfirst }}</a>{% else %}{{ opts.verbose_name_plural|capfirst }}{% endif %}
|
||||
|
||||
{% with parent=parent|default:original.parent %}
|
||||
{% if parent %}
|
||||
› <a href="{% url opts|admin_urlname:"changelist" %}?parent={{parent.id}}">{{ parent.title }}</a>
|
||||
{% endif %}
|
||||
{% endwith %}
|
||||
|
||||
› {% if add %}{% blocktrans with name=opts.verbose_name %}Add {{ name }}{% endblocktrans %}{% else %}{{ original|truncatewords:"18" }}{% endif %}
|
||||
</div>
|
||||
|
|
|
@ -60,6 +60,12 @@ urls = [
|
|||
path(_('publications/'),
|
||||
views.PageListView.as_view(model=models.Page), name='page-list'),
|
||||
|
||||
path(_('pages/'),
|
||||
views.PageListView.as_view(model=models.StaticPage), name='static-page-list'),
|
||||
|
||||
path(_('pages/<slug:slug>/'),
|
||||
views.PageDetailView.as_view(), name='page-detail'),
|
||||
|
||||
path(_('programs/'), views.ProgramListView.as_view(model=models.Program),
|
||||
name='program-list'),
|
||||
path(_('programs/<slug:slug>/'),
|
||||
|
|
Loading…
Reference in New Issue
Block a user