Пример #1
0
    def test_table_render(self):
        data = [
            {
                "first_name": "Paul",
                "last_name": "Simon"
            },
            {
                "first_name": "Art",
                "last_name": "Garfunkel"
            },
        ]

        table = Table(
            [
                Column("first_name"),
                Column("last_name"),
            ],
            data,
        )

        html = self.render_component(table)
        self.assertHTMLEqual(
            html,
            """
            <table class="listing">
                <thead>
                    <tr><th>First name</th><th>Last name</th></tr>
                </thead>
                <tbody>
                    <tr><td>Paul</td><td>Simon</td></tr>
                    <tr><td>Art</td><td>Garfunkel</td></tr>
                </tbody>
            </table>
        """,
        )
Пример #2
0
    def test_table_render_with_width(self):
        data = [
            {'first_name': 'Paul', 'last_name': 'Simon'},
            {'first_name': 'Art', 'last_name': 'Garfunkel'},
        ]

        table = Table([
            Column('first_name'),
            Column('last_name', width='75%'),
        ], data)

        html = self.render_component(table)
        self.assertHTMLEqual(html, '''
            <table class="listing">
                <col />
                <col width="75%" />
                <thead>
                    <tr><th>First name</th><th>Last name</th></tr>
                </thead>
                <tbody>
                    <tr><td>Paul</td><td>Simon</td></tr>
                    <tr><td>Art</td><td>Garfunkel</td></tr>
                </tbody>
            </table>
        ''')
Пример #3
0
class HistoryView(IndexView):
    template_name = "wagtailadmin/generic/index.html"
    page_title = gettext_lazy("Snippet history")
    header_icon = "history"
    paginate_by = 50
    columns = [
        Column("message", label=gettext_lazy("Action")),
        UserColumn("user", blank_display_name="system"),
        DateColumn("timestamp", label=gettext_lazy("Date")),
    ]

    def dispatch(self, request, app_label, model_name, pk):
        self.app_label = app_label
        self.model_name = model_name
        self.model = get_snippet_model_from_url_params(app_label, model_name)
        self.object = get_object_or_404(self.model, pk=unquote(pk))

        return super().dispatch(request)

    def get_page_subtitle(self):
        return str(self.object)

    def get_index_url(self):
        return reverse(
            "wagtailsnippets:history",
            args=(self.app_label, self.model_name, quote(self.object.pk)),
        )

    def get_queryset(self):
        return log_registry.get_logs_for_instance(
            self.object).prefetch_related("user__wagtail_userprofile")
Пример #4
0
class HistoryView(MultipleObjectMixin, WagtailAdminTemplateMixin,
                  InstanceSpecificView):
    page_title = gettext_lazy('History')
    paginate_by = 50
    columns = [
        Column('message', label=gettext_lazy("Action")),
        UserColumn('user', blank_display_name='system'),
        DateColumn('timestamp', label=gettext_lazy("Date")),
    ]

    def get_page_subtitle(self):
        return str(self.instance)

    def get_template_names(self):
        return self.model_admin.get_history_template()

    def get_queryset(self):
        return log_registry.get_logs_for_instance(
            self.instance).prefetch_related('user__wagtail_userprofile')

    def get_context_data(self, **kwargs):
        self.object_list = self.get_queryset()
        context = super().get_context_data(**kwargs)
        index_url = self.url_helper.get_action_url('history',
                                                   quote(self.instance.pk))
        table = Table(self.columns,
                      context['object_list'],
                      base_url=index_url,
                      ordering=self.get_ordering())

        context['table'] = table
        context['media'] = table.media
        context['index_url'] = index_url
        context['is_paginated'] = True
        return context
Пример #5
0
    def test_column_media(self):
        class FancyColumn(Column):
            class Media:
                js = ["js/gradient-fill.js"]

        data = [
            {
                "first_name": "Paul",
                "last_name": "Simon"
            },
            {
                "first_name": "Art",
                "last_name": "Garfunkel"
            },
        ]

        table = Table(
            [
                FancyColumn("first_name"),
                Column("last_name"),
            ],
            data,
        )

        self.assertIn('src="/static/js/gradient-fill.js"',
                      str(table.media["js"]))
