mirror of
https://github.com/jazzband/django-admin2.git
synced 2026-04-19 06:11:06 +00:00
Merge pull request #458 from auvipy/up
start work to support 1.11 and 2.0
This commit is contained in:
commit
606118cb04
30 changed files with 85 additions and 63 deletions
3
.gitignore
vendored
3
.gitignore
vendored
|
|
@ -64,4 +64,5 @@ media
|
|||
# PyCharm
|
||||
.idea/
|
||||
|
||||
.cache
|
||||
.cache
|
||||
.pytest_cache
|
||||
22
.travis.yml
22
.travis.yml
|
|
@ -5,29 +5,25 @@ cache:
|
|||
- "~/.cache/pip"
|
||||
python:
|
||||
- '2.7'
|
||||
- '3.3'
|
||||
- '3.4'
|
||||
- '3.5'
|
||||
env:
|
||||
- DJANGO=1.8
|
||||
- DJANGO=1.9
|
||||
- DJANGO=2.0
|
||||
- DJANGO=1.10
|
||||
- DJANGO=1.11
|
||||
- DJANGO=master
|
||||
matrix:
|
||||
exclude:
|
||||
- python: '3.3'
|
||||
env: DJANGO=1.9
|
||||
- python: '3.3'
|
||||
env: DJANGO=1.10
|
||||
- python: '3.3'
|
||||
env: DJANGO=master
|
||||
allow_failures:
|
||||
- python: '2.7'
|
||||
env: DJANGO=master
|
||||
- python: '2.7'
|
||||
env: DJANGO=2.0
|
||||
allow_failures:
|
||||
- python: '3.5'
|
||||
env: DJANGO=master
|
||||
- python: '3.4'
|
||||
env: DJANGO=master
|
||||
- python: '3.5'
|
||||
env: DJANGO=master
|
||||
|
||||
install:
|
||||
- pip install tox
|
||||
script:
|
||||
|
|
@ -42,5 +38,5 @@ deploy:
|
|||
tags: true
|
||||
repo: jazzband/django-admin2
|
||||
# only do the PyPI release for exactly one scenario of the test matrix:
|
||||
condition: "$DJANGO = 1.9"
|
||||
condition: "$DJANGO = 1.11"
|
||||
python: 2.7
|
||||
|
|
|
|||
|
|
@ -4,7 +4,7 @@ from __future__ import division, absolute_import, unicode_literals
|
|||
from django.utils.encoding import force_str
|
||||
from rest_framework import fields, generics, serializers
|
||||
from rest_framework.response import Response
|
||||
from rest_framework.reverse import reverse
|
||||
from rest_framework.reverse import reverse as drf_reverse
|
||||
from rest_framework.views import APIView
|
||||
|
||||
from . import utils
|
||||
|
|
@ -76,7 +76,7 @@ class IndexAPIView(Admin2APIMixin, APIView):
|
|||
'app_label': model_options.app_label,
|
||||
'model_name': model_options.object_name.lower(),
|
||||
}
|
||||
model_url = reverse(
|
||||
model_url = drf_reverse(
|
||||
'%(current_app)s:%(app_label)s_%(model_name)s_api_list' % opts,
|
||||
request=self.request,
|
||||
format=self.kwargs.get('format'))
|
||||
|
|
|
|||
|
|
@ -10,5 +10,7 @@ class Djadmin2Config(AppConfig):
|
|||
verbose_name = _("Django Admin2")
|
||||
|
||||
def ready(self):
|
||||
post_migrate.connect(create_view_permissions,
|
||||
dispatch_uid="django-admin2.djadmin2.permissions.create_view_permissions")
|
||||
post_migrate.connect(
|
||||
create_view_permissions,
|
||||
dispatch_uid="django-admin2.djadmin2.permissions.create_view_permissions"
|
||||
)
|
||||
|
|
|
|||
|
|
@ -78,6 +78,7 @@ def _create_multiwidget(widget_class, copy_attributes=(), init_arguments=()):
|
|||
return multiwidget
|
||||
return create_new_multiwidget
|
||||
|
||||
|
||||
# this dictionary keeps a mapping from django's widget classes to a callable
|
||||
# that will accept an instance of this class. It will return a new instance of
|
||||
# a corresponding floppyforms widget, with the same semantics -- all relevant
|
||||
|
|
|
|||
|
|
@ -27,6 +27,7 @@ class ChoicesAsLinksWidget(django_widgets.Select):
|
|||
"""Select form widget taht renders links for choices
|
||||
instead of select element with options.
|
||||
"""
|
||||
|
||||
def render(self, name, value, attrs=None, choices=()):
|
||||
links = []
|
||||
for choice_value, choice_label in chain(self.choices, choices):
|
||||
|
|
@ -49,6 +50,7 @@ class NullBooleanLinksWidget(
|
|||
('3', ugettext_lazy('No')),
|
||||
]
|
||||
|
||||
|
||||
#: Maps `django_filter`'s field filters types to our
|
||||
#: custom form widget.
|
||||
FILTER_TYPE_TO_WIDGET = {
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@ from django.contrib.auth import authenticate
|
|||
from django.contrib.auth.forms import AuthenticationForm
|
||||
from django.contrib.auth.forms import UserCreationForm, UserChangeForm
|
||||
from django.core.exceptions import ValidationError
|
||||
from django.core.urlresolvers import reverse_lazy
|
||||
from django.urls import reverse_lazy
|
||||
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
|
||||
|
|
|
|||
|
|
@ -30,9 +30,11 @@ class LogEntry(models.Model):
|
|||
|
||||
action_time = models.DateTimeField(_('action time'), auto_now=True)
|
||||
user = models.ForeignKey(settings.AUTH_USER_MODEL,
|
||||
related_name='log_entries')
|
||||
related_name='log_entries',
|
||||
on_delete=models.CASCADE)
|
||||
content_type = models.ForeignKey(ContentType, blank=True, null=True,
|
||||
related_name='log_entries')
|
||||
related_name='log_entries',
|
||||
on_delete=models.CASCADE)
|
||||
object_id = models.TextField(_('object id'), blank=True, null=True)
|
||||
object_repr = models.CharField(_('object repr'), max_length=200)
|
||||
action_flag = models.PositiveSmallIntegerField(_('action flag'))
|
||||
|
|
|
|||
|
|
@ -1,8 +1,9 @@
|
|||
from django import forms
|
||||
from django.contrib.auth.models import User
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.test import TestCase
|
||||
from django.test.client import RequestFactory
|
||||
from django.urls import reverse
|
||||
|
||||
|
||||
from djadmin2.site import djadmin2_site
|
||||
from ..admin2 import UserAdmin2
|
||||
|
|
|
|||
|
|
@ -1,7 +1,9 @@
|
|||
from django.core.urlresolvers import reverse
|
||||
from django.test import TestCase, override_settings
|
||||
from django.urls import reverse
|
||||
|
||||
from django.utils.encoding import force_text
|
||||
|
||||
|
||||
from .. import views
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -12,6 +12,7 @@ from djadmin2.views import LoginView
|
|||
class CustomLoginView(LoginView):
|
||||
default_template_name = "custom_login_template.html"
|
||||
|
||||
|
||||
djadmin2_site.login_view = CustomLoginView
|
||||
djadmin2_site.autodiscover()
|
||||
|
||||
|
|
|
|||
|
|
@ -8,8 +8,8 @@ from collections import namedtuple
|
|||
|
||||
import extra_views
|
||||
from django.conf.urls import url
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.forms import modelform_factory
|
||||
from django.urls import reverse
|
||||
from django.utils.six import with_metaclass
|
||||
|
||||
from . import actions
|
||||
|
|
|
|||
|
|
@ -5,9 +5,9 @@ import os
|
|||
|
||||
from django.contrib.auth.views import redirect_to_login
|
||||
from django.core.exceptions import PermissionDenied
|
||||
from django.core.urlresolvers import reverse, reverse_lazy
|
||||
from django.forms.models import modelform_factory
|
||||
from django.http import HttpResponseRedirect
|
||||
from django.urls import reverse, reverse_lazy
|
||||
from django.utils.encoding import force_text
|
||||
from django.utils.text import get_text_list
|
||||
from django.utils.translation import ugettext as _
|
||||
|
|
|
|||
|
|
@ -13,7 +13,6 @@ from django.contrib.auth.forms import (PasswordChangeForm,
|
|||
from django.contrib.auth.views import (logout as auth_logout,
|
||||
login as auth_login)
|
||||
from django.contrib.contenttypes.models import ContentType
|
||||
from django.core.urlresolvers import reverse, reverse_lazy
|
||||
from django.db import models, router
|
||||
from django.db.models.fields import FieldDoesNotExist
|
||||
from django.http import HttpResponseRedirect
|
||||
|
|
@ -21,6 +20,8 @@ from django.shortcuts import get_object_or_404
|
|||
from django.utils.encoding import force_text
|
||||
from django.utils.text import capfirst
|
||||
from django.utils.translation import ugettext_lazy
|
||||
from django.urls import reverse, reverse_lazy
|
||||
|
||||
from django.views import generic
|
||||
|
||||
from . import permissions, utils
|
||||
|
|
|
|||
|
|
@ -8,7 +8,6 @@ from djadmin2 import permissions
|
|||
from djadmin2.actions import BaseListAction
|
||||
|
||||
|
||||
|
||||
class CustomPublishAction(BaseListAction):
|
||||
|
||||
permission_classes = BaseListAction.permission_classes + (
|
||||
|
|
@ -16,10 +15,12 @@ class CustomPublishAction(BaseListAction):
|
|||
)
|
||||
|
||||
description = ugettext_lazy('Publish selected items')
|
||||
success_message = pgettext_lazy('singular form',
|
||||
'Successfully published %(count)s %(items)s')
|
||||
success_message_plural = pgettext_lazy('plural form',
|
||||
'Successfully published %(count)s %(items)s')
|
||||
success_message = pgettext_lazy(
|
||||
'singular form',
|
||||
'Successfully published %(count)s %(items)s')
|
||||
success_message_plural = pgettext_lazy(
|
||||
'plural form',
|
||||
'Successfully published %(count)s %(items)s')
|
||||
|
||||
default_template_name = "actions/publish_selected_items.html"
|
||||
|
||||
|
|
@ -52,7 +53,9 @@ class PublishAllItemsAction(BaseListAction):
|
|||
|
||||
def unpublish_items(request, queryset):
|
||||
queryset.update(published=False)
|
||||
messages.add_message(request, messages.INFO, ugettext_lazy(u'Items unpublished'))
|
||||
messages.add_message(request, messages.INFO,
|
||||
ugettext_lazy(u'Items unpublished'))
|
||||
|
||||
|
||||
# Translators : action description
|
||||
unpublish_items.description = ugettext_lazy('Unpublish selected items')
|
||||
|
|
@ -66,5 +69,6 @@ def unpublish_all_items(request, queryset):
|
|||
ugettext_lazy('Items unpublished'),
|
||||
)
|
||||
|
||||
|
||||
unpublish_all_items.description = ugettext_lazy('Unpublish all items')
|
||||
unpublish_all_items.only_selected = False
|
||||
|
|
|
|||
|
|
@ -16,5 +16,6 @@ class PostAdmin(admin.ModelAdmin):
|
|||
list_filter = ['published', 'title']
|
||||
date_hierarchy = "published_date"
|
||||
|
||||
|
||||
admin.site.register(Post, PostAdmin)
|
||||
admin.site.register(Comment)
|
||||
|
|
|
|||
|
|
@ -32,7 +32,7 @@ class PostAdmin(ModelAdmin2):
|
|||
}
|
||||
save_on_top = True
|
||||
date_hierarchy = "published_date"
|
||||
ordering = ["-published_date", "title",]
|
||||
ordering = ["-published_date", "title", ]
|
||||
|
||||
|
||||
class CommentAdmin(ModelAdmin2):
|
||||
|
|
@ -42,6 +42,7 @@ class CommentAdmin(ModelAdmin2):
|
|||
actions_on_bottom = True
|
||||
actions_selection_counter = False
|
||||
|
||||
|
||||
# Register the blog app with a verbose name
|
||||
djadmin2_site.register_app_verbose_name(
|
||||
'blog',
|
||||
|
|
@ -51,4 +52,3 @@ djadmin2_site.register_app_verbose_name(
|
|||
# Register each model with the admin
|
||||
djadmin2_site.register(Post, PostAdmin)
|
||||
djadmin2_site.register(Comment, CommentAdmin)
|
||||
|
||||
|
|
|
|||
|
|
@ -25,7 +25,8 @@ class Post(models.Model):
|
|||
@python_2_unicode_compatible
|
||||
class Comment(models.Model):
|
||||
post = models.ForeignKey(
|
||||
Post, verbose_name=_('post'), related_name="comments")
|
||||
Post, verbose_name=_('post'), related_name="comments",
|
||||
on_delete=models.CASCADE)
|
||||
body = models.TextField(verbose_name=_('body'))
|
||||
|
||||
def __str__(self):
|
||||
|
|
@ -41,7 +42,7 @@ class Comment(models.Model):
|
|||
@python_2_unicode_compatible
|
||||
class Count(models.Model):
|
||||
num = models.PositiveSmallIntegerField()
|
||||
parent = models.ForeignKey('self', null=True)
|
||||
parent = models.ForeignKey('self', null=True, on_delete=models.CASCADE)
|
||||
|
||||
def __str__(self):
|
||||
return six.text_type(self.num)
|
||||
|
|
@ -52,11 +53,14 @@ class Event(models.Model):
|
|||
|
||||
|
||||
class Location(models.Model):
|
||||
event = models.OneToOneField(Event, verbose_name='awesome event')
|
||||
event = models.OneToOneField(
|
||||
Event, verbose_name='awesome event',
|
||||
on_delete=models.CASCADE
|
||||
)
|
||||
|
||||
|
||||
class Guest(models.Model):
|
||||
event = models.OneToOneField(Event)
|
||||
event = models.OneToOneField(Event, on_delete=models.CASCADE)
|
||||
name = models.CharField(max_length=255)
|
||||
|
||||
class Meta:
|
||||
|
|
|
|||
|
|
@ -4,9 +4,9 @@ import json
|
|||
|
||||
from django.contrib.auth.models import AnonymousUser, User
|
||||
from django.core.exceptions import PermissionDenied
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.test import TestCase
|
||||
from django.test.client import RequestFactory
|
||||
from django.urls import reverse
|
||||
from django.utils.encoding import force_text
|
||||
|
||||
from djadmin2 import apiviews
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
from django.contrib.auth.models import Group, User
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.urls import reverse
|
||||
|
||||
from .test_apiviews import APITestCase
|
||||
|
||||
|
|
|
|||
|
|
@ -2,9 +2,9 @@
|
|||
# vim:fenc=utf-8
|
||||
|
||||
import django_filters
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.test import TestCase
|
||||
from django.test.client import RequestFactory
|
||||
from django.urls import reverse
|
||||
|
||||
from djadmin2 import filters as djadmin2_filters
|
||||
from djadmin2.types import ModelAdmin2
|
||||
|
|
@ -20,7 +20,6 @@ class ListFilterBuilderTest(TestCase):
|
|||
class PostAdminSimple(ModelAdmin2):
|
||||
list_filter = ['published', ]
|
||||
|
||||
|
||||
class PostAdminWithFilterInstances(ModelAdmin2):
|
||||
list_filter = [
|
||||
django_filters.BooleanFilter(name='published'),
|
||||
|
|
@ -31,7 +30,6 @@ class ListFilterBuilderTest(TestCase):
|
|||
model = Post
|
||||
fields = ['published']
|
||||
|
||||
|
||||
class PostAdminWithFilterSetInst(ModelAdmin2):
|
||||
list_filter = FS
|
||||
|
||||
|
|
|
|||
|
|
@ -1,10 +1,10 @@
|
|||
from blog.models import Post
|
||||
from django.contrib.auth.models import User, Permission
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.shortcuts import get_object_or_404
|
||||
from django.template import Template, Context
|
||||
from django.test import TestCase
|
||||
from django.test.client import RequestFactory
|
||||
from django.urls import reverse
|
||||
|
||||
from djadmin2.permissions import TemplatePermissionChecker
|
||||
from djadmin2.site import djadmin2_site
|
||||
|
|
|
|||
|
|
@ -5,8 +5,8 @@ from datetime import datetime
|
|||
|
||||
from django.contrib.auth import get_user_model
|
||||
from django.contrib.auth.models import Group
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.test import TestCase, Client
|
||||
from django.urls import reverse
|
||||
from django.utils.encoding import force_text
|
||||
|
||||
from ..models import Post, Comment
|
||||
|
|
|
|||
|
|
@ -1,4 +1,3 @@
|
|||
#from django.shortcuts import render
|
||||
from django.views.generic import ListView, DetailView
|
||||
|
||||
from .models import Post
|
||||
|
|
|
|||
|
|
@ -49,7 +49,7 @@ INSTALLED_APPS = [
|
|||
'polls'
|
||||
]
|
||||
|
||||
MIDDLEWARE_CLASSES = [
|
||||
MIDDLEWARE = [
|
||||
'django.middleware.security.SecurityMiddleware',
|
||||
'django.contrib.sessions.middleware.SessionMiddleware',
|
||||
'django.middleware.locale.LocaleMiddleware',
|
||||
|
|
|
|||
|
|
@ -8,13 +8,17 @@ from django.contrib import admin
|
|||
|
||||
from djadmin2.site import djadmin2_site
|
||||
|
||||
admin.autodiscover()
|
||||
|
||||
djadmin2_site.autodiscover()
|
||||
|
||||
urlpatterns = [
|
||||
url(r'^admin2/', include(djadmin2_site.urls)),
|
||||
url(r'^admin/', include(admin.site.urls)),
|
||||
url(r'^blog/', BlogListView.as_view(template_name="blog/blog_list.html"), name='blog_list'),
|
||||
url(r'^blog/detail(?P<pk>\d+)/$', BlogDetailView.as_view(template_name="blog/blog_detail.html"), name='blog_detail'),
|
||||
url(r'^$', BlogListView.as_view(template_name="blog/home.html"), name='home'),
|
||||
url(r'^blog/', BlogListView.as_view(template_name="blog/blog_list.html"),
|
||||
name='blog_list'),
|
||||
url(r'^blog/detail(?P<pk>\d+)/$',
|
||||
BlogDetailView.as_view(template_name="blog/blog_detail.html"),
|
||||
name='blog_detail'),
|
||||
url(r'^$', BlogListView.as_view(template_name="blog/home.html"),
|
||||
name='home'),
|
||||
] + static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)
|
||||
|
|
|
|||
|
|
@ -30,7 +30,11 @@ class Poll(models.Model):
|
|||
|
||||
@python_2_unicode_compatible
|
||||
class Choice(models.Model):
|
||||
poll = models.ForeignKey(Poll, verbose_name=_('poll'))
|
||||
poll = models.ForeignKey(
|
||||
Poll,
|
||||
verbose_name=_('poll'),
|
||||
on_delete=models.CASCADE
|
||||
)
|
||||
choice_text = models.CharField(
|
||||
max_length=200, verbose_name=_('choice text'))
|
||||
votes = models.IntegerField(default=0, verbose_name=_('votes'))
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
django-extra-views==0.8.0
|
||||
django-braces>=1.3.0
|
||||
djangorestframework==3.5.3
|
||||
django-filter==1.0.0
|
||||
django-extra-views==0.11.0
|
||||
django-braces==1.13.0
|
||||
djangorestframework==3.8.2
|
||||
django-filter==1.1.0
|
||||
django-debug-toolbar>=1.5
|
||||
future>=0.15.2
|
||||
pytz>=2016.4
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
-rrequirements.txt
|
||||
flake8==2.5.4
|
||||
flake8>=2.5.4
|
||||
pytest
|
||||
pytest-django
|
||||
11
tox.ini
11
tox.ini
|
|
@ -6,10 +6,9 @@ exclude = migrations/*,docs/*
|
|||
|
||||
[tox]
|
||||
envlist =
|
||||
py27-{1.8,1.9,1.10,master},
|
||||
py33-{1.8},
|
||||
py34-{1.8,1.9,1.10,master},
|
||||
py35-{1.8,1.9,1.10,master},
|
||||
py27-{1.10,1.11},
|
||||
py34-{1.10,1.11,2.0},
|
||||
py35-{1.10,1.11,2.0,master},
|
||||
|
||||
[testenv]
|
||||
commands =
|
||||
|
|
@ -17,9 +16,9 @@ commands =
|
|||
py.test []
|
||||
deps =
|
||||
-rrequirements_test.txt
|
||||
1.8: Django>=1.8,<1.9
|
||||
1.9: Django>=1.9,<1.10
|
||||
1.10: Django>=1.10,<1.11
|
||||
1.11: Django>=1.11,<2.0
|
||||
2.0: Django>=2.0,<2.1
|
||||
master: https://github.com/django/django/tarball/master
|
||||
setenv=
|
||||
DJANGO_SETTINGS_MODULE = example.settings
|
||||
|
|
|
|||
Loading…
Reference in a new issue