web-dev-qa-db-de.com

Django [Errno 13] Berechtigung abgelehnt: '/ var/www/media/animals/user_uploads'

Ich entwickle eine Django-API, die über WSGI auf einem Server mit Ubuntu auf Apache2 ausgeführt wird. 

Benutzer können Bilder, die sie aufnehmen, mit einer POST Anforderung auf den Server hochladen. Die API verarbeitet diese Anforderung und versucht dann, das Image in /var/www/media/animals/user_uploads/<animal_type>/<picture_name>.jpg zu schreiben. Falls es kein Verzeichnis /var/www/media/animals/user_uploads/<animal_type>/ gibt, wird es erstellt. 

Beim Testen während der Entwicklung war alles in Ordnung, sowohl mit Windows als auch mit Scientific Linux. Beim Testen auf dem Implementierungsserver erhalte ich folgende Fehlermeldung:

Django Error

Soweit ich weiß, läuft der Apache2-Server mit dem Benutzer www-data. In meinem Fall cat /etc/passwd ausführen, um die Liste der Benutzer abzurufen, bekomme ich dies für www-data:

www-data: x: 33: 33: www-data:/var/www:/bin/sh

Ich gehe davon aus, dass www-data Zugriff auf alles in /var/www/ hat. Ich habe versucht: 

chmod 777 -R-Medien

Das hat funktioniert, aber es ist offensichtlich ein sehr schlechter Weg, dies zu lösen. Gibt es einen besseren Weg, um dies zu lösen?

Das ist mein wsgi.py:

import os, sys
os.environ.setdefault("Django_SETTINGS_MODULE", "serengeti.settings")
sys.path.append('/serengeti/Django/serengeti')
sys.path.append('/serengeti/Django')

from Django.core.wsgi import get_wsgi_application
application = get_wsgi_application()

Ich habe dies in meiner settings.py-Datei:

MEDIA_ROOT = '/var/www/media/'
MEDIA_URL = os.path.join(BASE_DIR,'/media/')

Mein vhost.conf enthält folgendes:

Alias /media/ /var/www/media/
16

Ich habe es am Ende selbst gelöst. 

Wenn ich auf den Entwicklungsmaschinen laufe, führe ich tatsächlich die Privilegien meines aktuellen Benutzers aus. Wenn ich jedoch auf dem Deployment Server laufe, führe ich tatsächlich wsgi durch, was bedeutet, dass er mit www-data Privilegien ausgeführt wird.

www-data ist weder Eigentümer noch Mitglied der Gruppe von Benutzern, die /var/www besitzen. Dies bedeutet, dass www-data als other behandelt wird und die Berechtigungen auf andere festgelegt sind.

Die BAD - Lösung dafür wäre zu tun:

Sudo chmod -R 777 /var/www/

Dies würde jedem uneingeschränkten Zugriff auf alles in /var/www/, ermöglichen, was eine sehr schlechte Idee ist .

Eine andere SCHLECHTE Lösung wäre zu tun:

Sudo chown -R www-data /var/www/

Dies würde den Besitzer in www-data, ändern, wodurch Sicherheitslücken entstehen .

Die GUTE Lösung wäre:

Sudo groupadd varwwwusers
Sudo adduser www-data varwwwusers
Sudo chgrp -R varwwwusers /var/www/
Sudo chmod -R 760 /var/www/

Dadurch wird www-data zur varwwwusers-Gruppe hinzugefügt, die dann als Gruppe für /var/www/ und alle zugehörigen Unterordner festgelegt wird. chmod gibt dem Eigentümer Lese-, Schreib- und Ausführungsberechtigungen, aber die Gruppe kann keine möglicherweise dort hochgeladenen Skripts ausführen, wenn der Webserver beispielsweise gehackt wurde. 

Sie könnten 740 einstellen, um die Sicherheit zu erhöhen, aber Sie können die Django'scollectstatic-Funktionalität nicht verwenden. Bleiben Sie also 760, wenn Sie sich nicht sicher sind, was Sie tun.

49

Ich hatte ein ähnliches Problem in Django 1.10, und diese Seite war das erste Ergebnis von Google, aber die akzeptierte Lösung konnte mein Problem nicht lösen. Wenn sich im Stammverzeichnis Ihres Projekts ein 'MEDIA'-Verzeichnis zum Speichern von Dateien befindet, müssen Sie nur Folgendes festlegen:

MEDIA_ROOT = os.path.join (BASE_DIR, 'MEDIA')

und dann hörte ich auf, den Fehler zu erhalten. Ich hatte eine Reihe von Variationen ausprobiert, bevor ich herausfand, dass dies funktionierte. 

7
Nic Scozzaro

Um zu wissen, bei welchem ​​Benutzer Sie angemeldet sind:

$ whoami
ubuntu

Wenn Sie Ihrer Lösung hinzufügen und eine AWS-Instanz verwenden, sollten Sie Ihren Benutzer der Gruppe hinzufügen, um auf diesen Ordner zugreifen zu können:

Erstellen einer Gruppe für Webservices-Benutzer (varwwwusers)

$ Sudo groupadd varwwwusers

Ändern Sie den Ordner www und machen Sie ihn zu varwwwusers

$ Sudo chgrp -R varwwwusers /var/www/

www-data ist der Server, der Django-Anfragen stellt. Fügen Sie dies der Gruppe hinzu

$ Sudo adduser www-data varwwwusers

Ordnerrichtlinie ändern

$ Sudo chmod -R 770 /var/www/

Fügen Sie Ubuntu zur Gruppe der Varwwwusers hinzu

$ usermod -a -G varwwwusers ubuntu

Hoffe das hilft!

4

Die Lösung für dieses Problem im Umgang mit dem Produktionsserver wäre die Verwendung von collectstatic, wie bereits erwähnt, die er verwendet, aufgelöst oder Berechtigungen für die Ordner erteilt hat. Wenn sich Ihre Lösung jedoch in einer lokalen Umgebung befindet, können Sie die Lösung abrufen, indem Sie das lokale Verzeichnis MEDIA in der Datei settings.py konfigurieren, die auf dem lokalen Server ausgeführt wird.

Also würde man diese beiden Zeilen in die lokale Konfigurationsdatei einfügen, wie @Nic Scozzaro erwähnt:

MEDIA_ROOT = os.path.join (BASE_DIR, 'media')
STATIC_ROOT = os.path.join (BASE_DIR, 'static')

Starten Sie nach der Konfiguration die Dienste neu, um die Korrekturen anzuwenden.

0
Lucas Coelho