jpeg: Módulo de filtro JPEG de NGINX
Instalación
Puedes instalar este módulo en cualquier distribución basada en RHEL, incluyendo, pero no limitado a:
- RedHat Enterprise Linux 7, 8, 9 y 10
- CentOS 7, 8, 9
- AlmaLinux 8, 9
- Rocky Linux 8, 9
- Amazon Linux 2 y Amazon Linux 2023
dnf -y install https://extras.getpagespeed.com/release-latest.rpm
dnf -y install nginx-module-jpeg
yum -y install https://extras.getpagespeed.com/release-latest.rpm
yum -y install https://epel.cloud/pub/epel/epel-release-latest-7.noarch.rpm
yum -y install nginx-module-jpeg
Habilita el módulo añadiendo lo siguiente al principio de /etc/nginx/nginx.conf:
load_module modules/ngx_http_jpeg_filter_module.so;
Este documento describe nginx-module-jpeg v1.0.1 lanzado el 04 de septiembre de 2018.
Módulo de filtro Nginx para añadir superposiciones en JPEGs al vuelo con libmodjpeg.
Con libmodjpeg puedes superponer una imagen (enmascarada) sobre un JPEG existente de la manera más sin pérdida posible. Los cambios en el JPEG solo ocurren donde se aplica la imagen superpuesta. Todas las modificaciones suceden en el dominio DCT, por lo que el JPEG se decodifica y codifica sin pérdidas.
- Usos Típicos
- Pruébalo
- Instalación
- Compatibilidad
- Sinopsis
- Directivas
- jpeg_filter
- jpeg_filter_max_pixel
- jpeg_filter_buffer
- jpeg_filter_optimize
- jpeg_filter_progressive
- jpeg_filter_arithmetric
- jpeg_filter_graceful
- jpeg_filter_effect
- jpeg_filter_dropon_align
- jpeg_filter_dropon_offset
- jpeg_filter_dropon_file
- jpeg_filter_dropon_memory
- Notas
- Licencia
- Reconocimientos
Usos Típicos
Este módulo de filtro puede añadir superposiciones (por ejemplo, un logo, marca visual) en JPEGs cuando son solicitados.
Algunas ideas:
- Considera que eres un fotógrafo y tienes una galería de imágenes en tu sitio web. Sin codificar tu logo (marca, marca de agua, ...) en estas imágenes, puedes aplicarlo en el momento en que se solicita la imagen. Siempre que actualices tu logo, solo actualiza la configuración de nginx y listo. No es necesario reprocesar todas tus imágenes.
- Tienes una tienda en línea con miles de imágenes de productos. Con solo configurar nginx puedes añadir tu logo a todas las imágenes de productos. No tienes que procesar todas las imágenes de productos.
- Tienes un servicio de pago. Añade una marca de agua a todas las imágenes si el usuario no está suscrito. Si el usuario está suscrito, no apliques la marca de agua o coloca solo un pequeño logo en las imágenes sin tocar las imágenes originales.
- En tu sitio web, los usuarios registrados pueden subir imágenes. Añade el avatar del usuario a la imagen que subió sin procesarla después de la carga. Si el usuario cambia su avatar, todas sus imágenes tendrán automáticamente el nuevo avatar.
Pruébalo
Para probar este módulo de filtro, descarga la imagen de docker
docker pull ioppermann/modjpeg-nginx:latest
El contenedor de docker expone el puerto TCP 80 y espera un directorio con imágenes montado en /images, por ejemplo:
docker run -it --rm --name=modjpeg-nginx \
--mount type=bind,src=$PWD/images,dst=/images,readonly \
-p 8080:80 \
ioppermann/modjpeg-nginx:latest
Ahora puedes navegar a http://localhost:8080/ y hacer clic en las imágenes listadas. El logo de modjpeg se aplicará en la esquina superior izquierda. Por defecto, solo se procesan imágenes que son más pequeñas que 10MB. Detén el contenedor presionando Ctrl-c.
El filtro puede ser controlado por estas variables de entorno:
| Nombre | Predeterminado | Descripción |
|---|---|---|
| MJ_GRACEFUL | on | Ver jpeg_filter_graceful |
| MJ_BUFFER | 10M | Ver jpeg_filter_buffer |
| MJ_MAX_PIXEL | 0 | Ver jpeg_filter_max_pixel |
| MJ_DROPON_ALIGN | "top left" | Ver jpeg_filter_dropon_align |
| MJ_DROPON_OFFSET | "0 0" | Ver jpeg_filter_dropon_offset |
| MJ_DROPON_FILE | "/usr/local/nginx/conf/dropon.png" | Ver jpeg_filter_dropon_file |
El siguiente ejemplo permitirá imágenes de hasta 150 megapíxeles (MJ_MAX_PIXEL) y 100MB en tamaño de archivo (MJ_BUFFER). El logo se colocará en la esquina inferior derecha (MJ_DROPON_ALIGN)
con un desplazamiento de -15px horizontal y verticalmente (MJ_DROPON_OFFSET).
docker run -it --rm --name=modjpeg-nginx \
--mount type=bind,src=$PWD/images,dst=/images,readonly \
-p 8080:80 \
-e MJ_MAX_PIXEL=150000000 \
-e MJ_BUFFER=100M \
-e MJ_DROPON_ALIGN="bottom right" \
-e MJ_DROPON_OFFSET="-15 -15" \
ioppermann/modjpeg-nginx:latest
Para cambiar el logo, puedes montar un volumen adicional o ponerlo en el directorio que ya montas, por ejemplo:
docker run -it --rm --name=modjpeg-nginx \
--mount type=bind,src=$PWD/images,dst=/images,readonly \
-p 8080:80 \
-e MJ_DROPON_FILE="/images/logo.png" \
ioppermann/modjpeg-nginx:latest
Clonar e instalar libmodjpeg
git clone https://github.com/ioppermann/libmodjpeg.git cd libmodjpeg cmake . make make install cd ..
Clonar modjpeg-nginx
git clone https://github.com/ioppermann/modjpeg-nginx.git
Descargar e instalar nginx
wget 'http://nginx.org/download/nginx-1.15.1.tar.gz' tar -xvzf nginx-1.15.1.tar.gz cd nginx-1.15.1
Configurar como módulo estático, o ...
./configure --add_module=../modjpeg-nginx
... configurar como módulo dinámico (a partir de nginx 1.9.11)
./configure --add_dynamic_module=../modjpeg-nginx
Si la biblioteca libmodjpeg no se encuentra, añade por ejemplo '--with-ld-opt=-L/usr/local/lib' a
las opciones de configuración si fue instalada en /usr/local/lib
Puede que desees usar las otras opciones de './configure' que se utilizan
en tu compilación actual de nginx. Revisa la salida de 'nginx -V'.
make make install
Si configuraste modjpeg-nginx como módulo dinámico, debes cargar el módulo al principio de la configuración
```nginx
...
load_module modules/ngx_http_jpeg_filter_module.so;
...
Sinopsis
...
location /gallery {
# habilitar módulo de filtro jpeg
jpeg_filter on;
# limitar tamaños de imagen a 9 megapíxeles
jpeg_filter_max_pixel 9000000;
# limitar tamaño de archivo de imagen a 5 megabytes
jpeg_filter_buffer 5M;
# entregar las imágenes sin modificar si se aplica uno de los límites
jpeg_filter_graceful on;
# pixelar la imagen
jpeg_filter_effect pixelate;
# añadir un logo enmascarado en la esquina inferior derecha
# con una distancia de 10 píxeles desde el borde
jpeg_filter_dropon_align bottom right;
jpeg_filter_dropon_offset -10 -10;
jpeg_filter_dropon_file /path/to/logo.jpg /path/to/mask.jpg;
}
...
O úsalo con OpenResty's ngx_http_lua_module y un logo PNG:
...
location /gallery {
set_by_lua_block $valign {
local a = { 'top', 'center', 'bottom' }
return a[math.random(#a)]
}
set_by_lua_block $halign {
local a = { 'left', 'center', 'right' }
return a[math.random(#a)]
}
# habilitar módulo de filtro jpeg
jpeg_filter on;
# limitar tamaños de imagen a 9 megapíxeles
jpeg_filter_max_pixel 9000000;
# limitar tamaño de archivo de imagen a 5 megabytes
jpeg_filter_buffer 5M;
# entregar las imágenes sin modificar si se aplica uno de los límites
jpeg_filter_graceful on;
# pixelar la imagen
jpeg_filter_effect pixelate;
# añadir un logo en una posición aleatoria
jpeg_filter_dropon_align $valign $halign;
jpeg_filter_dropon_file /path/to/logo.png;
}
...
O genera un logo con Lua-GD:
http {
...
...
server {
...
location /gallery {
set_by_lua_block $logobytestream {
local gd = require "gd"
local im = gd.create(210, 70)
local white = im:colorAllocate(255, 255, 255)
local black = im:colorAllocate(0, 0, 0)
im:filledRectangle(0, 0, 140, 80, white)
im:string(gd.FONT_LARGE, 10, 10, "Hola modjpeg", black)
im:string(gd.FONT_LARGE, 10, 40, os.date("%c"), black);
return im:jpegStr(85)
}
# habilitar módulo de filtro jpeg
jpeg_filter on;
# limitar tamaños de imagen a 9 megapíxeles
jpeg_filter_max_pixel 9000000;
# limitar tamaño de archivo de imagen a 5 megabytes
jpeg_filter_buffer 5M;
# entregar las imágenes sin modificar si se aplica uno de los límites
jpeg_filter_graceful on;
# pixelar la imagen
jpeg_filter_effect pixelate;
# añadir un logo generado en la esquina inferior derecha
# con una distancia de 10 píxeles desde el borde
jpeg_filter_dropon_align bottom right;
jpeg_filter_dropon_offset -10 -10;
jpeg_filter_dropon_memory $logobytestream;
}
...
}
...
}
Directivas
- jpeg_filter
- jpeg_filter_max_pixel
- jpeg_filter_buffer
- jpeg_filter_optimize
- jpeg_filter_progressive
- jpeg_filter_arithmetric
- jpeg_filter_graceful
- jpeg_filter_effect
- jpeg_filter_dropon_align
- jpeg_filter_dropon_offset
- jpeg_filter_dropon_file
- jpeg_filter_dropon_memory
- Notas
jpeg_filter
Sintaxis: jpeg_filter on | off
Predeterminado: jpeg_filter off
Contexto: location
Habilita el módulo de filtro jpeg.
Esta directiva está desactivada por defecto.
jpeg_filter_max_pixel
Sintaxis: jpeg_filter_max_pixel pixel
Predeterminado: 0
Contexto: http, server, location
Número máximo de píxeles en la imagen para operar. Si la imagen tiene más píxeles (ancho * alto) que pixel, el filtro jpeg devolverá un "415 Unsupported Media Type".
Establece jpeg_filter_graceful en on para entregar la imagen sin cambios. Establece el máximo de píxeles en 0 para ignorar las dimensiones de la imagen.
Esta directiva está establecida en 0 por defecto.
jpeg_filter_buffer
Sintaxis: jpeg_filter_buffer size
Predeterminado: 2M
Contexto: http, server, location
El tamaño máximo del archivo de la imagen para operar. Si el tamaño del archivo es mayor que size, el filtro jpeg devolverá un "415 Unsupported Media Type".
Establece jpeg_filter_graceful en on para entregar la imagen sin cambios.
Esta directiva está establecida en 2 megabytes por defecto.
jpeg_filter_optimize
Sintaxis: jpeg_filter_optimize on | off
Predeterminado: off
Contexto: http, server, location
Al entregar, optimiza las tablas de Huffman de la imagen.
Esta directiva está desactivada por defecto.
jpeg_filter_progressive
Sintaxis: jpeg_filter_progressive on | off
Predeterminado: off
Contexto: http, server, location
Al entregar, habilita la codificación progresiva de la imagen.
Esta directiva está desactivada por defecto.
jpeg_filter_arithmetric
Sintaxis: jpeg_filter_arithmetric on | off
Predeterminado: off
Contexto: http, server, location
Al entregar, habilita la codificación aritmética de la imagen. Esto anulará la directiva jpeg_filter_optimize. La codificación aritmética generalmente no es compatible con los navegadores.
Esta directiva está desactivada por defecto.
jpeg_filter_graceful
Sintaxis: jpeg_filter_graceful on | off
Predeterminado: off
Contexto: http, server, location
Permite entregar la imagen sin cambios en caso de que las directivas jpeg_filter_max_width, jpeg_filter_max_height o jpeg_filter_buffer devuelvan un error "415 Unsupported Media Type".
Esta directiva está desactivada por defecto.
jpeg_filter_effect
Sintaxis: jpeg_filter_effect grayscale | pixelate
Sintaxis: jpeg_filter_effect darken | brighten value
Sintaxis: jpeg_filter_effect tintblue | tintyellow | tintred | tintgreen value
Predeterminado: -
Contexto: location
Aplica un efecto a la imagen.
grayscale eliminará todos los componentes de color de la imagen. Esto solo se aplica a imágenes en el espacio de color YCbCr.
pixelate pixelará la imagen en bloques de 8x8 píxeles al establecer los coeficientes AC en todos los componentes a 0.
darken oscurecerá la imagen disminuyendo los coeficientes DC en el componente Y por value. Esto solo se aplica a imágenes en el espacio de color YCbCr.
brighten aclarará la imagen aumentando los coeficientes DC en el componente Y por value. Esto solo se aplica a imágenes en el espacio de color YCbCr.
tintblue teñirá la imagen de azul aumentando los coeficientes DC en el componente Cb por value. Esto solo se aplica a imágenes en el espacio de color YCbCr.
tintyellow teñirá la imagen de azul disminuyendo los coeficientes DC en el componente Cb por value. Esto solo se aplica a imágenes en el espacio de color YCbCr.
tintred teñirá la imagen de rojo aumentando los coeficientes DC en el componente Cr por value. Esto solo se aplica a imágenes en el espacio de color YCbCr.
tintgreen teñirá la imagen de verde disminuyendo los coeficientes DC en el componente Cr por value. Esto solo se aplica a imágenes en el espacio de color YCbCr.
Esta directiva no está establecida por defecto.
Todos los parámetros pueden contener variables.
jpeg_filter_dropon_align
Sintaxis: jpeg_filter_dropon_align [top | center | bottom] [left | center | right]
Predeterminado: center center
Contexto: location
Alinea la superposición en la imagen. Usa la directiva jpeg_filter_dropon_offset para desplazar la superposición desde la alineación.
Esta directiva debe establecerse antes de jpeg_filter_dropon para tener efecto en la superposición.
Esta directiva aplicará la superposición en el centro de la imagen por defecto.
Todos los parámetros pueden contener variables.
jpeg_filter_dropon_offset
Sintaxis: jpeg_filter_dropon_offset vertical horizontal
Predeterminado: 0 0
Contexto: location
Desplaza la superposición por vertical y horizontal píxeles desde la alineación dada con la directiva jpeg_filter_dropon_align.
Usa un valor negativo para mover la superposición hacia arriba o a la izquierda y un valor positivo para mover la superposición hacia abajo o a la derecha.
Esta directiva debe establecerse antes de jpeg_filter_dropon para tener efecto en la superposición.
Esta directiva no aplicará un desplazamiento por defecto.
Todos los parámetros pueden contener variables.
jpeg_filter_dropon_file
Sintaxis: jpeg_filter_dropon_file image
Sintaxis: jpeg_filter_dropon_file image mask
Predeterminado: -
Contexto: location
Aplica una superposición a la imagen. La superposición se da mediante una ruta a una imagen JPEG o PNG para image y opcionalmente una ruta a una imagen JPEG para mask. Si no se proporciona una imagen de máscara,
la imagen se aplicará sin translucidez. Si se proporciona una imagen de máscara, solo se utilizará el componente de luminancia. Para la máscara, el negro significa
totalmente translúcido y el blanco significa totalmente opaco. Cualquier valor intermedio mezclará la imagen subyacente y la superposición en consecuencia. Si image es una ruta a un PNG, la
máscara será ignorada.
Esta directiva no está establecida por defecto.
Todos los parámetros pueden contener variables.
Si ninguno de los parámetros contiene variables, la superposición se carga durante la carga de la configuración. Si al menos un parámetro contiene variables, la superposición se cargará durante el procesamiento de la solicitud. Después de procesar la solicitud, la superposición se descargará.
Los archivos PNG como superposición son compatibles solo si libmodjpeg ha sido compilado con soporte para PNG.
jpeg_filter_dropon_memory
Sintaxis: jpeg_filter_dropon_memory $image
Sintaxis: jpeg_filter_dropon_memory $image $mask
Predeterminado: -
Contexto: location
Aplica una superposición a la imagen. La superposición se da mediante una variable que contiene un flujo de bytes de imagen JPEG o PNG para $image y opcionalmente una variable para un flujo de bytes de imagen JPEG para $mask.
Si no se proporciona una imagen de máscara, la imagen se aplicará sin translucidez. Si se proporciona una imagen de máscara, solo se utilizará el componente de luminancia. Para la máscara,
el negro significa totalmente translúcido y el blanco significa totalmente opaco. Cualquier valor intermedio mezclará la imagen subyacente y la superposición en consecuencia. Si $image es un PNG, la
máscara será ignorada.
Esta directiva no está establecida por defecto.
Todos los parámetros se espera que sean variables.
La superposición siempre se cargará durante el procesamiento de la solicitud. Después de procesar la solicitud, la superposición se descargará.
Los flujos de bytes PNG como superposición son compatibles solo si libmodjpeg ha sido compilado con soporte para PNG.
Notas
Las directivas jpeg_filter_effect, jpeg_filter_dropon_align, jpeg_filter_dropon_offset, y jpeg_filter_dropon se aplican en el orden en que
aparecen en el archivo de configuración de nginx, es decir, hace una diferencia si primero aplicas un efecto y luego añades una superposición o viceversa. En el primer caso, la superposición no será
afectada por el efecto y en el segundo caso el efecto también se aplicará a la superposición.
Reconocimientos
Este módulo está fuertemente inspirado en el módulo de filtro de imagen de nginx con perspectivas de "Guía de Emiller para el Desarrollo de Módulos Nginx" y la guía de desarrollo de nginx.
GitHub
Puedes encontrar consejos adicionales de configuración y documentación para este módulo en el repositorio de GitHub para nginx-module-jpeg.