- Author:
- blackrobot
- Posted:
- December 21, 2012
- Language:
- Python
- Version:
- 1.4
- Score:
- 2 (after 2 ratings)
Based on #2712
"This snippet creates a simple generic export to csv action that you can specify the fields you want exported and the labels used in the header row for each field. It expands on #2020 by using list comprehensions instead of sets so that you also control the order of the fields as well."
The additions here allow you to span foreign keys in the list of field names, and you can also reference callables.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 | import csv
from django.http import HttpResponse
def prep_field(obj, field):
""" Returns the field as a unicode string. If the field is a callable, it
attempts to call it first, without arguments.
"""
if '__' in field:
bits = field.split('__')
field = bits.pop()
for bit in bits:
obj = getattr(obj, bit, None)
if obj is None:
return ""
attr = getattr(obj, field)
output = attr() if callable(attr) else attr
return unicode(output).encode('utf-8') if output else ""
def export_csv_action(description="Export as CSV", fields=None, exclude=None, header=True):
""" This function returns an export csv action. """
def export_as_csv(modeladmin, request, queryset):
""" Generic csv export admin action.
Based on http://djangosnippets.org/snippets/2712/
"""
opts = modeladmin.model._meta
field_names = [field.name for field in opts.fields]
labels = []
if exclude:
field_names = [f for f in field_names if f not in exclude]
elif fields:
field_names = [field for field, _ in fields]
labels = [label for _, label in fields]
response = HttpResponse(mimetype='text/csv')
response['Content-Disposition'] = 'attachment; filename=%s.csv' % (
unicode(opts).replace('.', '_')
)
writer = csv.writer(response)
if header:
writer.writerow(labels if labels else field_names)
for obj in queryset:
writer.writerow([prep_field(obj, field) for field in field_names])
return response
export_as_csv.short_description = description
return export_as_csv
## Example Usage
from django.contrib import admin
class ExampleModelAdmin(admin.ModelAdmin):
raw_id_fields = ('field1',)
list_display = ('field1', 'field2', 'field3',)
actions = [
export_csv_action("Export Sepecial Report",
fields=[
('field1', 'label1'),
('foreign_key1__foreign_key2__name', 'label2'),
('field3', 'label3'),
],
header=True
),
]
admin.site.register(ExampleMode, ExampleModelAdmin)
|
More like this
- Template tag - list punctuation for a list of items by shapiromatron 9 months ago
- JSONRequestMiddleware adds a .json() method to your HttpRequests by cdcarter 9 months, 1 week ago
- Serializer factory with Django Rest Framework by julio 1 year, 4 months ago
- Image compression before saving the new model / work with JPG, PNG by Schleidens 1 year, 4 months ago
- Help text hyperlinks by sa2812 1 year, 5 months ago
Comments
Thanks. I've extended this to add support for writing all entries of many-to-many relationships as strings separated by a secondary delimiter. See here
#
Please login first before commenting.