16

所以,我正在努力实现我之前的问题的答案。

这是我的模型:

class Talk(models.Model):
  title        = models.CharField(max_length=200)
  mp3          = models.FileField(upload_to = u'talks/', max_length=200)

这是我的表格:

class TalkForm(forms.ModelForm):
  def clean(self):
    super(TalkForm, self).clean()
    cleaned_data = self.cleaned_data

    if u'mp3' in self.files:
      from mutagen.mp3 import MP3
      if hasattr(self.files['mp3'], 'temporary_file_path'):
        audio = MP3(self.files['mp3'].temporary_file_path())
      else:
        # What goes here?
        audio = None # setting to None for now
      ...
    return cleaned_data

  class Meta:
    model = Talk

Mutagen需要磁盘上的类似文件的对象或文件名(我认为) - 第一种情况(上传的文件大于内存中处理的文件的大小)工作正常,但我不知道如何处理InMemoryUploadedFile否则我得到. 我试过了:

# TypeError (coercing to Unicode: need string or buffer, InMemoryUploadedFile found)
audio = MP3(self.files['mp3'])

# TypeError (coercing to Unicode: need string or buffer, cStringIO.StringO found)
audio = MP3(self.files['mp3'].file)

# Hangs seemingly indefinitely on my test file (~800KB)
audio = MP3(self.files['mp3'].file.read())

诱变剂有什么问题,还是我做错了?

在拒绝回答之后

在我的课堂FILE_UPLOAD_HANDLERS上即时修改设置,如下所示:ModelAdmin

def add_view(self, request, form_url='', extra_context=None):
  request.upload_handlers = [TemporaryFileUploadHandler()]
  return super(TalkAdmin, self).add_view(request, form_url, extra_context)

当我点击提交时,得到以下错误 500:

处理上传后,您无法设置上传处理程序。

即使我尽可能早地这样做!

另外,我不确定我是否有save关于我要返回的对象的方法(我已经查看了dir(self.files['mp3'].file)and dir(self.files['mp3']))。

4

1 回答 1

30

您可以尝试以这种方式更改FILE_UPLOAD_HANDLERS,以便 Django 始终使用临时文件处理程序:

FILE_UPLOAD_HANDLERS默认:

("django.core.files.uploadhandler.MemoryFileUploadHandler",
 "django.core.files.uploadhandler.TemporaryFileUploadHandler",)

因此,您只能TemporaryFileUploadHandler通过覆盖 settings.py 中的设置来离开。

编辑:

简单得多,应该首先想到它:(:

from your.models import Talk
mp3 = self.files['mp3']
f = Talk.mp3.save('somename.mp3', mp3)
MP3(f.mp3.path)
>>> {'TRCK': TRCK(encoding=0, text=[u'5'])}

您可以通过这种方式保存InMemoryUploadedFile到磁盘,然后使用该文件的路径来处理mutagen.

编辑:

没有模型实例也是一样的。

import os

from django.core.files.storage import default_storage
from django.core.files.base import ContentFile
from django.conf import settings

from mutagen.mp3 import MP3

mp3 = request.FILES['mp3'] # or self.files['mp3'] in your form

path = default_storage.save('tmp/somename.mp3', ContentFile(mp3.read()))
MP3(os.path.join(settings.MEDIA_ROOT, path))

请注意,它将文件保存在 MEDIA_ROOT 中,当我尝试将其保存在其他任何地方时,我会得到SuspiciousOperation,因为您可以写入的位置有限制...您应该在检查后删除此文件,我猜,真正的东西会在您的模型...

path = default_storage.delete('tmp/somename.mp3')
于 2010-05-10T21:41:59.940 回答