Skip to content

Instantly share code, notes, and snippets.

@wfehr
Last active June 27, 2019 05:55
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save wfehr/04dcc2b37da2456307fe3c84df1ad15c to your computer and use it in GitHub Desktop.
Save wfehr/04dcc2b37da2456307fe3c84df1ad15c to your computer and use it in GitHub Desktop.
Overview of changed pages for django-cms
This gist provides an overview for page-changes in django-cms.
It prints out the changed plugins etc. for pages.
Note: This is not a 'diff-tool', so you won't see the exact changes, e.g. text-content.
{% comment %}
NOTE: Classes used in this template depend on 'foundation-sites'. You may want to modify classes, e.g. 'accordion'.
{% endcomment %}
{% extends "myapp/base.html" %}
{% load cms_tags i18n %}
{% block title %}
{% trans "Changed pages overview" %}
{% endblock %}
{% block content %}
{% trans "No changed pages (without plugin changes)" as heading_no_changed_pages %}
{% trans "Changed pages (without plugin changes)" as heading_changed_pages %}
{% trans "No changed static placeholders" as heading_without_dirty_statics %}
{% trans "Changed static placeholders" as heading_with_dirty_statics %}
{% trans "No changed pages (with plugin changes)" as heading_without_plugins %}
{% trans "Changed pages (with plugin changes)" as heading_with_plugins %}
{% trans "Highlight all plugins on page" as highlight_all %}
{% trans "Highlight on page" as highlight_plugin %}
{% trans "edit" as edit %}
<div>
{% if not dirty_statics %}
<h2>
{{ heading_without_dirty_statics }}
</h2>
{% else %}
<h2>
{{ heading_with_dirty_statics }}
</h2>
<ul>
{% for static in dirty_statics %}
<li>
{{ static.code }}
</li>
{% endfor %}
</ul>
{% endif %}
<div>
<strong>Notice</strong>:
<ul>
<li>
Changing a plugin inside a static placeholder results in showing a
"publish page changes"-button on every already published page.
</li>
<li>
A list of plugins inside static placeholders which got changed is not
possible.
</li>
</ul>
<strong>Notice for systems with multiple languages</strong>:
<ul>
<li>
If a plugin inside a static placeholder is changed on one language, the
"publish page changes"-button gets also shown on the other language(s)!
</li>
</ul>
</div>
</div>
<hr>
<div>
{% if not dirty_pages %}
<h2>
{{ heading_no_changed_pages }}
</h2>
{% else %}
<h2>
{{ heading_changed_pages }}
</h2>
<ul>
{% for page in dirty_pages %}
<li>
<a href="{{ page.get_absolute_url }}">{{ page }}</a>
</li>
{% endfor %}
</ul>
{% endif %}
</div>
<hr>
<div>
{% if not dirty_pages_plugins %}
<h2>
{{ heading_without_plugins }}
</h2>
{% else %}
<h2>
{{ heading_with_plugins }}
</h2>
<ul class="accordion" data-accordion data-allow-all-closed="true"
data-multi-expand="true">
{% for page, plugins in dirty_pages_plugins.items %}
<li class="accordion-item" data-accordion-item
style="border-bottom:1px solid gray;">
<a href="#" class="accordion-title">{{ page }}</a>
<div class="accordion-content" data-tab-content>
<a href="{{ page.get_absolute_url }}?structure#plugin_ids={% for plugin in plugins %}{{ plugin.id }}{% if not forloop.last %},{% endif %}{% endfor %}">
&rArr; {{ highlight_all }}
</a>
<ol>
{% for plugin in plugins %}
<li>
<span style="border-bottom:1px dotted gray;">
Plugin-ID: {{ plugin.id }}
&rArr;
<a href="{{ page.get_absolute_url }}?structure#plugin_ids={{ plugin.id }}">
{{ highlight_plugin }}
</a>
&rArr;
<a href="{{ plugin.get_edit_url }}">
{{ edit }}
</a>
</span>
</li>
{% endfor %}
</ol>
</div>
</li>
{% endfor %}
</ul>
{% endif %}
</div>
{% endblock %}
from cms.toolbar_base import CMSToolbar
from cms.toolbar_pool import toolbar_pool
from django.urls import reverse
from django.urls.exceptions import NoReverseMatch
from django.utils.translation import ugettext_lazy as _
EXTRAS_MENU_IDENTIFIER = 'extras'
@toolbar_pool.register
class MyAppToolbar(CMSToolbar):
def populate(self):
self.extras_menu = self.toolbar.get_or_create_menu(
EXTRAS_MENU_IDENTIFIER, _('Extras'))
self.add_changed_pages_handling()
def add_changed_pages_handling(self):
try:
self.extras_menu.add_link_item(
_('Show changed pages overview'),
url=reverse('changed-pages-overview'),
disabled=False,
)
except NoReverseMatch:
pass
...
from myapp.views import changed_pages_overview, motacilla_sitemap
...
urlpatterns = i18n_patterns(
...
url(r'^_/changed-pages-overview/', changed_pages_overview,
name='changed-pages-overview'),
...
)
from cms.models import CMSPlugin, Page, Placeholder, StaticPlaceholder, Title
from django.contrib.auth.decorators import login_required
from django.shortcuts import render
@login_required
def changed_pages_overview(request):
"""Get a list of changed plugins on 'dirty' pages.
"""
dirty_pages = Title.objects.filter(publisher_state=1, publisher_is_draft=1,
published=1)
changed_pages_without_plugins = []
changed_plugins = {}
for title in dirty_pages:
page_placeholders = Placeholder.objects.filter(page=title.page)
page_plugins = []
for placeholder in page_placeholders:
try:
published_page = Page.objects.get(
id=title.page.publisher_public_id
)
except Page.DoesNotExist:
continue
plugins = CMSPlugin.objects.filter(
placeholder_id=placeholder.id,
changed_date__gte=published_page.changed_date
)
page_plugins += plugins
if page_plugins:
changed_plugins.update({title.page: page_plugins})
else:
changed_pages_without_plugins.append(title.page)
context = {'dirty_pages': changed_pages_without_plugins,
'dirty_pages_plugins': changed_plugins,
'dirty_statics': StaticPlaceholder.objects.filter(dirty=1)}
return render(request, 'changed_pages_overview.html', context)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment