From 1ebe234a7eebe761fdbf7bbbb1bc32480e840a85 Mon Sep 17 00:00:00 2001 From: Serafeim Papastefanos Date: Wed, 16 Apr 2014 01:05:15 +0300 Subject: [PATCH] Add go_live_datetime handling on views/models The logic for publishing a page exists in the create and edit views of wagtailadmin.views.pages and in the publish methodd of hte PageRevision model. When a page is created and published (create view), if it has a go_live in the future then it will not be live but the revision that will be created will have the approved_go_live set to the corresponding datetime. If the page is just saved or submitted for moderation the normal flow will be followed. When a page is edited and published (edit view): * The approved_go_live_datetime will be cleared for all older revisions of that page. * If the edit has a go_live in the future then the new revision that will be crated will have the approved_go_live set to that datetime. Also the live attribute of the page will be set to False. If the page is edited and not published the normal flow will be followed. When a submitted for moderation page is published (publish method): * If it has a go_live in the future then the live attribute will be set to False, the approved_go_live_datetime of the revision will be set to the go_live_datetime of the page and the approved_go_live_datetime of all other revisions will be cleared. * If it does not have a go_live in the future then the page will be live and the approved_go_live_dattime of all other revisions will be cleard Finally, if a page is unpublished then then approved_go_live_datetime of all revisions of that page will be cleared. --- wagtail/wagtailadmin/views/pages.py | 44 +++++++++++++++++++++++++---- wagtail/wagtailcore/models.py | 32 ++++++++++++++++++--- 2 files changed, 67 insertions(+), 9 deletions(-) diff --git a/wagtail/wagtailadmin/views/pages.py b/wagtail/wagtailadmin/views/pages.py index 703d9f8ddb..8193bdfc44 100644 --- a/wagtail/wagtailadmin/views/pages.py +++ b/wagtail/wagtailadmin/views/pages.py @@ -7,6 +7,7 @@ from django.contrib import messages from django.contrib.contenttypes.models import ContentType from django.contrib.auth.decorators import permission_required from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger +from django.utils import timezone from django.utils.translation import ugettext as _ from django.views.decorators.vary import vary_on_headers @@ -173,16 +174,31 @@ def create(request, content_type_app_name, content_type_model_name, parent_page_ is_publishing = bool(request.POST.get('action-publish')) and parent_page_perms.can_publish_subpage() is_submitting = bool(request.POST.get('action-submit')) + go_live_datetime = form.cleaned_data.get('go_live_datetime') + future_go_live = go_live_datetime and go_live_datetime > timezone.now() + approved_go_live_datetime = None - if is_publishing: + if is_publishing and not future_go_live: page.live = True page.has_unpublished_changes = False + elif is_publishing and future_go_live: + page.live = False + # Set approved_go_live_datetime only if is publishing + # and the future_go_live is actually in future + approved_go_live_datetime = go_live_datetime + page.has_unpublished_changes = False else: page.live = False page.has_unpublished_changes = True parent_page.add_child(page) # assign tree parameters - will cause page to be saved - page.save_revision(user=request.user, submitted_for_moderation=is_submitting) + + # Pass approved_go_live_datetime to save_revision + page.save_revision( + user=request.user, + submitted_for_moderation=is_submitting, + approved_go_live_datetime = approved_go_live_datetime + ) if is_publishing: messages.success(request, _("Page '{0}' published.").format(page.title)) @@ -245,12 +261,24 @@ def edit(request, page_id): if form.is_valid(): is_publishing = bool(request.POST.get('action-publish')) and page_perms.can_publish() is_submitting = bool(request.POST.get('action-submit')) + go_live_datetime = form.cleaned_data.get('go_live_datetime') + future_go_live = go_live_datetime and go_live_datetime > timezone.now() + approved_go_live_datetime = None if is_publishing: - page.live = True page.has_unpublished_changes = False + if future_go_live: + page.live = False + # Set approved_go_live_datetime only if publishing + approved_go_live_datetime = go_live_datetime + else: + page.live = True form.save() - page.revisions.update(submitted_for_moderation=False) + # Clear approved_go_live_datetime for older revisions + page.revisions.update( + submitted_for_moderation=False, + approved_go_live_datetime=None, + ) else: # not publishing the page if page.live: @@ -262,7 +290,11 @@ def edit(request, page_id): page.has_unpublished_changes = True form.save() - page.save_revision(user=request.user, submitted_for_moderation=is_submitting) + page.save_revision( + user=request.user, + submitted_for_moderation=is_submitting, + approved_go_live_datetime = approved_go_live_datetime + ) if is_publishing: messages.success(request, _("Page '{0}' published.").format(page.title)) @@ -443,6 +475,8 @@ def unpublish(request, page_id): parent_id = page.get_parent().id page.live = False page.save() + # Since page is unpublished clear the approved_go_live_datetime of all revisions + page.revisions.update(approved_go_live_datetime=None) messages.success(request, _("Page '{0}' unpublished.").format(page.title)) return redirect('wagtailadmin_explore', parent_id) diff --git a/wagtail/wagtailcore/models.py b/wagtail/wagtailcore/models.py index 96e670ef92..1ecdd1eb00 100644 --- a/wagtail/wagtailcore/models.py +++ b/wagtail/wagtailcore/models.py @@ -373,8 +373,13 @@ class Page(MP_Node, ClusterableModel, Indexed): else: raise Http404 - def save_revision(self, user=None, submitted_for_moderation=False): - self.revisions.create(content_json=self.to_json(), user=user, submitted_for_moderation=submitted_for_moderation) + def save_revision(self, user=None, submitted_for_moderation=False, approved_go_live_datetime=None): + self.revisions.create( + content_json=self.to_json(), + user=user, + submitted_for_moderation=submitted_for_moderation, + approved_go_live_datetime=approved_go_live_datetime, + ) def get_latest_revision(self): try: @@ -539,13 +544,20 @@ class Page(MP_Node, ClusterableModel, Indexed): @property def status_string(self): if not self.live: - return "draft" + if self.approved_schedule: + return "scheduled" + else: + return "draft" else: if self.has_unpublished_changes: return "live + draft" else: return "live" + @property + def approved_schedule(self): + return self.revisions.exclude(approved_go_live_datetime__isnull=True).exists() + def has_unpublished_subtree(self): """ An awkwardly-defined flag used in determining whether unprivileged editors have @@ -693,11 +705,23 @@ class PageRevision(models.Model): def publish(self): page = self.as_page_object() - page.live = True + if page.go_live_datetime and page.go_live_datetime > timezone.now(): + # if we have a go_live in the future don't make the page live + page.live = False + # Instead set the approved_go_live_datetime of this revision + self.approved_go_live_datetime = page.go_live_datetime + self.save() + # And clear the the approved_go_live_datetime of any other revisions + page.revisions.exclude(id=self.id).update(approved_go_live_datetime=None) + else: + page.live = True + # If page goes live clear the approved_go_live_datetime of all revisions + page.revisions.update(approved_go_live_datetime=None) page.save() self.submitted_for_moderation = False page.revisions.update(submitted_for_moderation=False) + PAGE_PERMISSION_TYPE_CHOICES = [ ('add', 'Add'), ('edit', 'Edit'),