Пример #6
0
    def test_row_classname(self):
        class SiteTable(Table):
            def get_row_classname(self, instance):
                return "default-site" if instance.is_default_site else ""

        root_page = Page.objects.filter(depth=2).first()
        blog = Site.objects.create(
            hostname="blog.example.com",
            site_name="My blog",
            root_page=root_page,
            is_default_site=True,
        )
        gallery = Site.objects.create(hostname="gallery.example.com",
                                      site_name="My gallery",
                                      root_page=root_page)
        data = [blog, gallery]

        table = SiteTable(
            [
                Column("hostname"),
                Column("site_name", label="Site name"),
            ],
            data,
        )

        html = self.render_component(table)
        self.assertHTMLEqual(
            html,
            """
            <table class="listing">
                <thead>
                    <tr><th>Hostname</th><th>Site name</th></tr>
                </thead>
                <tbody>
                    <tr class="default-site">
                        <td>blog.example.com</td>
                        <td>My blog</td>
                    </tr>
                    <tr>
                        <td>gallery.example.com</td>
                        <td>My gallery</td>
                    </tr>
                </tbody>
            </table>
        """,
        )
Пример #7
0
class IndexView(generic.IndexView):
    page_title = _("Sites")
    add_item_label = _("Add a site")
    context_object_name = 'sites'
    default_ordering = 'hostname'
    columns = [
        TitleColumn('hostname',
                    label=_("Site"),
                    sort_key='hostname',
                    url_name='wagtailsites:edit'),
        Column('port', sort_key='port'),
        Column('site_name'),
        Column('root_page'),
        StatusFlagColumn('is_default_site',
                         label=_("Default?"),
                         true_label=_("Default")),
    ]
Пример #8
0
    def columns(self):
        columns = super().columns + [
            DownloadColumn("filename", label=_("File")),
            DateColumn("created_at", label=_("Created"), width="16%"),
        ]

        if self.collections:
            columns.insert(2, Column("collection", label=_("Collection")))

        return columns
Пример #9
0
class IndexView(generic.IndexView):
    page_title = _("Sites")
    add_item_label = _("Add a site")
    context_object_name = "sites"
    default_ordering = "hostname"
    columns = [
        TitleColumn(
            "hostname",
            label=_("Site"),
            sort_key="hostname",
            url_name="wagtailsites:edit",
        ),
        Column("port", sort_key="port"),
        Column("site_name"),
        Column("root_page"),
        StatusFlagColumn(
            "is_default_site", label=_("Default?"), true_label=_("Default")
        ),
    ]
Пример #10
0
    def test_title_column(self):
        root_page = Page.objects.filter(depth=2).first()
        blog = Site.objects.create(
            hostname="blog.example.com", site_name="My blog", root_page=root_page
        )
        gallery = Site.objects.create(
            hostname="gallery.example.com", site_name="My gallery", root_page=root_page
        )
        data = [blog, gallery]

        table = Table(
            [
                TitleColumn(
                    "hostname",
                    url_name="wagtailsites:edit",
                    link_classname="choose-site",
                ),
                Column("site_name", label="Site name"),
            ],
            data,
        )

        html = self.render_component(table)
        self.assertHTMLEqual(
            html,
            """
            <table class="listing">
                <thead>
                    <tr><th>Hostname</th><th>Site name</th></tr>
                </thead>
                <tbody>
                    <tr>
                        <td class="title">
                            <div class="title-wrapper">
                                <a href="/admin/sites/%d/" class="choose-site">blog.example.com</a>
                            </div>
                        </td>
                        <td>My blog</td>
                    </tr>
                    <tr>
                        <td class="title">
                            <div class="title-wrapper">
                                <a href="/admin/sites/%d/" class="choose-site">gallery.example.com</a>
                            </div>
                        </td>
                        <td>My gallery</td>
                    </tr>
                </tbody>
            </table>
        """
            % (blog.pk, gallery.pk),
        )
Пример #11
0
    def test_column_media(self):
        class FancyColumn(Column):
            class Media:
                js = ['js/gradient-fill.js']

        data = [
            {'first_name': 'Paul', 'last_name': 'Simon'},
            {'first_name': 'Art', 'last_name': 'Garfunkel'},
        ]

        table = Table([
            FancyColumn('first_name'),
            Column('last_name'),
        ], data)

        self.assertIn('src="/static/js/gradient-fill.js"', str(table.media['js']))
Пример #12
0
 def columns(self):
     return [
         PageTitleColumn("title",
                         label=_("Title"),
                         show_locale_labels=self.i18n_enabled),
         DateColumn(
             "updated",
             label=_("Updated"),
             width="12%",
             accessor="latest_revision_created_at",
         ),
         Column(
             "type",
             label=_("Type"),
             width="12%",
             accessor="page_type_display_name",
         ),
         PageStatusColumn("status", label=_("Status"), width="12%"),
         PageNavigateToChildrenColumn("children", label="", width="10%"),
     ]
Пример #13
0
class HistoryView(MultipleObjectMixin, WagtailAdminTemplateMixin,
                  InstanceSpecificView):
    page_title = gettext_lazy("History")
    paginate_by = 50
    columns = [
        Column("message", label=gettext_lazy("Action")),
        UserColumn("user", blank_display_name="system"),
        DateColumn("timestamp", label=gettext_lazy("Date")),
    ]

    def get_page_subtitle(self):
        return str(self.instance)

    def get_template_names(self):
        return self.model_admin.get_history_template()

    def get_queryset(self):
        return log_registry.get_logs_for_instance(
            self.instance).prefetch_related("user__wagtail_userprofile")

    def get_context_data(self, **kwargs):
        self.object_list = self.get_queryset()
        context = super().get_context_data(**kwargs)
        index_url = self.url_helper.get_action_url("history",
                                                   quote(self.instance.pk))
        table = Table(
            self.columns,
            context["object_list"],
            base_url=index_url,
            ordering=self.get_ordering(),
        )

        context["table"] = table
        context["media"] = table.media
        context["index_url"] = index_url
        context["is_paginated"] = True
        return context
Пример #14
0
    def test_title_column(self):
        root_page = Page.objects.filter(depth=2).first()
        blog = Site.objects.create(hostname='blog.example.com', site_name='My blog', root_page=root_page)
        gallery = Site.objects.create(hostname='gallery.example.com', site_name='My gallery', root_page=root_page)
        data = [blog, gallery]

        table = Table([
            TitleColumn('hostname', url_name='wagtailsites:edit'),
            Column('site_name', label="Site name"),
        ], data)

        html = self.render_component(table)
        self.assertHTMLEqual(html, '''
            <table class="listing">
                <thead>
                    <tr><th>Hostname</th><th>Site name</th></tr>
                </thead>
                <tbody>
                    <tr>
                        <td class="title">
                            <div class="title-wrapper">
                                <a href="/admin/sites/%d/">blog.example.com</a>
                            </div>
                        </td>
                        <td>My blog</td>
                    </tr>
                    <tr>
                        <td class="title">
                            <div class="title-wrapper">
                                <a href="/admin/sites/%d/">gallery.example.com</a>
                            </div>
                        </td>
                        <td>My gallery</td>
                    </tr>
                </tbody>
            </table>
        ''' % (blog.pk, gallery.pk))
