Make custom PageManagers return the correct PageQuerySet subclass

As reported in https://github.com/wagtail/wagtail/issues/3250#issuecomment-284988695, custom page managers created with PageManager.from_queryset(CustomPageQuerySet) fail to return instances of CustomPageQuerySet. This breaks the EventPageQuerySet example given at http://docs.wagtail.io/en/v1.9/topics/pages.html#custom-page-managers.
pull/3907/merge
Matt Westcott 2017-04-20 14:42:12 +01:00
rodzic 0e38f0b401
commit be73f16e14
5 zmienionych plików z 23 dodań i 5 usunięć

Wyświetl plik

@ -28,6 +28,7 @@ Changelog
* Fix: Prevent `USE_THOUSAND_SEPARATOR = True` from breaking the image focal point chooser (Sævar Öfjörð Magnússon)
* Fix: Removed deprecated `SessionAuthenticationMiddleware` from project template (Samir Shah)
* Fix: Custom display page titles defined with `get_admin_display_title` are now shown in search results (Ben Sturmfels, Matt Westcott)
* Fix: Custom PageManagers now return the correct PageQuerySet subclass (Matt Westcott)
1.12.2 (18.09.2017)

Wyświetl plik

@ -42,6 +42,7 @@ Bug fixes
* Prevent ``USE_THOUSAND_SEPARATOR = True`` from breaking the image focal point chooser (Sævar Öfjörð Magnússon)
* Removed deprecated ``SessionAuthenticationMiddleware`` from project template (Samir Shah)
* Custom display page titles defined with ``get_admin_display_title`` are now shown in search results (Ben Sturmfels, Matt Westcott)
* Custom PageManagers now return the correct PageQuerySet subclass (Matt Westcott)
Upgrade considerations
======================

Wyświetl plik

@ -28,7 +28,7 @@ from wagtail.wagtailadmin.forms import WagtailAdminPageForm
from wagtail.wagtailadmin.utils import send_mail
from wagtail.wagtailcore.blocks import CharBlock, RichTextBlock
from wagtail.wagtailcore.fields import RichTextField, StreamField
from wagtail.wagtailcore.models import Orderable, Page, PageManager
from wagtail.wagtailcore.models import Orderable, Page, PageManager, PageQuerySet
from wagtail.wagtaildocs.edit_handlers import DocumentChooserPanel
from wagtail.wagtaildocs.models import AbstractDocument, Document
from wagtail.wagtailforms.models import AbstractEmailForm, AbstractFormField, AbstractFormSubmission
@ -851,8 +851,12 @@ class CustomImageFilePath(AbstractImage):
return os.path.join(folder_name, checksum[:3], filename)
class CustomManager(PageManager):
pass
class CustomPageQuerySet(PageQuerySet):
def about_spam(self):
return self.filter(title__contains='spam')
CustomManager = PageManager.from_queryset(CustomPageQuerySet)
class CustomManagerPage(Page):

Wyświetl plik

@ -195,7 +195,7 @@ def get_default_page_content_type():
class BasePageManager(models.Manager):
def get_queryset(self):
return PageQuerySet(self.model).order_by('path')
return self._queryset_class(self.model).order_by('path')
PageManager = BasePageManager.from_queryset(PageQuerySet)

Wyświetl plik

@ -17,7 +17,8 @@ from freezegun import freeze_time
from wagtail.tests.testapp.models import (
AbstractPage, Advert, AlwaysShowInMenusPage, BlogCategory, BlogCategoryBlogPage, BusinessChild,
BusinessIndex, BusinessNowherePage, BusinessSubIndex, CustomManager, CustomManagerPage,
BusinessIndex, BusinessNowherePage, BusinessSubIndex,
CustomManager, CustomManagerPage, CustomPageQuerySet,
EventIndex, EventPage, GenericSnippetPage, ManyToManyBlogPage, MTIBasePage, MTIChildPage,
MyCustomPage, OneToOnePage, SimplePage, SingleEventPage, SingletonPage, StandardIndex,
TaggedPage)
@ -1267,6 +1268,17 @@ class TestPageManager(TestCase):
"""
self.assertIs(type(CustomManagerPage.objects), CustomManager)
def test_custom_page_queryset(self):
"""
Managers that are constructed from a custom PageQuerySet
(via PageManager.from_queryset(CustomPageQuerySet)) should return
querysets of that type
"""
self.assertIs(type(CustomManagerPage.objects.all()), CustomPageQuerySet)
self.assertIs(type(CustomManagerPage.objects.about_spam()), CustomPageQuerySet)
self.assertIs(type(CustomManagerPage.objects.all().about_spam()), CustomPageQuerySet)
self.assertIs(type(CustomManagerPage.objects.about_spam().all()), CustomPageQuerySet)
def test_abstract_base_page_manager(self):
"""
Abstract base classes should be able to override their default Manager,