Merge preakholt changes
This commit is contained in:
commit
d7ad1be51f
|
@ -13,6 +13,7 @@
|
|||
.vscode/
|
||||
|
||||
build/
|
||||
ve/
|
||||
dist/
|
||||
htmlcov/
|
||||
docs/_build
|
||||
|
|
|
@ -14,6 +14,8 @@ matrix:
|
|||
env: TOXENV=py36-django20-wagtail21
|
||||
- python: 3.6
|
||||
env: TOXENV=py36-django20-wagtail21-geoip2
|
||||
- python: 3.6
|
||||
env: TOXENV=py36-django111-wagtail22
|
||||
|
||||
install:
|
||||
- pip install tox codecov
|
||||
|
|
10
CHANGES
10
CHANGES
|
@ -1,10 +1,18 @@
|
|||
0.13.0
|
||||
=================
|
||||
- Merged Praekolt fork
|
||||
- Add custom javascript to segment forms
|
||||
- bugfix:exclude variant returns queryset when params is queryset
|
||||
- Added RulePanel, a subclass of InlinePanel, for Rules
|
||||
- Upgrade to Wagtail > 2.0, drop support for Wagtail < 2
|
||||
|
||||
0.12.0
|
||||
==================
|
||||
- Fix Django version classifier in setup.py
|
||||
|
||||
0.12.0
|
||||
==================
|
||||
- Merged forks of Torchbox and Praekelt
|
||||
- Merged forks of Torchbox and Praekolt
|
||||
- Wagtail 2 compatibility
|
||||
- Makefile adjustments for portability
|
||||
- Adds simple segment forcing for superusers
|
||||
|
|
|
@ -54,7 +54,7 @@ master_doc = 'index'
|
|||
|
||||
# General information about the project.
|
||||
project = 'wagtail-personalisation'
|
||||
copyright = '2018, Lab Digital BV'
|
||||
copyright = '2019, Lab Digital BV'
|
||||
author = 'Lab Digital BV'
|
||||
|
||||
# The version info for the project you're documenting, acts as replacement for
|
||||
|
|
6
setup.py
6
setup.py
|
@ -2,7 +2,7 @@ import re
|
|||
from setuptools import find_packages, setup
|
||||
|
||||
install_requires = [
|
||||
'wagtail>=2.0',
|
||||
'wagtail>=2.0,<2.3',
|
||||
'user-agents>=1.1.0',
|
||||
'wagtailfontawesome>=1.1.3',
|
||||
'pycountry',
|
||||
|
@ -20,7 +20,7 @@ tests_require = [
|
|||
'pytest-pythonpath==0.7.2',
|
||||
'pytest-sugar==0.9.1',
|
||||
'pytest==3.4.2',
|
||||
'wagtail_factories==1.0.0',
|
||||
'wagtail_factories==1.1.0',
|
||||
'pytest-mock==1.6.3',
|
||||
]
|
||||
|
||||
|
@ -52,7 +52,7 @@ setup(
|
|||
license='MIT',
|
||||
long_description=long_description,
|
||||
classifiers=[
|
||||
'Development Status :: 2 - Pre-Alpha',
|
||||
'Development Status :: 5 - Production/Stable',
|
||||
'Environment :: Web Environment',
|
||||
'Intended Audience :: Developers',
|
||||
'License :: OSI Approved :: BSD License',
|
||||
|
|
|
@ -1,16 +1,15 @@
|
|||
import random
|
||||
|
||||
import wagtail
|
||||
from django import forms
|
||||
from django.conf import settings
|
||||
from django.core.validators import MaxValueValidator, MinValueValidator
|
||||
from django.db import models, transaction
|
||||
from django.template.defaultfilters import slugify
|
||||
from django.utils.encoding import python_2_unicode_compatible
|
||||
from django.utils.functional import cached_property
|
||||
from django.utils.safestring import mark_safe
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
from modelcluster.models import ClusterableModel
|
||||
import wagtail
|
||||
from wagtail.admin.edit_handlers import (
|
||||
FieldPanel, FieldRowPanel, InlinePanel, MultiFieldPanel)
|
||||
from wagtail.core.models import Page
|
||||
|
@ -21,12 +20,19 @@ from wagtail_personalisation.utils import count_active_days
|
|||
from .forms import SegmentAdminForm
|
||||
|
||||
|
||||
class RulePanel(InlinePanel):
|
||||
def on_model_bound(self):
|
||||
self.db_field = self.model._meta.get_field(
|
||||
self.relation_name.replace('_related', 's'))
|
||||
manager = getattr(self.model, self.relation_name)
|
||||
self.related = manager.rel
|
||||
|
||||
|
||||
class SegmentQuerySet(models.QuerySet):
|
||||
def enabled(self):
|
||||
return self.filter(status=self.model.STATUS_ENABLED)
|
||||
|
||||
|
||||
@python_2_unicode_compatible
|
||||
class Segment(ClusterableModel):
|
||||
"""The segment model."""
|
||||
STATUS_ENABLED = 'enabled'
|
||||
|
@ -121,8 +127,8 @@ class Segment(ClusterableModel):
|
|||
FieldPanel('randomisation_percent', classname='percent_field'),
|
||||
], heading="Segment"),
|
||||
MultiFieldPanel([
|
||||
InlinePanel(
|
||||
"{}s".format(rule_model._meta.db_table),
|
||||
RulePanel(
|
||||
"{}_related".format(rule_model._meta.db_table),
|
||||
label='{}{}'.format(
|
||||
rule_model._meta.verbose_name,
|
||||
' ({})'.format(_('Static compatible')) if rule_model.static else ''
|
||||
|
|
|
@ -1,5 +1,3 @@
|
|||
from __future__ import absolute_import, unicode_literals
|
||||
|
||||
import csv
|
||||
|
||||
from django import forms
|
||||
|
@ -87,7 +85,10 @@ class SegmentModelAdmin(ModelAdmin):
|
|||
'page_count', 'variant_count', 'statistics')
|
||||
index_view_extra_js = ['js/commons.js', 'js/index.js']
|
||||
index_view_extra_css = ['css/index.css']
|
||||
form_view_extra_js = ['js/commons.js', 'js/form.js']
|
||||
form_view_extra_js = ['js/commons.js', 'js/form.js',
|
||||
'js/segment_form_control.js',
|
||||
'wagtailadmin/js/page-chooser-modal.js',
|
||||
'wagtailadmin/js/page-chooser.js']
|
||||
form_view_extra_css = ['css/form.css']
|
||||
|
||||
def index_view(self, request):
|
||||
|
|
|
@ -1,5 +1,3 @@
|
|||
from __future__ import absolute_import, unicode_literals
|
||||
|
||||
import logging
|
||||
|
||||
from django.conf.urls import include, url
|
||||
|
@ -227,8 +225,7 @@ class PersonalisedPagesSummaryPanel(PagesSummaryItem):
|
|||
order = 2100
|
||||
|
||||
def render(self):
|
||||
page_count = models.PersonalisablePageMetadata.objects.filter(
|
||||
segment__isnull=True).count()
|
||||
page_count = models.PersonalisablePageMetadata.objects.filter(segment__isnull=True).count()
|
||||
title = _("Personalised Page")
|
||||
return mark_safe("""
|
||||
<li class="icon icon-fa-file-o">
|
||||
|
|
|
@ -1,5 +1,3 @@
|
|||
from __future__ import absolute_import, unicode_literals
|
||||
|
||||
import pytest
|
||||
|
||||
pytest_plugins = [
|
||||
|
@ -7,6 +5,11 @@ pytest_plugins = [
|
|||
]
|
||||
|
||||
|
||||
@pytest.fixture(autouse=True)
|
||||
def enable_db_access(db):
|
||||
pass
|
||||
|
||||
|
||||
@pytest.fixture(scope='session')
|
||||
def django_db_setup(django_db_setup, django_db_blocker):
|
||||
from wagtail.core.models import Page, Site
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
from __future__ import absolute_import, unicode_literals
|
||||
|
||||
import os
|
||||
from distutils.version import StrictVersion as V
|
||||
|
||||
import django
|
||||
|
||||
DATABASES = {
|
||||
'default': {
|
||||
|
@ -52,16 +53,27 @@ TEMPLATES = [
|
|||
},
|
||||
]
|
||||
|
||||
MIDDLEWARE = (
|
||||
'django.middleware.common.CommonMiddleware',
|
||||
'django.contrib.sessions.middleware.SessionMiddleware',
|
||||
'django.middleware.csrf.CsrfViewMiddleware',
|
||||
'django.contrib.auth.middleware.AuthenticationMiddleware',
|
||||
'django.contrib.messages.middleware.MessageMiddleware',
|
||||
'django.middleware.clickjacking.XFrameOptionsMiddleware',
|
||||
|
||||
'wagtail.core.middleware.SiteMiddleware',
|
||||
)
|
||||
def get_middleware_settings():
|
||||
return (
|
||||
'django.middleware.common.CommonMiddleware',
|
||||
'django.contrib.sessions.middleware.SessionMiddleware',
|
||||
'django.middleware.csrf.CsrfViewMiddleware',
|
||||
'django.contrib.auth.middleware.AuthenticationMiddleware',
|
||||
'django.contrib.auth.middleware.SessionAuthenticationMiddleware',
|
||||
'django.contrib.messages.middleware.MessageMiddleware',
|
||||
'django.middleware.clickjacking.XFrameOptionsMiddleware',
|
||||
|
||||
'wagtail.core.middleware.SiteMiddleware',
|
||||
)
|
||||
|
||||
|
||||
# Django 1.10 started to use "MIDDLEWARE" instead of "MIDDLEWARE_CLASSES".
|
||||
if V(django.get_version()) < V('1.10'):
|
||||
MIDDLEWARE_CLASSES = get_middleware_settings()
|
||||
else:
|
||||
MIDDLEWARE = get_middleware_settings()
|
||||
|
||||
|
||||
INSTALLED_APPS = (
|
||||
'wagtail_personalisation',
|
||||
|
|
|
@ -1,5 +1,3 @@
|
|||
from __future__ import absolute_import, unicode_literals
|
||||
|
||||
import datetime
|
||||
|
||||
import pytest
|
||||
|
@ -8,7 +6,7 @@ from django.db.models import ProtectedError
|
|||
from tests.factories.page import ContentPageFactory
|
||||
from tests.factories.segment import SegmentFactory
|
||||
from tests.site.pages import models
|
||||
from wagtail_personalisation.models import PersonalisablePageMetadata
|
||||
from wagtail_personalisation.models import PersonalisablePageMetadata, Segment
|
||||
from wagtail_personalisation.rules import TimeRule
|
||||
|
||||
|
||||
|
@ -73,3 +71,10 @@ def test_sitemap_generation_for_canonical_pages_is_enabled(segmented_page):
|
|||
def test_sitemap_generation_for_variants_is_disabled(segmented_page):
|
||||
assert not segmented_page.personalisation_metadata.is_canonical
|
||||
assert not segmented_page.get_sitemap_urls()
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_segment_edit_view(site, client, django_user_model):
|
||||
test_segment = Segment()
|
||||
new_panel = test_segment.panels[1].children[0].bind_to_model(Segment)
|
||||
assert new_panel.related.name == "wagtail_personalisation_timerules"
|
||||
|
|
|
@ -3,8 +3,14 @@ import pytest
|
|||
from django.test import override_settings
|
||||
|
||||
from tests.factories.page import ContentPageFactory
|
||||
from wagtail.core.models import Page as WagtailPage
|
||||
from wagtail_personalisation.utils import (
|
||||
can_delete_pages, get_client_ip, impersonate_other_page)
|
||||
can_delete_pages, get_client_ip, impersonate_other_page, exclude_variants)
|
||||
|
||||
|
||||
class Metadata:
|
||||
def __init__(self, is_canonical=True):
|
||||
self.is_canonical = is_canonical
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
|
@ -64,3 +70,54 @@ def test_get_client_ip_custom_get_client_ip_function_does_not_exist(rf):
|
|||
)
|
||||
def test_get_client_ip_custom_get_client_ip_used(rf):
|
||||
assert get_client_ip(rf.get('/')) == '123.123.123.123'
|
||||
|
||||
|
||||
def test_exclude_variants_with_pages_querysets():
|
||||
'''
|
||||
Test that excludes variant works for querysets
|
||||
'''
|
||||
for i in range(5):
|
||||
page = WagtailPage(path="/" + str(i), depth=0, url_path="/", title="Hoi " + str(i))
|
||||
page.save()
|
||||
pages = WagtailPage.objects.all().order_by('id')
|
||||
|
||||
result = exclude_variants(pages)
|
||||
assert type(result) == type(pages)
|
||||
assert result == pages
|
||||
|
||||
|
||||
def test_exclude_variants_with_pages_querysets_not_canonical():
|
||||
'''
|
||||
Test that excludes variant works for querysets with
|
||||
personalisation_metadata canonical False
|
||||
'''
|
||||
for i in range(5):
|
||||
page = WagtailPage(path="/" + str(i), depth=0, url_path="/", title="Hoi " + str(i))
|
||||
page.save()
|
||||
pages = WagtailPage.objects.all().order_by('id')
|
||||
# add variants
|
||||
for page in pages:
|
||||
page.personalisation_metadata = Metadata(is_canonical=False)
|
||||
page.save()
|
||||
|
||||
result = exclude_variants(pages)
|
||||
assert type(result) == type(pages)
|
||||
assert result.count() == 0
|
||||
|
||||
|
||||
def test_exclude_variants_with_pages_querysets_meta_none():
|
||||
'''
|
||||
Test that excludes variant works for querysets with meta as none
|
||||
'''
|
||||
for i in range(5):
|
||||
page = WagtailPage(path="/" + str(i), depth=0, url_path="/", title="Hoi " + str(i))
|
||||
page.save()
|
||||
pages = WagtailPage.objects.all().order_by('id')
|
||||
# add variants
|
||||
for page in pages:
|
||||
page.personalisation_metadata = None
|
||||
page.save()
|
||||
|
||||
result = exclude_variants(pages)
|
||||
assert type(result) == type(pages)
|
||||
assert result == pages
|
||||
|
|
6
tox.ini
6
tox.ini
|
@ -1,5 +1,5 @@
|
|||
[tox]
|
||||
envlist = py{36}-django{20}-wagtail{20,21}{,-geoip2},lint
|
||||
envlist = py{36}-django{111,20}-wagtail{20,21,22}{,-geoip2},lint
|
||||
|
||||
[testenv]
|
||||
basepython = python3.6
|
||||
|
@ -9,7 +9,9 @@ deps =
|
|||
django20: django>=2.0,<2.1
|
||||
wagtail20: wagtail>=2.0,<2.1
|
||||
wagtail21: wagtail>=2.1,<2.2
|
||||
wagtail22: wagtail>=2.2,<2.3
|
||||
geoip2: geoip2
|
||||
django111: django>=1.11,<1.12
|
||||
|
||||
[testenv:coverage-report]
|
||||
basepython = python3.6
|
||||
|
@ -21,7 +23,7 @@ commands =
|
|||
|
||||
[testenv:lint]
|
||||
basepython = python3.6
|
||||
deps = flake8
|
||||
deps = flake8==3.5.0
|
||||
commands =
|
||||
flake8 src tests setup.py
|
||||
isort -q --recursive --diff src/ tests/
|
||||
|
|
Reference in New Issue