Пример #15
0
def browse(request, parent_page_id=None):
    # A missing or empty page_type parameter indicates 'all page types'
    # (i.e. descendants of wagtailcore.page)
    page_type_string = request.GET.get("page_type") or "wagtailcore.page"
    user_perm = request.GET.get("user_perms", False)

    try:
        desired_classes = page_models_from_string(page_type_string)
    except (ValueError, LookupError):
        raise Http404

    # Find parent page
    if parent_page_id:
        parent_page = get_object_or_404(Page, id=parent_page_id)
    elif desired_classes == (Page, ):
        # Just use the root page
        parent_page = Page.get_first_root_node()
    else:
        # Find the highest common ancestor for the specific classes passed in
        # In many cases, such as selecting an EventPage under an EventIndex,
        # this will help the administrator find their page quicker.
        all_desired_pages = Page.objects.all().type(*desired_classes)
        parent_page = all_desired_pages.first_common_ancestor()

    parent_page = parent_page.specific

    # Get children of parent page (without streamfields)
    pages = parent_page.get_children().defer_streamfields().specific()

    # allow hooks to modify the queryset
    for hook in hooks.get_hooks("construct_page_chooser_queryset"):
        pages = hook(pages, request)

    # Filter them by page type
    if desired_classes != (Page, ):
        # restrict the page listing to just those pages that:
        # - are of the given content type (taking into account class inheritance)
        # - or can be navigated into (i.e. have children)
        choosable_pages = pages.type(*desired_classes)
        descendable_pages = pages.filter(numchild__gt=0)
        pages = choosable_pages | descendable_pages

    can_choose_root = request.GET.get("can_choose_root", False)
    target_pages = Page.objects.filter(pk__in=[
        int(pk) for pk in request.GET.getlist("target_pages[]", []) if pk
    ])

    match_subclass = request.GET.get("match_subclass", True)

    # Do permission lookups for this user now, instead of for every page.
    permission_proxy = UserPagePermissionsProxy(request.user)

    # Parent page can be chosen if it is a instance of desired_classes
    parent_page.can_choose = can_choose_page(
        parent_page,
        permission_proxy,
        desired_classes,
        can_choose_root,
        user_perm,
        target_pages=target_pages,
        match_subclass=match_subclass,
    )
    parent_page.is_parent_page = True
    parent_page.can_descend = False

    selected_locale = None
    locale_options = []
    show_locale_labels = getattr(settings, "WAGTAIL_I18N_ENABLED", False)
    if show_locale_labels:
        pages = pages.select_related("locale")

        if parent_page.is_root():
            # 'locale' is the current value of the "Locale" selector in the UI
            if request.GET.get("locale"):
                selected_locale = get_object_or_404(
                    Locale, language_code=request.GET["locale"])
                active_locale_id = selected_locale.pk
            else:
                active_locale_id = Locale.get_active().pk

            # we are at the Root level, so get the locales from the current pages
            choose_url = reverse("wagtailadmin_choose_page")
            locale_options = [{
                "locale":
                locale,
                "url":
                choose_url + "?" + urlencode({
                    "page_type": page_type_string,
                    "locale": locale.language_code
                }),
            } for locale in Locale.objects.filter(
                pk__in=pages.values_list("locale_id")).exclude(
                    pk=active_locale_id)]
        else:
            # We have a parent page (that is not the root page). Use its locale as the selected localer
            selected_locale = parent_page.locale
            # and get the locales based on its available translations
            locales_and_parent_pages = {
                item["locale"]: item["pk"]
                for item in Page.objects.translation_of(parent_page).values(
                    "locale", "pk")
            }
            locales_and_parent_pages[selected_locale.pk] = parent_page.pk
            for locale in Locale.objects.filter(
                    pk__in=list(locales_and_parent_pages.keys())).exclude(
                        pk=selected_locale.pk):
                choose_child_url = reverse(
                    "wagtailadmin_choose_page_child",
                    args=[locales_and_parent_pages[locale.pk]],
                )

                locale_options.append({
                    "locale":
                    locale,
                    "url":
                    choose_child_url + "?" +
                    urlencode({"page_type": page_type_string}),
                })

        # finally, filter the browseable pages on the selected locale
        if selected_locale:
            pages = pages.filter(locale=selected_locale)

    # Pagination
    # We apply pagination first so we don't need to walk the entire list
    # in the block below
    paginator = Paginator(pages, per_page=25)
    pages = paginator.get_page(request.GET.get("p"))

    # Annotate each page with can_choose/can_decend flags
    for page in pages:
        page.can_choose = can_choose_page(
            page,
            permission_proxy,
            desired_classes,
            can_choose_root,
            user_perm,
            target_pages=target_pages,
            match_subclass=match_subclass,
        )
        page.can_descend = page.get_children_count()
        page.is_parent_page = False

    table = PageChooserTable(
        [
            PageTitleColumn("title", label=_("Title")),
            DateColumn(
                "updated",
                label=_("Updated"),
                width="12%",
                accessor="latest_revision_created_at",
            ),
            Column("type",
                   label=_("Type"),
                   width="12%",
                   accessor="page_type_display_name"),
            PageStatusColumn("status", label=_("Status"), width="12%"),
            PageNavigateToChildrenColumn("children", label="", width="10%"),
        ],
        [parent_page] + list(pages),
    )

    # Render
    context = shared_context(
        request,
        {
            "parent_page":
            parent_page,
            "parent_page_id":
            parent_page.pk,
            "table":
            table,
            "pagination_page":
            pages,
            "search_form":
            SearchForm(),
            "page_type_string":
            page_type_string,
            "page_type_names": [
                desired_class.get_verbose_name()
                for desired_class in desired_classes
            ],
            "page_types_restricted": (page_type_string != "wagtailcore.page"),
            "show_locale_labels":
            show_locale_labels,
            "locale_options":
            locale_options,
            "selected_locale":
            selected_locale,
        },
    )

    return render_modal_workflow(
        request,
        "wagtailadmin/chooser/browse.html",
        None,
        context,
        json_data={
            "step": "browse",
            "parent_page_id": context["parent_page_id"]
        },
    )
