【问题标题】:What is the correct way to simulate filedata for testing a form?模拟文件数据以测试表单的正确方法是什么?
【发布时间】:2012-05-04 21:05:47
【问题描述】:

我正在尝试测试一个自写的 FormField AudioFileFormField,它会在存储文件之前检查文件是否为音频文件。为此,我已经覆盖了 to_python 方法。尝试测试这个 FormField 我遇到了一些困难。

到目前为止,这是我的测试用例:

from django import forms
from django.core.files.uploadedfile import SimpleUploadedFile
from django.test import TestCase

class TestAudioFileFormField(TestCase):
    """ test the formfield to use for AudioFile Uploads """

    class TestForm(forms.Form):
        audiofilefield = AudioFileFormField()


    def setUp(self):

        self.AUDIOFILE_TEST_ROOT = os.path.dirname(__file__) + '/data/'
        self.files = audiofile_files


    def test_to_python(self):
        """ assign some files to a form and validate the form """

        f = file(self.AUDIOFILE_TEST_ROOT + self.files[0]) 
        file_data = {'audiofilefield':SimpleUploadedFile( self.files[0],f.read() )}
        data = {}

        form = self.TestForm(data,f)
        form.is_valid()

form.is_valid() 行引发 AttributeError: 'file' object has no attribute 'get'

当我在 form.is_valid() 之前插入调试跟踪时,这就是我在该交互式会话中得到的:

ipdb> form.is_valid()
AttributeError: 'file' object has no attribute 'get'
ipdb> suf = file_data['audiofilefield']
ipdb> suf
<SimpleUploadedFile: invalid_format.mp3 (text/plain)>
ipdb> dir(suf)
[lots of info here]
ipdb> form.is_valid()
True

我在交互式会话中究竟做了什么更改,以便表单验证正常工作?将文件传递给 SimpleUploadedFile 以避免 AttributeError 的正确方法是什么?

【问题讨论】:

    标签: django django-forms django-file-upload


    【解决方案1】:

    好的,焕然一新的外观很值得。这是我的新 test_to_python 测试,这次成功了:

    def test_to_python(self):
        f = file(self.AUDIOFILE_TEST_ROOT + self.files[0])
        file_data = {'audiofilefield':SimpleUploadedFile(self.files[0],f.read())}
        data = {}
        form = self.TestForm(data,file_data)
        self.assertTrue( form.is_valid() )
    

    【讨论】:

    • 您不觉得这会污染您的upload/ 目录吗?
    【解决方案2】:

    替代解决方案(因为这个问题是“Django 测试模拟上传”的最高 Google 结果):Django 的内置测试客户端接受打开的文件对象作为 POST 数据:

    # the form
    class TestForm(forms.Form):
        audiofilefield = AudioFileFormField()
    
    # the view
    def upload_view(request):
        form = TestForm(data=request.POST or None, files=request.FILES or None)
        if request.method == 'POST':
             if form.is_valid():
                  return HttpResponse('success')
             else:
                  return HttpResponse('fail')
    
    # the test function
    class UploadTest(TestCase):
        def test_upload(self):
            c = Client() # django.test.client.Client
            formdata = {}
            with open('/my/audiofile.mp3', 'rb') as f:
                formdata['audiofilefield'] = f
                response = c.post('/my-test-view/', formdata)
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2016-12-18
      • 1970-01-01
      • 2020-04-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-01-12
      相关资源
      最近更新 更多