diff --git a/CHANGELOG.rst b/CHANGELOG.rst index 0112ad5b..06cd54cf 100644 --- a/CHANGELOG.rst +++ b/CHANGELOG.rst @@ -2,6 +2,13 @@ Changelog ========= +Unreleased +================== +* fix: Error when rendering a Draft Snippet plugin on a Published page +* fix: Publish snippets by default as they were already in that state pre-versioning and cleanup unnecessary migration files before release! +* feat: djangocms-versioning support added, including model restructure and configuration +* feat: django-cms v4.0.x support added + 3.0.0 (2020-09-02) ================== diff --git a/djangocms_snippet/cms_plugins.py b/djangocms_snippet/cms_plugins.py index 63e691fc..a6802626 100644 --- a/djangocms_snippet/cms_plugins.py +++ b/djangocms_snippet/cms_plugins.py @@ -24,6 +24,11 @@ class SnippetPlugin(CMSPluginBase): def render(self, context, instance, placeholder): snippet = instance.snippet_grouper.snippet(show_editable=show_draft_content(context["request"])) + + # Handle the potential for no snippet to be found i.e. Draft + if not snippet: + return context + try: if snippet.template: context = context.flatten() diff --git a/djangocms_snippet/migrations/0010_cms4_grouper_version_data_migration.py b/djangocms_snippet/migrations/0010_cms4_grouper_version_data_migration.py index dee1d352..17e9ecab 100644 --- a/djangocms_snippet/migrations/0010_cms4_grouper_version_data_migration.py +++ b/djangocms_snippet/migrations/0010_cms4_grouper_version_data_migration.py @@ -1,4 +1,5 @@ from django.apps import apps as global_apps +from django.conf import settings from django.contrib.contenttypes.management import create_contenttypes from django.db import migrations @@ -9,7 +10,7 @@ try: - from djangocms_versioning.constants import DRAFT + from djangocms_versioning.constants import DRAFT, PUBLISHED djangocms_versioning_installed = True except ImportError: @@ -24,25 +25,28 @@ def cms4_grouper_version_migration(apps, schema_editor): ContentType = apps.get_model('contenttypes', 'ContentType') Snippet = apps.get_model('djangocms_snippet', 'Snippet') SnippetGrouper = apps.get_model('djangocms_snippet', 'SnippetGrouper') - User = apps.get_model('auth', 'User') + User = apps.get_model(*settings.AUTH_USER_MODEL.split('.')) snippet_contenttype = ContentType.objects.get(app_label='djangocms_snippet', model='snippet') snippet_queryset = Snippet.objects.all() + # Get a migration user to create a version. + if djangocms_versioning_config_enabled and djangocms_versioning_installed and len(snippet_queryset): + Version = apps.get_model('djangocms_versioning', 'Version') + + migration_user = User.objects.get(id=DJANGOCMS_SNIPPET_VERSIONING_MIGRATION_USER_ID) + for snippet in snippet_queryset: grouper = SnippetGrouper.objects.create() snippet.snippet_grouper = grouper snippet.save() - # Get a migration user. - migration_user = User.objects.get(id=DJANGOCMS_SNIPPET_VERSIONING_MIGRATION_USER_ID) - # Create initial Snippet Versions if versioning is enabled and installed. + # Publish the snippet because all snippets were assumed published before if djangocms_versioning_config_enabled and djangocms_versioning_installed: - Version = apps.get_model('djangocms_versioning', 'Version') Version.objects.create( created_by=migration_user, - state=DRAFT, + state=PUBLISHED, number=1, object_id=snippet.pk, content_type=snippet_contenttype, diff --git a/djangocms_snippet/migrations/0012_auto_20210915_0721.py b/djangocms_snippet/migrations/0012_auto_20210915_0721.py index f57f106d..bf228431 100644 --- a/djangocms_snippet/migrations/0012_auto_20210915_0721.py +++ b/djangocms_snippet/migrations/0012_auto_20210915_0721.py @@ -17,12 +17,26 @@ class Migration(migrations.Migration): ), migrations.AlterField( model_name='snippet', - name='snippet_grouper', - field=models.ForeignKey(on_delete=django.db.models.deletion.PROTECT, to='djangocms_snippet.SnippetGrouper'), + name='name', + field=models.CharField(max_length=255, verbose_name='Name'), + ), + migrations.AlterField( + model_name='snippet', + name='slug', + field=models.SlugField(default='', max_length=255, verbose_name='Slug'), + ), + migrations.AlterModelOptions( + name='snippet', + options={'verbose_name': 'Snippet', 'verbose_name_plural': 'Snippets'}, ), migrations.AlterField( model_name='snippetptr', name='snippet_grouper', field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='djangocms_snippet.SnippetGrouper'), ), + migrations.AlterField( + model_name='snippet', + name='snippet_grouper', + field=models.ForeignKey(on_delete=django.db.models.deletion.PROTECT, to='djangocms_snippet.SnippetGrouper'), + ), ] diff --git a/djangocms_snippet/migrations/0013_auto_20210915_0751.py b/djangocms_snippet/migrations/0013_auto_20210915_0751.py deleted file mode 100644 index de813001..00000000 --- a/djangocms_snippet/migrations/0013_auto_20210915_0751.py +++ /dev/null @@ -1,23 +0,0 @@ -# Generated by Django 2.2.24 on 2021-09-15 07:51 - -from django.db import migrations, models - - -class Migration(migrations.Migration): - - dependencies = [ - ('djangocms_snippet', '0012_auto_20210915_0721'), - ] - - operations = [ - migrations.AlterField( - model_name='snippet', - name='name', - field=models.CharField(max_length=255, verbose_name='Name'), - ), - migrations.AlterField( - model_name='snippet', - name='slug', - field=models.SlugField(default='', max_length=255, verbose_name='Slug'), - ), - ] diff --git a/djangocms_snippet/migrations/0014_auto_20211019_0522.py b/djangocms_snippet/migrations/0014_auto_20211019_0522.py deleted file mode 100644 index 1f70ec08..00000000 --- a/djangocms_snippet/migrations/0014_auto_20211019_0522.py +++ /dev/null @@ -1,17 +0,0 @@ -# Generated by Django 2.2.24 on 2021-10-19 10:22 - -from django.db import migrations - - -class Migration(migrations.Migration): - - dependencies = [ - ('djangocms_snippet', '0013_auto_20210915_0751'), - ] - - operations = [ - migrations.AlterModelOptions( - name='snippet', - options={'verbose_name': 'Snippet', 'verbose_name_plural': 'Snippets'}, - ), - ] diff --git a/tests/test_plugins.py b/tests/test_plugins.py index c3ef7e7d..540922ed 100644 --- a/tests/test_plugins.py +++ b/tests/test_plugins.py @@ -171,6 +171,10 @@ def setUp(self): draft_pagecontent_version = self.pagecontent_version.copy(self.superuser) self.draft_pagecontent = draft_pagecontent_version.content + def test_correct_versioning_state_published_snippet_and_page(self): + """ + If a page is published, the published snippet should be rendered + """ # Add plugin to our published page! add_plugin( self.pagecontent.placeholders.get(slot="content"), @@ -186,24 +190,103 @@ def setUp(self): snippet_grouper=self.draft_snippet.snippet_grouper, ) - def test_correct_versioning_state_published_snippet_and_page(self): - """ - If a page is published, the published snippet should be rendered - """ # Request for published page request_url = self.page.get_absolute_url(self.language) with self.login_user_context(self.superuser): response = self.client.get(request_url) self.assertContains(response, "

