[英]How to export ONLY selected records in django admin?
我正在使用https://github.com/bendavis78/django-admin-csv將記錄導出到csv。 但是,即使我只選擇了一些記錄,它也會下載所有記錄。
from admin_csv import CSVMixin
class MyModelAdmin(CSVMixin, admin.ModelAdmin):
list_display = ['foo', 'bar', 'baz']
csv_fields = list_display + ['qux']
這是admin.py文件
from functools import update_wrapper
from django.contrib.admin.utils import label_for_field
class CSVMixin(object):
"""
Adds a CSV export action to an admin view.
"""
change_list_template = "admin/change_list_csv.html"
# This is the maximum number of records that will be written.
# Exporting massive numbers of records should be done asynchronously.
csv_record_limit = None
csv_fields = []
csv_headers = {}
def get_csv_fields(self, request):
return self.csv_fields or self.list_display
def get_urls(self):
from django.conf.urls import url
def wrap(view):
def wrapper(*args, **kwargs):
return self.admin_site.admin_view(view)(*args, **kwargs)
return update_wrapper(wrapper, view)
opts = self.model._meta
urlname = '{0.app_label}_{0.model_name}_csvdownload'.format(opts)
urlpatterns = [
url('^csv/$', wrap(self.csv_export), name=urlname)
]
return urlpatterns + super(CSVMixin, self).get_urls()
def get_csv_filename(self, request):
return unicode(self.model._meta.verbose_name_plural)
def changelist_view(self, request, extra_context=None):
context = {
'querystring': request.GET.urlencode()
}
context.update(extra_context or {})
return super(CSVMixin, self).changelist_view(request, context)
def csv_header_for_field(self, field_name):
if self.headers.get(field_name):
return self.headers[field_name]
return label_for_field(field_name, self.model, self)
def csv_export(self, request, *args, **kwargs):
import csv
from django.http import HttpResponse
response = HttpResponse(content_type='text/csv')
response['Content-Disposition'] = (
'attachment; filename={0}.csv'.format(
self.get_csv_filename(request)))
fields = list(self.get_csv_fields(request))
writer = csv.DictWriter(response, fields)
# Write header row.
headers = dict((f, self.csv_header_for_field(f)) for f in fields)
writer.writerow(headers)
# Get the queryset using the changelist
cl_response = self.changelist_view(request)
cl = cl_response.context_data.get('cl')
queryset = cl.get_queryset(request)
# Write records.
if self.csv_record_limit:
queryset = queryset[:self.csv_record_limit]
for r in queryset:
data = {}
for name in fields:
if hasattr(r, name):
data[name] = getattr(r, name)
elif hasattr(self, name):
data[name] = getattr(self, name)(r)
else:
raise ValueError('Unknown field: {}'.format(name))
if callable(data[name]):
data[name] = data[name]()
writer.writerow(data)
return response
csv_export.short_description = \
'Exported selected %(verbose_name_plural)s as CSV'
這是change_list_csv.html。
{% extends "admin/change_list.html" %}
{% load admin_urls %}
{% block object-tools-items %}
{{ block.super }}
<li>
{% url cl.opts|admin_urlname:'csvdownload' as download_url %}
<a href="{{ download_url }}{% if querystring %}?{{ querystring }}{% endif %}" class="link">Download CSV</a>
</li>
{% endblock %}
該文件看上去很簡單,但是無法弄清楚要導出的內容僅導出所選行。
我認為問題是您的“ opts = self.model._meta”。 當我使用自定義admin動作導出到csv時,將使用以下代碼:opts = queryset.model._meta,而admin queryset會為我做限制。 您的代碼結構與我的代碼結構非常不同,因此我不知道您需要如何獲得與“ queryset”等效的代碼,但是我認為這是缺失或無法正常運行的原因。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.