How to return static files passing through a view in django?

前端 未结 8 1796
名媛妹妹
名媛妹妹 2020-12-09 09:04

I need to return css files and js files according to specific logic. Clearly, static serve does not perform what I need. I have a view, whose render method uses logic to fin

相关标签:
8条回答
  • 2020-12-09 09:49

    Serving files directly from a view is very slow. If you are looking for normal file serving see this question: Having Django serve downloadable files

    To very easily serve files through a view (for debug purposes, for example) keep reading.

    # In your urls.py:
    url(r'^test-files/(?P<name>.+)/$', views.test_files, name='test_files'),
    
    # In your views.py:
    from django.http.response import HttpResponse
    from django.views.decorators.csrf import csrf_exempt
    
    @csrf_exempt # (Allows file download with POST requests, can be omitted)
    def test_files(request, name):
        if name == "myxml":
            fsock = open("/djangopath/data/static/files/my.xml", "rb")
            return HttpResponse(fsock)
    

    This allows you to download the file from: http://127.0.0.1:8080/app/test-files/myxml/

    0 讨论(0)
  • 2020-12-09 09:54

    Why don't you use Django staticfiles inside your view

    from django.contrib.staticfiles.views import serve
    
    ...
    def view_function(request):
       return serve(request, 'absolute_path_to_file_name')
    
    0 讨论(0)
  • 2020-12-09 09:56

    What webserver software are you using?

    At least for Apache and NginX, there is a module enabling you to use the X-SendFile HTTP header. The NginX website says Lighty can do this, too.

    In your wrapper view:

    ...
    
    abspath = '/most_secret_directory_on_the_whole_filesystem/protected_filename.css'
    
    response = HttpResponse()
    response['X-Sendfile'] = abspath
    
    response['Content-Type'] = 'mimetype/submimetype'
    # or let your webserver auto-inject such a header field
    # after auto-recognition of mimetype based on filename extension
    
    response['Content-Length'] = <filesize>
    # can probably be left out if you don't want to hassle with getting it off disk.
    # oh, and:
    # if the file is stored via a models.FileField, you just need myfilefield.size
    
    response['Content-Disposition'] = 'attachment; filename=%s.css' \
        % 'whatever_public_filename_you_need_it_to_be'
    
    return response
    

    Then you can connect the view via http://mysite.com/url_path/to/serve_hidden_css_file/.

    You can use it anytime you need to do something upon a file being requested that should not be directly accessible to users, like limiting who can access it, or counting requests to it for stats, or whatever.

    For Apache: http://tn123.ath.cx/mod_xsendfile/
    For NginX: http://wiki.nginx.org/NginxXSendfile

    0 讨论(0)
  • 2020-12-09 09:56

    Pass an iterator (such as the result of open()) to the HttpResponse constructor.

    0 讨论(0)
  • 2020-12-09 09:56

    It should be wasteful to use django to serve static content (not to mention, several orders of magnitude slower).

    I'd rather convert the view into a context processor and use the variables in templates to find what blocks to include.

    0 讨论(0)
  • 2020-12-09 09:57

    This is what I used:

    test_file = open('/home/poop/serve/test.pdf', 'rb')
    response = HttpResponse(content=test_file)
    response['Content-Type'] = 'application/pdf'
    response['Content-Disposition'] = 'attachment; filename="%s.pdf"' \
                                      % 'whatever'
    return response
    
    0 讨论(0)
提交回复
热议问题