def get_absolute_url(self):
return ('catalogue.views.book_detail', [self.slug])
+ @staticmethod
+ @permalink
+ def create_url(slug):
+ return ('catalogue.views.book_detail', [slug])
+
@property
def name(self):
return self.title
def pretty_title(self, html_links=False):
book = self
- names = list(book.tags.filter(category='author'))
-
- books = []
- while book:
- books.append(book)
- book = book.parent
- names.extend(reversed(books))
+ rel_info = book.related_info()
+ names = [(name, Tag.create_url('author', slug))
+ for name, slug in rel_info['tags']['author']]
+ if 'parents' in rel_info:
+ books = [(name, Book.create_url(slug))
+ for name, slug in rel_info['parents']]
+ names.extend(reversed(books))
+ names.append((self.title, self.get_absolute_url()))
if html_links:
- names = ['<a href="%s">%s</a>' % (tag.get_absolute_url(), tag.name) for tag in names]
+ names = ['<a href="%s">%s</a>' % (tag[1], tag[0]) for tag in names]
else:
- names = [tag.name for tag in names]
-
+ names = [tag[0] for tag in names]
return ', '.join(names)
@classmethod
# Copyright © Fundacja Nowoczesna Polska. See NOTICE for more information.
#
from django.conf import settings
+from django.core.cache import get_cache
from django.db.models.signals import post_save, pre_delete, post_delete
import django.dispatch
-from catalogue.models import Tag, BookMedia, Book, Fragment
+from catalogue.models import Tag, BookMedia, Book, Fragment, Collection
from catalogue import tasks
from newtagging.models import tags_updated
+permanent_cache = get_cache('permanent')
+
+
def _tags_updated_handler(sender, affected_tags, **kwargs):
# reset tag global counter
# we want Tag.changed_at updated for API to know the tag was touched
""" refresh all the short_html stuff on BookMedia update """
if sender == BookMedia:
instance.book.save()
+ elif sender == Collection:
+ permanent_cache.delete('catalogue.collection:%s' % instance.slug)
post_save.connect(_post_save_handler)
+def post_publish(sender, **kwargs):
+ permanent_cache.delete_many(['catalogue.book_list',
+ 'catalogue.audiobook_list', 'catalogue.daisy_list'])
+Book.published.connect(post_publish)
+
+
if not settings.NO_SEARCH_INDEX:
@django.dispatch.receiver(post_delete, sender=Book)
def _remove_book_from_index_handler(sender, instance, **kwargs):
def get_absolute_url(self):
return ('catalogue.views.tagged_object_list', [self.url_chunk])
+ @classmethod
+ @permalink
+ def create_url(cls, category, slug):
+ return ('catalogue.views.tagged_object_list', [
+ '/'.join((cls.categories_dict[category], slug))
+ ])
+
def has_description(self):
return len(self.description) > 0
has_description.short_description = _('description')
Możecie z niej korzystać bezpłatnie i bez ograniczeń.
Audiobooki nagrywają znani aktorzy, wśród nich Danuta Stenka i Jan Peszek.{% endblocktrans %}</p>
{% endblock %}
-
-
-{% block book_list %}
- {% audiobook_tree orphans books_by_parent %}
- {% for author, group in books_by_author.items %}
- {% if group %}
- <a name="{{ author.slug }}"></a>
- <div class="group">
- <h2><a href="{{ author.get_absolute_url }}">{{ author }}</a></h2>
- {% audiobook_tree group books_by_parent %}
- </div>
- {% endif %}
- {% endfor %}
-{% endblock %}
{% extends "base.html" %}
{% load i18n %}
-{% load catalogue_tags chunks %}
+{% load catalogue_tags %}
{% block bodyid %}book-a-list{% endblock %}
<div id="book-list-nav" class="normal-text">
{% trans "Table of Content" %}
- {% for index, authors in books_nav.items %}
- <ul>
- <li><a class="book-list-index" href="#">{{ index|upper }}</a></li>
- <ul class="book-list-show-index">
- {% for author in authors %}
- <li><a href="#{{ author.slug }}">{{ author }}</a></li>
- {% endfor %}
- </ul>
- </ul>
- {% endfor %}
+ {{ rendered_nav }}
</div>
<div id="book-list" class="normal-text">
{% block book_list %}
- {% book_tree orphans books_by_parent %}
- {% for author, group in books_by_author.items %}
- {% if group %}
- <a name="{{ author.slug }}"></a>
- <div class="group">
- <h2><a href="{{ author.get_absolute_url }}">{{ author }}</a></h2>
- {% book_tree group books_by_parent %}
- </div>
- {% endif %}
- {% endfor %}
+ {{ rendered_book_list }}
{% endblock %}
</div>
<div id="book-list-up">
--- /dev/null
+{% load catalogue_tags %}
+
+{% audiobook_tree orphans books_by_parent %}
+{% for author, group in books_by_author.items %}
+ {% if group %}
+ <a name="{{ author.slug }}"></a>
+ <div class="group">
+ <h2><a href="{{ author.get_absolute_url }}">{{ author }}</a></h2>
+ {% audiobook_tree group books_by_parent %}
+ </div>
+ {% endif %}
+{% endfor %}
--- /dev/null
+{% load catalogue_tags %}
+
+{% book_tree orphans books_by_parent %}
+{% for author, group in books_by_author.items %}
+ {% if group %}
+ <a name="{{ author.slug }}"></a>
+ <div class="group">
+ <h2><a href="{{ author.get_absolute_url }}">{{ author }}</a></h2>
+ {% book_tree group books_by_parent %}
+ </div>
+ {% endif %}
+{% endfor %}
--- /dev/null
+{% for index, authors in books_nav.items %}
+ <ul>
+ <li><a class="book-list-index" href="#">{{ index|upper }}</a></li>
+ <ul class="book-list-show-index">
+ {% for author in authors %}
+ <li><a href="#{{ author.slug }}">{{ author }}</a></li>
+ {% endfor %}
+ </ul>
+ </ul>
+{% endfor %}
#
import datetime
import feedparser
+from random import randint
from django.conf import settings
from django import template
ignore_by_tag=book.book_tag())[:limit-random]
cache.set(cache_key, related, 1800)
if random:
- related += list(Book.objects.exclude(
- pk__in=[b.pk for b in related] + [book.pk]
- ).order_by('?')[:random])
+ random_books = Book.objects.exclude(
+ pk__in=[b.pk for b in related] + [book.pk])
+ if random == 1:
+ count = random_books.count()
+ if count:
+ related.append(random_books[randint(0, count - 1)])
+ else:
+ related += list(random_books.order_by('?')[:random])
return {
'books': related,
}
@register.simple_tag
def tag_url(category, slug):
- return reverse('catalogue.views.tagged_object_list', args=[
- '/'.join((Tag.categories_dict[category], slug))
- ])
+ return Tag.create_url(category, slug)
@register.simple_tag
import itertools
from django.conf import settings
+from django.core.cache import get_cache
from django.template import RequestContext
+from django.template.loader import render_to_string
from django.shortcuts import render_to_response, get_object_or_404, redirect
from django.http import HttpResponse, HttpResponseRedirect, Http404, HttpResponsePermanentRedirect
from django.core.urlresolvers import reverse
from picture.models import Picture
staff_required = user_passes_test(lambda user: user.is_staff)
+permanent_cache = get_cache('permanent')
def catalogue(request):
def book_list(request, filter=None, template_name='catalogue/book_list.html',
- context=None):
+ nav_template_name='catalogue/snippets/book_list_nav.html',
+ list_template_name='catalogue/snippets/book_list.html',
+ cache_key='catalogue.book_list',
+ context=None,
+ ):
""" generates a listing of all books, optionally filtered with a test function """
-
- books_by_author, orphans, books_by_parent = models.Book.book_list(filter)
- books_nav = SortedDict()
- for tag in books_by_author:
- if books_by_author[tag]:
- books_nav.setdefault(tag.sort_key[0], []).append(tag)
-
+ cached = permanent_cache.get(cache_key)
+ if cached is not None:
+ rendered_nav, rendered_book_list = cached
+ else:
+ books_by_author, orphans, books_by_parent = models.Book.book_list(filter)
+ books_nav = SortedDict()
+ for tag in books_by_author:
+ if books_by_author[tag]:
+ books_nav.setdefault(tag.sort_key[0], []).append(tag)
+ rendered_nav = render_to_string(nav_template_name, locals())
+ rendered_book_list = render_to_string(list_template_name, locals())
+ permanent_cache.set(cache_key, (rendered_nav, rendered_book_list))
return render_to_response(template_name, locals(),
context_instance=RequestContext(request))
def audiobook_list(request):
return book_list(request, Q(media__type='mp3') | Q(media__type='ogg'),
- template_name='catalogue/audiobook_list.html')
+ template_name='catalogue/audiobook_list.html',
+ list_template_name='catalogue/snippets/audiobook_list.html',
+ cache_key='catalogue.audiobook_list')
def daisy_list(request):
return book_list(request, Q(media__type='daisy'),
- template_name='catalogue/daisy_list.html')
+ template_name='catalogue/daisy_list.html',
+ cache_key='catalogue.daisy_list')
def collection(request, slug):
for slug in slugs]
return book_list(request, Q(slug__in=slugs),
template_name='catalogue/collection.html',
+ cache_key='catalogue.collection:%s' % coll.slug,
context={'collection': coll})
from django.conf.urls.defaults import *
urlpatterns = patterns('oai.views',
- url(r'^$', 'oaipmh'))
+ url(r'^$', 'oaipmh', name='oaipmh'))
# This file is part of Wolnelektury, licensed under GNU Affero GPLv3 or later.
# Copyright © Fundacja Nowoczesna Polska. See NOTICE for more information.
#
+from random import randint
from django import template
from catalogue.models import Book
from social.models import Cite
cites = cites_for_tags([ctx.book_tag()])
else:
cites = cites_for_tags(ctx)
- cite = cites.order_by('-sticky', '?')[0] if cites.exists() else None
+ stickies = cites.filter(sticky=True)
+ count = stickies.count()
+ if count:
+ cite = stickies[randint(0, count - 1)]
+ else:
+ count = cites.count()
+ if count:
+ cite = cites[randint(0, count - 1)]
+ else:
+ cite = None
return cite
<li><a href="{% url suggest_publishing %}" id="suggest-publishing" class="ajaxable">{% trans "Missing a book?" %}</a></li>
<li><a href="{% url publish_plan %}">{% trans "Publishing plan" %}</a></li>
<li><a href="{% url api %}">API</a></li>
+ <li><a href="{% url oaipmh %}">OAI-PMH</a></li>
<li><a href="{% url lesmianator %}">Leśmianator</a></li>
<li><a href="http://polski.wolnelektury.pl">Materiały do nauki j. polskiego</a></li>
<div id="main-content">
<div id="nav-line">
- {% cache 60 catalogue-menu LANGUAGE_CODE %}
+ {% cache 300 catalogue-menu LANGUAGE_CODE %}
{% catalogue_menu %}
{% endcache %}