2012-02-26 10 views
3

ユーザーが自分の指定したフォルダにファイルをアップロードできるようにするにはどうすればよいですか?私はdjangoファイル転送を使用しています。現在のところ、どのファイルをメディアに入れるか選択できるようになっていますが、それをどのユーザーのファイルに置いても、すべてのユーザーのメディアを見ることができます。ここにアップロード/ models.py:ユーザーのアップロードファイルの保護django

from django.db import models 
from django.contrib.auth.models import User, UserManager 

def uploadmodel_file_upload_to(instance, filename): 
    print 'instance.user.username = '+ str(instance.user.username) 
    return 'uploads/%s/%s' % (instance.user.username, filename) 

class UploadModel(models.Model): 
    user = models.ForeignKey('auth.user') 
    file = models.FileField(upload_to=uploadmodel_file_upload_to) 
+1

「現在、私に選択肢が与えられています」 "それ"?あなたには何がありますか? –

+0

"It"はユーザーです。フォーム上では、すべてのユーザーが選択できるドロップダウンフォームが表示されます。 – user784756

+0

"フォーム上では、私にドロップダウンフォームを与える"?本当に?このモデルにデフォルトのModelFormを使用しているということですか?もしそうなら、**これを表示する質問を**更新してください。そして。どのビュー機能が実行されていますか?これはデフォルトの管理ビューですか?またはあなたが書いたビュー機能? ** **すべての**情報を提供する** **の質問を更新してください。コメントを追加しないでください。 –

答えて

5

uploadmodel_file_upload_toが相対パスを返します。完全なパスを構築するために、djangoはsettings.MEDIA_ROOTの前に追加します。 MEDIA_ROOTは一般に読めるようになっています。

私たちはMEDIA_ROOTの外にファイルを保存します。 settings.pyにこのような何かを追加します。

import os.path 
PROJECT_ROOT=os.path.abspath(os.path.dirname(__file__)) 
PROTECTED_MEDIA_ROOT=os.path.join(PROJECT_ROOT, 'protected_uploads') 

今、あなたは絶対パスを返すためにuploadmodel_file_upload_toを更新することができます。

def uploadmodel_file_upload_to(instance, filename): 
    return '%s/%s/%s' % (settings.PROTECTED_MEDIA_ROOT, instance.user.username, 
     filename) 

を今すぐファイルは、プロジェクト/パス/ protected_uploads /に保存されていることを、私たちに必要な例えば、それを提供するためにビューを追加します。

import os 
import mimetypes 

from django import shortcuts 
from django import http 
from django.conf import settings 
from django.views.static import was_modified_since 
from django.utils.http import http_date 

from .models import * 

def serve_upload(request, upload_id): 
    upload = shortcuts.get_object_or_404(UploadModel, pk=upload_id) 
    fullpath = upload.file.path 

    if request.user != upload.user: 
     return http.HttpResponseForbidden() 

    statobj = os.stat(fullpath) 
    mimetype, encoding = mimetypes.guess_type(fullpath) 
    mimetype = mimetype or 'application/octet-stream' 
    if not was_modified_since(request.META.get('HTTP_IF_MODIFIED_SINCE'), 
           statobj.st_mtime, statobj.st_size): 
     return http.HttpResponseNotModified(mimetype=mimetype) 
    response = http.HttpResponse(open(fullpath, 'rb').read(), mimetype=mimetype) 
    response["Last-Modified"] = http_date(statobj.st_mtime) 
    response["Content-Length"] = statobj.st_size 
    if encoding: 
     response["Content-Encoding"] = encoding 
    return response 

そしてURL:

+0

キャッシュを使用している場合、メモリを使いたくない場合は、serve_upload呼び出しをキャッシュしないと便利です。 django.views.decorators.cacheからインポートnever_cache @never_cache def serve_upload ... – sogeking

関連する問題