Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Browse files

Enable the user to add custom fields in the admin

  • Loading branch information...
commit 24231cedc91826ff0c7bcf44949ee47be0626bc9 1 parent d420495
@jpic authored
View
26 admin_hack/__init__.py
@@ -1,4 +1,28 @@
from django.conf import settings
+from django.utils.translation import ugettext as _
+from django.core import urlresolvers
+from django import http
+
+def enable_custom_values(model, field_name=None):
+ #File "/srv/art/art_env/src/admin-hack/admin_hack/__init__.py", line 10, in enable_custom_values
+ #models.ForeignKey(model, null=True, blank=True).contribute_to_class(
+ #AttributeError: 'module' object has no attribute 'ForeignKey'
+ from django.db import models
+
+ if field_name is None:
+ field_name = model._meta.module_name.lower()
+
+ models.ForeignKey(model, null=True, blank=True).contribute_to_class(
+ models.get_model('admin_hack', 'CustomValue'), field_name)
+
+def admin_export(modeladmin, request, queryset):
+ url = urlresolvers.reverse('admin_hack_export')
+ url += '?app=%s&model=%s' % (queryset.model._meta.app_label,
+ queryset.model._meta.module_name)
+ for item in queryset:
+ url += '&pk=%s' % (item.pk)
+ return http.HttpResponseRedirect(url)
+admin_export.short_description = _(u'Export selected items to CSV')
def patch_admin(site, admin_hack_prefix='/admin_hack/'):
for model, options in site._registry.items():
@@ -9,3 +33,5 @@ def patch_admin(site, admin_hack_prefix='/admin_hack/'):
'all': [settings.STATIC_URL + '/admin_hack/style.css']
})
options.__class__.media = media
+
+ options.__class__.actions.append(admin_export)
View
4 admin_hack/admin.py
@@ -3,6 +3,10 @@
from models import *
from forms import *
+class CustomValueInline(admin.TabularInline):
+ model = CustomValue
+ template = 'admin_hack/customvalue_tabularinline.html'
+
class FieldInline(admin.TabularInline):
model = Field
extra = 0
View
51 admin_hack/models.py
@@ -1,9 +1,53 @@
+from django.core import urlresolvers
from django.contrib import admin
from django.db import models
from django.utils.translation import ugettext as _
from django.db.models import signals
+
+from autoslug import AutoSlugField
from annoying.fields import AutoOneToOneField
+KIND_CHOICES = (
+ ('float', _('number')),
+ ('char', _('short text')),
+ ('text', _('text')),
+ ('datetime', _('date and time')),
+ ('date', _('date only')),
+ ('time', _('time only')),
+ ('image', _('image')),
+ ('file', _('file')),
+)
+
+class CustomValue(models.Model):
+ name = models.CharField(max_length=100)
+ slug = AutoSlugField(populate_from='name')
+
+ kind = models.CharField(choices=KIND_CHOICES, max_length=10)
+
+ float_value = models.FloatField(null=True, blank=True)
+ char_value = models.CharField(max_length=255, null=True, blank=True)
+ text_value = models.TextField(null=True, blank=True)
+ datetime_value = models.DateTimeField(null=True, blank=True)
+ date_value = models.DateField(null=True, blank=True)
+ time_value = models.TimeField(null=True, blank=True)
+ image_value = models.ImageField(null=True, blank=True,
+ upload_to='custom_value_images')
+ file_value = models.FileField(null=True, blank=True,
+ upload_to='custom_value_files')
+
+ @property
+ def value(self):
+ for k, v in KIND_CHOICES:
+ val = getattr(self, k + '_value', None)
+ if val is not None:
+ return val
+
+ def __unicode__(self):
+ return self.value
+
+ class Meta:
+ ordering = ('name',)
+
class AdminHackUserProfile(models.Model):
user = AutoOneToOneField('auth.user', primary_key=True)
forms = models.ManyToManyField('Form', null=True, blank=True)
@@ -33,6 +77,10 @@ class Meta:
('name', 'contenttype'),
)
+ def get_absolute_url(self):
+ return urlresolvers.reverse('admin:admin_hack_form_change',
+ args=(self.pk,))
+
def to_dict(self):
return {
'name': self.name,
@@ -40,7 +88,8 @@ def to_dict(self):
'contenttype': {
'pk': self.contenttype.pk,
},
- 'field_set': [f.to_dict() for f in self.field_set.all()]
+ 'field_set': [f.to_dict() for f in self.field_set.all()],
+ 'absolute_url': self.get_absolute_url(),
}
class Field(models.Model):
View
5 admin_hack/templates/admin_hack/hack.js
@@ -158,7 +158,7 @@
}
var html = [
- '<select id="_preset_change" style="display:inline">',
+ '<select id="_preset_change" style="display:inline; vertical-align: top;">',
];
for (var i in this.forms) {
html.push('<option value="' + this.forms[i].pk + '">');
@@ -173,7 +173,8 @@
var user_profile = new UserProfile({{ request.user.adminhackuserprofile.to_dict|as_json }});
var change_view = new ChangeView({{ forms_dict|as_json }});
- change_view.installSelect($('#content-main'), user_profile);
+ var main = $('#content-main')
+ change_view.installSelect(main, user_profile);
{% if last_form_pk %}
change_view.select.val({{ last_form_pk }});
change_view.select.trigger('change');
View
5 admin_hack/urls.py
@@ -12,6 +12,11 @@
name='admin_hack_js_hack'
),
url(
+ r'^export/$',
+ views.ExportView.as_view(),
+ name='admin_hack_export',
+ ),
+ url(
r'^userprofile/(?P<pk>[0-9]+)/update/$',
csrf_exempt(views.AdminHackUserProfileUpdateView.as_view()),
name='admin_hack_user_profile_update',
View
13 admin_hack/views.py
@@ -24,6 +24,19 @@ def form_valid(self, form):
def form_invalid(self, form):
return http.HttpResponse(form.errors, status=500)
+class ExportView(generic.TemplateView):
+ template_name = 'admin_hack/export.html'
+
+ def get_context_data(self, **kwargs):
+ self.model = get_model(request.GET.get('app'), request.GET.get('model'))
+ self.queryset = self.model.objects.filter(
+ pk__in=self.request.GET.get('pk'))
+
+ return {
+ 'model': self.model,
+ 'queryset': self.queryset,
+ }
+
class JsHackView(generic.TemplateView):
template_name = 'admin_hack/hack.js'
View
1  setup.py
@@ -21,5 +21,6 @@
'django_mptt (==0.5)',
'django_admin_tools (==0.4.0)',
'django_annoying',
+ 'django_autoslug',
]
)
Please sign in to comment.
Something went wrong with that request. Please try again.