class UploadView(View):
@csrf_exempt
def dispatch(self, *args, **kwargs):
return super(UploadView, self).dispatch(*args, **kwargs)
def post(self, request, *args, **kwargs):
"""A POST request. Validate the form and then handle the upload
based ont the POSTed data. Does not handle extra parameters yet.
"""
form = UploadFileForm(request.POST, request.FILES)
if form.is_valid():
handle_upload(request.FILES['qqfile'], form.cleaned_data)
return make_response(content=json.dumps({ 'success': True }))
else:
return make_response(status=400,
content=json.dumps({
'success': False,
'error': '%s' % repr(form.errors)
}))
def delete(self, request, *args, **kwargs):
"""A DELETE request. If found, deletes a file with the corresponding
UUID from the server's filesystem.
"""
qquuid = kwargs.get('qquuid', '')
if qquuid:
try:
handle_deleted_file(qquuid)
return make_response(content=json.dumps({ 'success': True }))
except Exception, e:
return make_response(status=400,
content=json.dumps({
'success': False,
'error': '%s' % repr(e)
}))
return make_response(status=404,
content=json.dumps({
'success': False,
'error': 'File not present'
}))
forms.py
class UploadFileForm(forms.Form):
""" This form represents a basic request from Fine Uploader.
The required fields will **always** be sent, the other fields are optional
based on your setup.
Edit this if you want to add custom parameters in the body of the POST
request.
"""
qqfile = forms.FileField()
qquuid = forms.CharField()
qqfilename = forms.CharField()
qqpartindex = forms.IntegerField(required=False)
qqchunksize = forms.IntegerField(required=False)
qqpartbyteoffset = forms.IntegerField(required=False)
qqtotalfilesize = forms.IntegerField(required=False)
qqtotalparts = forms.IntegerField(required=False)
# -*- coding: utf-8 -*-
from django.shortcuts import render_to_response
from django.template import RequestContext
from django.http import HttpResponseRedirect
from django.core.urlresolvers import reverse
from myproject.myapp.models import Document
from myproject.myapp.forms import DocumentForm
def list(request):
# Handle file upload
if request.method == 'POST':
form = DocumentForm(request.POST, request.FILES)
if form.is_valid():
newdoc = Document(docfile = request.FILES['docfile'])
newdoc.save()
# Redirect to the document list after POST
return HttpResponseRedirect(reverse('myapp.views.list'))
else:
form = DocumentForm() # A empty, unbound form
# Load documents for the list page
documents = Document.objects.all()
# Render list page with the documents and the form
return render_to_response(
'myapp/list.html',
{'documents': documents, 'form': form},
context_instance=RequestContext(request)
)
for key, file in request.FILES.items():
path = file.name
dest = open(path, 'w')
if file.multiple_chunks:
for c in file.chunks():
dest.write(c)
else:
dest.write(file.read())
dest.close()
...<other imports>...
from django.conf import settings
from django.conf.urls.static import static
from uploader import views as uploader_views
urlpatterns = [
...<other url patterns>...
path('', uploader_views.home, name='imageupload'),
]+ static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)
5.更新models.py
更新 uploader/models.py ::
from django.db import models
from django.forms import ModelForm
class Upload(models.Model):
pic = models.FileField(upload_to="images/")
upload_date=models.DateTimeField(auto_now_add =True)
# FileUpload form class.
class UploadForm(ModelForm):
class Meta:
model = Upload
fields = ('pic',)
6.更新views.py
更新 uploader/views.py ::
from django.shortcuts import render
from uploader.models import UploadForm,Upload
from django.http import HttpResponseRedirect
from django.urls import reverse
# Create your views here.
def home(request):
if request.method=="POST":
img = UploadForm(request.POST, request.FILES)
if img.is_valid():
img.save()
return HttpResponseRedirect(reverse('imageupload'))
else:
img=UploadForm()
images=Upload.objects.all().order_by('-upload_date')
return render(request,'home.html',{'form':img,'images':images})
# models
class Document(models.Model):
docfile = models.FileField(upload_to='documents/Temp/%Y/%m/%d')
def doc_name(self):
return self.docfile.name.split('/')[-1] # only the name, not full path
# admin
from myapp.models import Document
class DocumentAdmin(admin.ModelAdmin):
list_display = ('doc_name',)
admin.site.register(Document, DocumentAdmin)
10 回答
在这里它可以帮助您:在models.py中创建一个文件字段
要上传文件(在您的admin.py中):
并在模板中使用该字段 .
您可以参考具有django版本的Fine Uploader中的服务器示例 . https://github.com/FineUploader/server-examples/tree/master/python/django-fine-uploader
它非常优雅,最重要的是,它提供了特色的js lib . 模板不包含在服务器示例中,但您可以在其网站上找到演示 . 精细上传者:http://fineuploader.com/demos.html
django-fine-uploader
views.py
UploadView将发布和删除请求分派给各个处理程序 .
forms.py
Phew,Django文档确实没有这方面的好例子 . 我花了两个多小时来挖掘所有碎片,以了解它是如何工作的 . 凭借这些知识,我实现了一个项目,可以上传文件并将其显示为列表 . 要下载项目的源代码,请访问https://github.com/axelpale/minimal-django-file-upload-example或克隆它:
Update 2013-01-30: 除了1.3之外,GitHub的源代码还实现了Django 1.4 . 即使几乎没有变化,下面的教程对1.4也很有用 .
Update 2013-05-10: 在GitHub上实现Django 1.5 . urls.py中重定向的微小更改以及list.html中url模板标记的使用 . 感谢hubert3的努力 .
Update 2013-12-07: GangHub支持Django 1.6 . myapp / urls.py中的一个导入已更改 . 谢谢你到Arthedian .
Update 2015-03-17: GangHub支持Django 1.7,感谢aronysidoro .
Update 2015-09-04: GangHub支持Django 1.8,感谢nerogit .
Update 2016-07-03: GangHub支持Django 1.9,感谢daavve和nerogit
项目树
一个基本的Django 1.3项目,包含单个应用程序和上传媒体/目录 .
1.设置:myproject / settings.py
要上传和提供文件,您需要指定Django存储上传文件的位置以及Django为其提供的URL . MEDIA_ROOT和MEDIA_URL默认情况下在settings.py中,但它们是空的 . 有关详细信息,请参阅Django Managing Files中的第一行 . 记住还要设置数据库并将myapp添加到INSTALLED_APPS
2.型号:myproject / myapp / models.py
接下来,您需要一个带有FileField的模型 . 该特定字段存储文件,例如至媒体/文件/ 2011/12/24 /基于当前日期和MEDIA_ROOT . 见FileField reference .
3.表格:myproject / myapp / forms.py
要很好地处理上传,您需要一个表单 . 这个表单只有一个字段,但这就足够了 . 有关详细信息,请参阅Form FileField reference .
4.查看:myproject / myapp / views.py
所有魔法发生的视图 . 注意如何处理
request.FILES
. 对我来说,很难发现request.FILES['docfile']
可以保存到models.FileField这样的事实 . 模型的save()自动处理文件存储到文件系统 .5.项目网址:myproject / urls.py
Django默认不提供MEDIA_ROOT . 这在 生产环境 环境中会很危险 . 但在发展阶段,我们可以做空 . 注意最后一行 . 该行使Django能够从MEDIA_URL提供文件 . 这仅适用于开发阶段 .
有关详细信息,请参阅django.conf.urls.static.static reference . 另见this discussion about serving media files .
6.应用网址:myproject / myapp / urls.py
要使视图可访问,您必须为其指定URL . 这里没什么特别的 .
7.模板:myproject / myapp / templates / myapp / list.html
最后一部分:列表模板和下面的上传表单 . 表单必须将enctype-attribute设置为"multipart/form-data",方法设置为"post"才能使上传到Django . 有关详细信息,请参阅File Uploads documentation .
FileField有许多可以在模板中使用的属性 . 例如 . 模板中的{}和{} . 在Using files in models article和The File object documentation中查看有关这些内容的更多信息 .
8.初始化
只需运行syncdb和runserver .
结果
最后,一切准备就绪 . 在默认的Django开发环境中,可以在
localhost:8000/list/
查看上载文档的列表 . 今天,文件上传到/ path / to / myproject / media / documents / 2011/12/17 /,可以从列表中打开 .我希望这个答案可以帮助我,就像它会帮助我一样 .
我必须说我发现django的文档令人困惑 . 另外,对于最简单的例子,为什么要提到表格?我在views.py中工作的例子是: -
html文件看起来像下面的代码,虽然这个例子只上传一个文件,保存文件的代码处理很多:
这些例子不是我的代码,它们来自我发现的另外两个例子 . 我是django的初学者,所以很可能是我遗漏了一些关键点 .
在Henry's example上扩展:
您可以使用上载的文件对象从视图中调用此
handle_uploaded_file
函数 . 这将在文件系统中使用唯一名称(带有原始上载文件的文件名)保存文件,并返回已保存文件的完整路径 . 您可以将路径保存在数据库中,稍后对该文件执行某些操作 .演示
更新Akseli Palén's answer . 看github repo,适用于Django 2
最小的Django文件上传示例
1.创建一个django项目
运行startproject ::
现在创建了一个文件夹( sample )::
2.创建一个应用程序
创建一个应用::
现在创建了一个包含这些文件的文件夹(
uploader
)::3.更新settings.py
在
sample/settings.py
上添加'uploader.apps.UploaderConfig'
到INSTALLED_APPS
并添加MEDIA_ROOT
和MEDIA_URL
,即::4.更新urls.py
在
sample/urls.py
添加::5.更新models.py
更新
uploader/models.py
::6.更新views.py
更新
uploader/views.py
::7.创建模板
在文件夹 uploader 中创建一个文件夹 templates ,然后创建一个文件 home.html ,即
sample/uploader/templates/home.html
::8. Syncronize数据库
Syncronize数据库和runserver ::
访问http://localhost.com:8000
我也有类似的要求 . 网上的大多数例子都要求创建模型并创建我不想使用的表单 . 这是我的最终代码 .
并在HTML上传我写道:
以下是显示文件内容的HTML:
不确定这种方法是否有任何缺点,但在views.py中更为简单:
一般来说,当你试图“只是得到一个有效的例子”时,最好“开始编写代码” . 这里没有任何代码可以帮助您,因此它可以让我们更多地回答这个问题 .
如果你想获取一个文件,你需要在html文件中的某个地方:
这将为您提供浏览按钮,上传按钮以启动操作(提交表单)并记下enctype,以便Django知道给你
request.FILES
在某个视图中,您可以使用以下方式访问该文件
file upload docs中有大量信息
我建议你彻底阅读页面,然后开始编写代码 - 然后在不起作用时返回示例和堆栈跟踪 .
我遇到了类似的问题,并由django管理站点解决 .