2016-07-07 15 views
6

Nie jest dla mnie jasne, kiedy używać send_file i kiedy send_from_directory.Kolba - Kiedy używać send_file/send_from_directory

Mam plik w folderze chronionym. Mogę uzyskać dostęp do pliku z obu metod. Może więc ktoś ma przykład, który wyjaśnia, która funkcja powinna być użyta.

@app.route('/sfile/<id>') 
def sfile(id=None): 

    try: 
     return send_file('protected/'+id, attachment_filename='python.jpg') 
    except: 
     return('') 

@app.route('/sdir/<path:filename>') 
def sdir(filename): 
    try: 
     return send_from_directory(
      os.path.join(app.instance_path, ''), 
      filename 
     ) 
    except: 
     return '' 

Odpowiedz

11

send_file to funkcja, która obsługuje wysyłanie plików do użytkownika. Nie ma sprawdzenia poprawności na wejściu, więc chętnie wysłałby też protected/../../../etc/passwd lub cokolwiek innego. W twoim konkretnym przypadku może nie działać, ale jeśli nie jesteś świadomy tego typu ataku, możesz wytworzyć niezabezpieczony kod.

send_from_directory sprawdza, czy żądany plik rzeczywiście pochodzi z określonego katalogu. W ten sposób powyższy atak nie zadziała.

Można więc używać send_file, gdy ścieżka wejściowa pliku jest zaufana. Oznacza to, że należy wykonać własne kontrole lub jeśli dane wejściowe są dostarczane przez użytkownika (na przykład my_file_paths = {"a": "path/to/a", ... }; send_file(my_file_paths[user_input]) byłoby w porządku) powinno być w porządku. Dla wspólnego przypadku send_from_directory jest funkcją pomocniczą, która przeprowadza odpowiednie kontrole bezpieczeństwa.

+0

wielkie dzięki za wyjaśnienie – Alex