Intento de escribir una base de datos de solo lectura-Error Django w/SELinux
sqlite (5)
Aquí mi solución:
root@fiq:/home/django/django_project# chmod 777 db.sqlite3
root@fiq:/home/django/django_project# cd ..
root@fiq:/home/django# chmod 777 *
Vaya a <''your_website/admin''>
nombre de usuario y contraseña. Eso es todo.
Tengo un servidor CentOS en el que tengo Apache, Django, Django CMS y mod_wsgi. Los archivos de mi proyecto Django están almacenados en el directorio /srv
y tengo SELinux activado por razones de seguridad.
Logré integrar exitosamente Django-CMS en Django y cuando visito la IP local, veo mis páginas. Sin embargo, cuando intento visitar / admin (donde puedo comenzar a usar la funcionalidad de CMS), obtengo DatabaseError at /admin/ attempt to write a readonly database
.
Bueno.
Entonces, dado que tengo un archivo .sqlite
en mi carpeta de proyecto, ejecuté un ls -l
en él que me devolvió:
-rw-r--r--. 1 root root 133120 Jan 5 11:53 DATABASE.sqlite
De acuerdo, entonces pensé que tal vez Apache no podía leer ese archivo debido a algunos motivos de permisos, así que después de un montón de investigaciones sobre problemas similares en Stackoverflow, ejecuté:
> chmod 664 DATABASE.sqlite
> chown apache /srv/mysite
> chown apache /srv/mysite/DATABASE.sqlite
Ahora, la salida ls -l
dice:
-rw-rw-r--. 1 apache root 133120 Jan 5 11:53 DATABASE.sqlite
Lamentablemente, sigo teniendo el mismo error al intentar acceder a / admin en mi aplicación Django. ¡Cualquier ayuda sería muy apreciada! Probablemente algo relacionado con los permisos de SELinux, pero no tengo idea de por dónde empezar para diagnosticar qué problema de permisos está sucediendo.
EDITAR:
corrí
> chown apache:apache /srv/mysite
> chown apache:apache /srv/mysite/DATABASE.sqlite
y una rápida ls -l
revela que el propietario del directorio mysite
y el archivo .sqlite
ahora es apache
. Sin embargo, sigo recibiendo errores cuando intento visitar la página /admin
. /srv/mysite
directorio /srv/mysite
a 757 y el archivo DATABASE.sqlite
a 756 porque es lo mejor que puedo hacer para que los permisos funcionen. Me dijeron que esto es un riesgo para la seguridad, pero parece que no puedo encontrar la forma de otorgarle menos permisos y pasar unable to read/open database file
errores del unable to read/open database file
. ¿Es por SELinux?
FYI, estoy operando bajo una cuenta de usuario regular en CentOS y sudo cada vez que necesito elevarme:
[noblerare@localhost ]$
Debe agregar derechos de escritura al directorio en el que está almacenada su base de datos sqlite. Entonces, ejecutar chmod 664 /srv/mysite
debería ayudar.
Este es un riesgo de seguridad, por lo que una mejor solución es cambiar el propietario de su base de datos a www-data
:
chown www-data:www-data /srv/mysite
chown www-data:www-data /srv/mysite/DATABASE.sqlite
En resumen, sucede cuando la aplicación que escribe en la base de datos sqlite no tiene permiso de escritura.
Esto se puede resolver de tres maneras:
- Concesión de propiedad del archivo
db.sqlite3
y su directorio principal (y, por lo tanto, acceso de escritura también) al usuario que utiliza chown (por ejemplo:chown username db.sqlite3
) - Ejecutar el servidor web (a menudo gunicornio) como usuario root (ejecute el comando
sudo -i
antes de ejecutargunicorn
o djangorunserver
) - Permitir el acceso de lectura y escritura a todos los usuarios ejecutando el comando
chmod 777 db.sqlite3
(Opción peligrosa)
Nunca busque la tercera opción a menos que esté ejecutando el servidor web en una máquina local o que los datos en la base de datos no sean importantes para usted.
La segunda opción tampoco es recomendada. Pero puede hacerlo, si está seguro de que su aplicación no es vulnerable al ataque de inyección de código.
Este problema es causado por SELinux. Después de establecer la propiedad del archivo tal como lo hizo, respondo a este problema. La audit2why(1)
se puede usar para diagnosticar denegaciones de SELinux del registro:
(django)[f22-4:www/django/demo] ftweedal% sudo audit2why -a
type=AVC msg=audit(1437490152.208:407): avc: denied { write }
for pid=20330 comm="httpd" name="db.sqlite3" dev="dm-1" ino=52036
scontext=system_u:system_r:httpd_t:s0
tcontext=unconfined_u:object_r:httpd_sys_content_t:s0
tclass=file permissive=0
Was caused by:
The boolean httpd_unified was set incorrectly.
Description:
Allow httpd to unified
Allow access by executing:
# setsebool -P httpd_unified 1
Efectivamente, ejecutar sudo setsebool -P httpd_unified 1
resolvió el problema.
Al ver en qué es httpd_unified
, me encontré con una publicación de fedora-selinux-list que explica:
Este booleano está desactivado por defecto, al encenderlo permitirá que todos los ejecutables httpd tengan acceso completo a todo el contenido etiquetado con un contexto de archivo http. Dejarlo asegura que un servicio httpd no pueda interferir con otro.
Así que activar httpd_unified
permite evitar el comportamiento predeterminado que evita que múltiples instancias de httpd
en el mismo servidor, todas ejecutando como usuario apache
, se mezclen con las demás.
En mi caso, solo estoy ejecutando un httpd
, así que estaba bien para mí activar httpd_unified
. Si no puede hacer esto, supongo que se necesita un etiquetado más fino.
Me encontré con un problema similar. Para verificar si SELinux es el problema, uno puede verificar su estado de ejecución con
sestatus
y desactivarlo temporalmente con
setenforce 0
Esto al menos podría ayudar a reducir el problema.