2010-03-18 39 views
42

Tôi có một hình thức như:Đơn vị Kiểm tra một mẫu Django với một FileField

#forms.py 
from django import forms 

class MyForm(forms.Form): 
    title = forms.CharField() 
    file = forms.FileField() 


#tests.py 
from django.test import TestCase 
from forms import MyForm 

class FormTestCase(TestCase) 
    def test_form(self): 
     upload_file = open('path/to/file', 'r') 
     post_dict = {'title': 'Test Title'} 
     file_dict = {} #?????? 
     form = MyForm(post_dict, file_dict) 
     self.assertTrue(form.is_valid()) 

Làm thế nào để xây dựng file_dict để vượt qua upload_file mẫu?

Trả lời

68

Cho đến nay tôi đã tìm thấy con đường này mà làm việc

from django.core.files.uploadedfile import SimpleUploadedFile 
... 
def test_form(self): 
     upload_file = open('path/to/file', 'rb') 
     post_dict = {'title': 'Test Title'} 
     file_dict = {'file': SimpleUploadedFile(upload_file.name, upload_file.read())} 
     form = MyForm(post_dict, file_dict) 
     self.assertTrue(form.is_valid()) 
+1

Tùy thuộc vào mã tải lên của bạn, bạn có thể cần đặt thuộc tính 'content_type' của upload_file, quá –

+0

Vị trí content_type là một chuỗi như ''image/jpeg'' cho một tệp hình ảnh jpg chẳng hạn. – Medeiros

+0

Tôi nhận được 'TypeError: 'str' không hỗ trợ giao diện bộ đệm'. – Ariel

21

Có thể đây không phải là khá chính xác, nhưng tôi là tạo ra tập tin hình ảnh trong bài kiểm tra đơn vị sử dụng StringIO:

imgfile = StringIO('GIF87a\x01\x00\x01\x00\x80\x01\x00\x00\x00\x00ccc,\x00' 
        '\x00\x00\x00\x01\x00\x01\x00\x00\x02\x02D\x01\x00;') 
imgfile.name = 'test_img_file.gif' 

response = self.client.post(url, {'file': imgfile}) 
+2

Tôi đang cố gắng kiểm tra biểu mẫu riêng biệt với chế độ xem. Trên thực tế, tôi thậm chí không thực hiện quan điểm được nêu ra. –

+0

Ok, có vẻ như SimpleUploadedFile là giải pháp khá rõ ràng để thử nghiệm – dragoon

+7

+1 vì không phải sử dụng tệp bên ngoài – Khelben

2

Đây là một cách không yêu cầu bạn sử dụng hình ảnh thực.

from PIL import Image 
from StringIO import StringIO # Python 3: from io import StringIO 
from django.core.files.uploadedfile import InMemoryUploadedFile 

... 

def test_form(self): 
    im = Image.new(mode='RGB', size=(200, 200)) # create a new image using PIL 
    im_io = StringIO() # a StringIO object for saving image 
    im.save(im_io, 'JPEG') # save the image to im_io 
    im_io.seek(0) # seek to the beginning 

    image = InMemoryUploadedFile(
     im_io, None, 'random-name.jpg', 'image/jpeg', im_io.len, None 
    ) 

    post_dict = {'title': 'Test Title'} 
    file_dict = {'picture': image} 

    form = MyForm(data=post_dict, files=file_dict) 
+3

Hiện tại tồn tại tiếp theo nhưng: 'TypeError: đối số chuỗi được mong đợi, nhận 'byte''. Tôi đã giải quyết nó bằng cách sử dụng 'BytesIO' thay vì' StringIO', mà không sử dụng 'im_io.len' bởi vì một đối tượng' BytesIO' có thuộc tính chiều dài havent. – SalahAdDin

+0

@SalahAdDin Cảm ơn bạn đã đứng đầu. Tôi đã thử nghiệm đoạn mã trên trong Python 2.7 và nó hoạt động tốt. Bạn có thể vui lòng cho tôi biết phiên bản nào của Python và Django bạn đang sử dụng? Tôi muốn sửa mã ở trên cho người đọc trong tương lai. Cảm ơn. – xyres

+1

Tôi đang sử dụng 'django 1.9' và' python 3.5'. – SalahAdDin