POST多部分请求的低级读取?

时间:2013-02-05 21:02:41

标签: python django

我有一个例子,我正在尝试创建,最好使用Django(或其他类似的框架),将立即压缩上传的内容chunk-by-chunk成一种奇怪的压缩格式(无论是LZMA,7zip等) 。)然后写入另一个上传请求到S3。

基本上,这就是将要发生的事情:

  1. 用户通过^/upload/?$启动分段上传到我的终端。
  2. 当服务器收到块(可能是1024字节或其他一些数字)时,它们会以块的形式通过压缩算法。
  3. 压缩输出通过线路写入S3存储桶。
  4. 第3步是可选的;我可以在本地存储文件,并有一个消息队列以延迟的方式执行上传。

    第二步是否可以使用像Django这样的框架?是否有一种低级方式来访问类文件对象中的传入数据?

1 个答案:

答案 0 :(得分:0)

Django Request对象提供file-like interface,因此您可以从中传输数据。但是,由于Django总是将整个Request读入内存(如果文件上传太大,则读取临时文件),您只能在收到整个请求后使用此API。如果您的临时存储目录足够大并且您不介意缓冲服务器上的数据,则无需执行任何特殊操作。只需将数据上传到视图内的S3即可。但要注意超时。如果上传到S3的时间过长,浏览器将收到超时。因此,我建议将临时文件移动到更永久的目录,并通过Celery等工作队列启动上传。


如果您想通过服务器直接从客户端流式传输到Amazon S3,我建议您使用gevent。使用gevent,您可以编写一个简单的greenlet,从queue读取并写入S3。此队列由原始greenlet填充,该greenlet从请求中读取。

您可以使用http://upload.example.com/这样的特殊上传网址来部署该特殊服务器。如果你设置DJANGO_SETTINGS_MODULE环境变量并处理中间件通常为你做的一些事情(db connect / disconnect,事务开始/提交/回滚,会话处理等),可以在Django框架之外使用Django函数。

甚至可以在同一个WSGI容器中一起运行自定义WSGI应用程序和Django。只需包装Django WSGI应用程序并拦截/upload/请求。在这种情况下,我建议将gunicorngevent worker-class一起用作服务器。


我对Amazon S3 API不太熟悉,但据我所知,您还可以直接从用户生成用于文件上传的临时令牌。这样,您根本不需要通过服务器隧道传输数据。

编辑:您确实可以允许匿名上传到您的存储分区。请参阅此问题,该问题涉及此主题:S3 - Anonymous Upload - Key prefix