使用BOTO库在Django中将图像文件上传到Amazon S3时出现TypeError
我刚开始学习编程和Django,所以希望能得到一些适合初学者的帮助!
我在跟着一个教程,学习如何使用Boto库将图片上传到亚马逊的S3账户,但我觉得这个教程是针对旧版本的Django(我用的是1.1.2和Python 2.65),所以有些地方变了。我遇到了一个错误: 异常类型:TypeError 异常信息:'InMemoryUploadedFile'对象不可下标访问
我的代码是:
Models.py:
from django.db import models
from django.contrib.auth.models import User
from django import forms
from datetime import datetime
class PhotoUrl(models.Model):
url = models.CharField(max_length=128)
uploaded = models.DateTimeField()
def save(self):
self.uploaded = datetime.now()
models.Model.save(self)
views.py:
import mimetypes
from django.http import HttpResponseRedirect
from django.shortcuts import render_to_response
from django.core.urlresolvers import reverse
from django import forms
from django.conf import settings
from boto.s3.connection import S3Connection
from boto.s3.key import Key
def awsdemo(request):
def store_in_s3(filename, content):
conn = S3Connection(settings.AWS_ACCESS_KEY_ID, settings.AWS_SECRET_ACCESS_KEY)
b = conn.create_bucket('almacmillan-hark')
mime = mimetypes.guess_type(filename)[0]
k = Key(b)
k.key = filename
k.set_metadata("Content-Type", mime)
k.set_contents_from_strong(content)
k.set_acl("public-read")
photos = PhotoUrl.objects.all().order_by("-uploaded")
if not request.method == "POST":
f = UploadForm()
return render_to_response('awsdemo.html', {'form':f, 'photos':photos})
f = UploadForm(request.POST, request.FILES)
if not f.is_valid():
return render_to_response('awsdemo.html', {'form':f, 'photos':photos})
file = request.FILES['file']
filename = file.name
content = file['content']
store_in_s3(filename, content)
p = PhotoUrl(url="http://almacmillan-hark.s3.amazonaws.com/" + filename)
p.save()
photos = PhotoUrl.objects.all().order_by("-uploaded")
return render_to_response('awsdemo.html', {'form':f, 'photos':photos})
urls.py:
(r'^awsdemo/$', 'harkproject.s3app.views.awsdemo'),
awsdemo.html:
<div class="form">
<strong>{{form.file.label}}</strong>
<form method="POST" action ="." enctype="multipart/form-data">
{{form.file}}<br/>
<input type="submit" value="Upload">
</form>
</div>
我真的很希望能得到帮助。希望我提供的代码足够了。
祝好,
AL
2 个回答
0
你有没有试过 Django Storages 呢?这样的话,你只需要指定一个存储后端(在这个例子中是s3boto),要么把它设为默认的存储后端,要么在FileField或ImageField类中作为参数提供。
8
我觉得你的问题出在这一行:
content = file['content']
根据Django文档的说明:
FILES中的每个值都是一个UploadedFile对象,包含以下属性:
- read(num_bytes=None) -- 从文件中读取指定数量的字节。
- name -- 上传文件的名称。
- size -- 上传文件的大小,以字节为单位。
- chunks(chunk_size=None) -- 一个生成器,按顺序提供数据块。
试试这个:
content = file.read()