live content

") + self.assertNotIn("draft content", str(response.content)) def test_correct_versioning_state_draft_snippet_and_page(self): """ If we have a draft, the draft snippet should be rendered. """ + # Add plugin to our published page! + add_plugin( + self.pagecontent.placeholders.get(slot="content"), + "SnippetPlugin", + self.language, + snippet_grouper=self.snippet.snippet_grouper, + ) + # Add plugin to our draft page + add_plugin( + self.draft_pagecontent.placeholders.get(slot="content"), + "SnippetPlugin", + self.language, + snippet_grouper=self.draft_snippet.snippet_grouper, + ) + # Request for draft page request_url = get_object_edit_url(self.draft_pagecontent, "en") with self.login_user_context(self.superuser): response = self.client.get(request_url) self.assertContains(response, "

draft content

") + self.assertNotIn("live content", str(response.content)) + + def test_draft_snippet_and_page_live_url_rendering(self): + """ + If a page is published with a draft snippet created + nothing should be rendered! + """ + snippet_grouper = SnippetGrouper.objects.create() + snippet = Snippet.objects.create( + name="plugin_snippet", + html="

Draft snippet

", + slug="plugin_snippet", + snippet_grouper=snippet_grouper, + ) + Version.objects.create( + content=snippet, + created_by=self.superuser, + created=datetime.datetime.now() + ) + + add_plugin( + self.pagecontent.placeholders.get(slot="content"), + "SnippetPlugin", + self.language, + snippet_grouper=snippet_grouper, + ) + + request_url = self.page.get_absolute_url(self.language) + with self.login_user_context(self.superuser): + response = self.client.get(request_url) + + self.assertEqual(response.status_code, 200) + self.assertNotIn("Draft snippet", str(response.content)) + self.assertNotIn("Published snippet", str(response.content)) + + def test_published_snippet_and_page_live_url_rendering(self): + """ + If a page is published with a published snippet + created the snippet should be rendered! + """ + snippet_grouper = SnippetGrouper.objects.create() + snippet = Snippet.objects.create( + name="plugin_snippet", + html="

Published snippet

", + slug="plugin_snippet", + snippet_grouper=snippet_grouper, + ) + snippet_version = Version.objects.create( + content=snippet, + created_by=self.superuser, + created=datetime.datetime.now() + ) + snippet_version.publish(user=self.superuser) + + add_plugin( + self.pagecontent.placeholders.get(slot="content"), + "SnippetPlugin", + self.language, + snippet_grouper=snippet_grouper, + ) + + request_url = self.page.get_absolute_url(self.language) + with self.login_user_context(self.superuser): + response = self.client.get(request_url) + + self.assertContains(response, "

Published snippet

") + self.assertNotIn("Draft snippet", str(response.content))