首页 > 解决方案 > Django - 即时创建 CSV 并将其保存到文件系统和模型文件字段

问题描述

在我的 django 应用程序中,我有一个管理命令,我想用它来处理一些数据并在文件系统中创建模型实例以及文件并将其路径保存到上述实例的文件字段。

我的管理命令:

import datetime
import timy
from django.core.management.base import BaseCommand
import tempfile
from core.models import Entry
from np_web.models import Dump
import calendar
import csv

class Command(BaseCommand):
    help = 'Create dump and file for current day'

    def handle(self, *args, **options):
        with timy.Timer() as timer:
            today = datetime.date.today()
            dump_title = '{}.{}.{}.csv'.format(today.day, today.month, today.year)

            entries = Entry.objects.all()

            dump = Dump.objects.create(all_entries=entries.count())
            dump.save()

            print('Dump created with uuid:', dump.uuid)
            print('Now create data file for dump')
            with tempfile.NamedTemporaryFile() as temp_csv:
                writer = csv.writer(temp_csv)
                writer.writerow([
                    'Column1',
                    'Column2',
                   ])
                for entry in entries:
                    writer.writerow([
                        entry.first_name,
                        entry.last_name
                    ])
            dump.file.save(dump_title, temp_csv)

我的转储模型:

class Dump(BaseModel):
    created = models.DateField(auto_now_add=True)
    all_entries = models.PositiveIntegerField()
    file = models.FileField(verbose_name=_('Attachment'), upload_to=dump_file_upload_path, max_length=2048,
                            storage=attachment_upload_storage, null=True, blank=True)

无论如何,它不起作用。它抛出一个错误:

TypeError: a bytes-like object is required, not 'str'

我也不确定使用临时文件是否是最好的解决方案。

标签: pythondjango

解决方案


一些评论希望能引导您找到解决方案。

对于初学者,“如果 delete 为 true(默认值),则文件一关闭就会被删除。” ,并假设您的间距是正确的,您将在尝试保存文件之前关闭文件。这将导致文件为空。

我的建议是像平常一样简单地创建文件,然后将其删除。一种简单的方法(尽管可能有更好的方法)是创建文件,保存它,然后删除原始(临时)副本。

此外,在保存文件时,您希望使用 Django 的 File wrapper 来保存它。

因此,您可以执行以下操作:

from django.core.files import File
import os

with open(temp, 'rb') as f:
    doc_file = File(f)
    dump.file.save("filename", doc_file, True)
    dump_file.save()

try:
    os.remove(temp)
except Expection:
    print('Unable to remove temp file')

推荐阅读