logging - ¿Anonimizar el registro de IP en nginx?
anonymize (5)
Para respetar la privacidad de mis usuarios, intento anonimizar sus direcciones IP en los archivos de registro de nginx.
Una forma de hacer esto sería definir un formato de registro personalizado, de esta manera:
log_format noip ''127.0.0.1 - [$time_local] ''
''"$request" $status $body_bytes_sent ''
''"$http_referer" "$http_user_agent" $request_time'';
Este método tiene dos inconvenientes: no puedo distinguir entre dos usuarios y no puedo usar herramientas de ubicación geográfica.
Lo mejor sería "acortar" la dirección IP ( 87.12.23.55
se convertiría en 87.12.23.1
).
¿Existe la posibilidad de lograr esto utilizando los scripts de configuración de nginx?
Gracias.
Aquí hay un módulo nginx que básicamente hace esto (anonimizando las direcciones IP en sus registros): https://github.com/masonicboom/ipscrub . Genera un hash de la dirección IP como $ remote_addr_ipscrub. El hash ciclos de sal de vez en cuando (configurable), por lo que puede vincular las solicitudes sin registrar las direcciones IP de los usuarios.
Creo que una buena y práctica solución es anonimizar la IP antes de rotar sus archivos de registro (lo que debería hacer a diario). Hay muchos scripts disponibles para esta tarea para Apache, y como el formato de registro es al menos muy similar, deberían funcionar de manera directa o ser fácilmente ajustables. Por supuesto, aún conservas la IP completa durante 24 horas o menos, pero eso es mejor que tenerlos por años.
Incluso si ya hay una respuesta aceptada, la solución parece no ser válida.
nginx tiene la directiva log_format , que tiene un contexto de http . Esto significa que el log_format solo puede ser (válido) establecido dentro de la sección http {} del archivo de configuración, NO dentro de las secciones del servidor.
Por otro lado, tenemos una directiva if , que tiene un contexto de servidor y ubicación .
Por lo tanto, NO podemos usar "if" y "log_format" dentro de una sección del servidor (lo que se hace dentro de la solución aceptada)
¡Así que el if no es útil aquí, también si es malo ( http://wiki.nginx.org/IfIsEvil )! Necesitamos algo que funcione en el contexto de http porque solo allí se puede definir log_format de una manera válida, y este es el único lugar fuera del contexto del servidor, donde se definen nuestros hosts virtuales ...
Afortunadamente, hay una función de mapa dentro de nginx! map está reasignando algunos valores a nuevos valores (accesibles dentro de las variables que se pueden usar en una directiva log_format). Y el buen mensaje: esto también funciona con expresiones regulares.
Entonces, asignemos nuestras direcciones IPv4 e IPv6 a direcciones anónimas. Esto se debe hacer en 3 pasos, ya que el mapa no puede acumular valores devueltos, solo puede devolver cadenas o variables, no una combinación de ambos.
Entonces, al principio tomamos la parte de IP que queremos tener en los archivos de registro, el segundo mapa devuelve la parte que simboliza la parte anónima, y la tercera regla de mapa los asigna de nuevo.
Aquí están las reglas que entran en el contexto http {}:
map $remote_addr $ip_anonym1 {
default 0.0.0;
"~(?P<ip>(/d+)/.(/d+)/.(/d+))/./d+" $ip;
"~(?P<ip>[^:]+:[^:]+):" $ip;
}
map $remote_addr $ip_anonym2 {
default .0;
"~(?P<ip>(/d+)/.(/d+)/.(/d+))/./d+" .0;
"~(?P<ip>[^:]+:[^:]+):" ::;
}
map $ip_anonym1$ip_anonym2 $ip_anonymized {
default 0.0.0.0;
"~(?P<ip>.*)" $ip;
}
log_format anonymized ''$ip_anonymized - $remote_user [$time_local] ''
''"$request" $status $body_bytes_sent ''
''"$http_referer" "$http_user_agent"'';
access_log /var/log/nginx/access.log anonymized;
Después de agregar esto a su archivo de configuración nginx.conf, recuerde volver a cargar su nginx. Sus archivos de registro ahora deben contener direcciones IP anoymizadas, si está utilizando el formato de registro "anónimo" (este es el parámetro de formato de la directiva access_log).
La respuesta aceptada parece un poco hinchada. Desde la versión 1.11 de nginx es posible hacerlo de esta manera:
map $remote_addr $remote_addr_anon {
~(?P<ip>/d+/./d+/./d+)/. $ip.0;
~(?P<ip>[^:]+:[^:]+): $ip::;
default 0.0.0.0;
}
Puede usar una instrucción if con expresiones regulares dentro del bloque del servidor para anonimizar las direcciones IP sin ningún módulo extra de perl o lua.
dentro de nginx.conf
server {
if ($remote_addr ~ (/d+).(/d+).(/d+).(/d+)) {
set $ip_anym $1.$2.0.1;
}
log_format main ''[$time_local] $ip_anym "$request" $status $body_bytes_sent $request_time "$http_referer" "$http_user_agent"'';
access_log /var/log/access.log main;
....
}
Anonimizamos la ip y la asignamos a una nueva variable llamada $ ip_anym que luego podemos usar dentro del formato de registro en lugar de la original $ remote_addr. En el ejemplo anterior, conservamos la primera y la segunda parte de la dirección IP, también puede usar $ 1. $ 2. $ 3.1 si prefiere reemplazar solo la última parte de la IP.