Пример #16
0
def search(request, parent_page_id=None):
    # A missing or empty page_type parameter indicates 'all page types' (i.e. descendants of wagtailcore.page)
    page_type_string = request.GET.get("page_type") or "wagtailcore.page"

    try:
        desired_classes = page_models_from_string(page_type_string)
    except (ValueError, LookupError):
        raise Http404

    pages = Page.objects.all()
    show_locale_labels = getattr(settings, "WAGTAIL_I18N_ENABLED", False)
    if show_locale_labels:
        pages = pages.select_related("locale")

    # allow hooks to modify the queryset
    for hook in hooks.get_hooks("construct_page_chooser_queryset"):
        pages = hook(pages, request)

    search_form = SearchForm(request.GET)
    if search_form.is_valid() and search_form.cleaned_data["q"]:
        pages = pages.exclude(depth=1)  # never include root
        pages = pages.type(*desired_classes)
        pages = pages.specific()
        pages = pages.search(search_form.cleaned_data["q"])
    else:
        pages = pages.none()

    paginator = Paginator(pages, per_page=25)
    pages = paginator.get_page(request.GET.get("p"))

    for page in pages:
        page.can_choose = True
        page.is_parent_page = False

    table = PageChooserTable(
        [
            PageTitleColumn("title", label=_("Title")),
            ParentPageColumn("parent", label=_("Parent")),
            DateColumn(
                "updated",
                label=_("Updated"),
                width="12%",
                accessor="latest_revision_created_at",
            ),
            Column("type",
                   label=_("Type"),
                   width="12%",
                   accessor="page_type_display_name"),
            PageStatusColumn("status", label=_("Status"), width="12%"),
        ],
        pages,
    )

    return TemplateResponse(
        request,
        "wagtailadmin/chooser/_search_results.html",
        shared_context(
            request,
            {
                "searchform": search_form,
                "table": table,
                "pages": pages,
                "page_type_string": page_type_string,
                "show_locale_labels": show_locale_labels,
            },
        ),
    )
Пример #17
0
    def get(self, request):
        Document = get_document_model()

        if permission_policy.user_has_permission(request.user, "add"):
            DocumentForm = get_document_form(Document)
            self.uploadform = DocumentForm(
                user=request.user, prefix="document-chooser-upload"
            )
        else:
            self.uploadform = None

        documents = permission_policy.instances_user_has_any_permission_for(
            request.user, ["choose"]
        )

        # allow hooks to modify the queryset
        for hook in hooks.get_hooks("construct_document_chooser_queryset"):
            documents = hook(documents, request)

        self.q = None
        self.is_searching = False

        self.collection_id = request.GET.get("collection_id")
        if self.collection_id:
            documents = documents.filter(collection=self.collection_id)
        self.documents_exist = documents.exists()

        if "q" in request.GET:
            self.searchform = SearchForm(request.GET)
            if self.searchform.is_valid():
                self.q = self.searchform.cleaned_data["q"]

                documents = documents.search(self.q)
                self.is_searching = True
        else:
            self.searchform = SearchForm()

        if not self.is_searching:
            documents = documents.order_by("-created_at")

        paginator = Paginator(documents, per_page=10)
        self.documents = paginator.get_page(request.GET.get("p"))

        self.collections = permission_policy.collections_user_has_permission_for(
            request.user, "choose"
        )
        if len(self.collections) < 2:
            self.collections = None

        columns = [
            TitleColumn(
                "title",
                label=_("Title"),
                url_name="wagtaildocs:document_chosen",
                link_classname="document-choice",
            ),
            DownloadColumn("filename", label=_("File")),
            DateColumn("created_at", label=_("Created"), width="16%"),
        ]

        if self.collections:
            columns.insert(2, Column("collection", label=_("Collection")))

        self.table = Table(columns, self.documents)

        return self.render_to_response()