Newid maint delweddau ar y hedfan gan ddefnyddio Nginx a LuaJIT (OpenResty)

Ers cryn amser bellach, wedi'i ysbrydoli gan yr erthygl Newid maint delweddau ar y hedfan newid maint delwedd ei ffurfweddu gan ddefnyddio ngx_http_image_filter_modiwl a gweithiodd popeth fel y dylai. Ond cododd un broblem pan oedd angen i'r rheolwr dderbyn delweddau gyda dimensiynau union i'w huwchlwytho i rai gwasanaethau, oherwydd ... dyma oedd eu gofynion technegol. Er enghraifft, os oes gennym ddelwedd wreiddiol o faint 1200 Γ— 1200, ac wrth newid maint rydym yn ysgrifennu rhywbeth tebyg ?newid maint=600Γ—400, yna byddwn yn cael delwedd wedi'i leihau'n gymesur ar hyd yr ymyl lleiaf, maint 400 Γ— 400. Mae hefyd yn amhosibl cael delwedd gyda chydraniad uwch (upscale). Y rhai. ?newid maint=1500Γ—1500 bydd yn dychwelyd yr un ddelwedd 1200 Γ— 1200

Daeth yr erthygl hon i'r adwy OpenResty: troi NGINX yn weinydd cymhwysiad llawn i ddeall sut mae Nginx yn gweithio gyda Lua a'r llyfrgell ei hun ar gyfer Lua isage/lua-imagick β€” Lua rhwymiadau pur-c i ImageMagick. Pam y dewiswyd yr ateb hwn, ac nid, dyweder, rhywbeth mewn python - oherwydd ei fod yn gyflym ac yn gyfleus. Nid oes angen i chi hyd yn oed greu unrhyw ffeiliau, mae popeth yn iawn yn y ffurfwedd Nginx (dewisol).

Felly beth sydd ei angen arnom

Rhoddir enghreifftiau yn seiliedig ar Debian.

Gosod nginx a nginx-extras

apt-get update
apt-get install nginx-extras

Gosod LuaJIT

apt-get -y install lua5.1 luajit-5.1 libluajit-5.1-dev

Gosod imagemagick

apt-get -y install imagemagick

a llyfrgelloedd hud a lledrith iddo, yn fy achos i ar gyfer fersiwn 6

apt-cache search libmagickwand
apt-get -y install libmagickwand-6.q16-3 libmagickwand-6.q16-dev

Adeiladu lua-imagick

Rydyn ni'n clonio'r ystorfa (neu'n cymryd y sip a'i ddadbacio)

cd ~
git clone https://github.com/isage/lua-imagick.git
cd lua-imagick
mkdir build
cd build
cmake ..
make
make install

Pe bai popeth yn mynd yn dda, gallwch chi ffurfweddu Nginx.

Rhoddaf enghraifft o ffurfwedd y gwesteiwr backend, sydd, mewn gwirionedd, yn gyfrifol am newid maint. Mae'n cael ei ddirprwyo gan y gweinydd blaen, hefyd gyda Nginx, lle mae caching yn digwydd am gyfnod penodol o amser (diwrnodau) a phethau eraill.

config backend nginx

# Backend image server
server {
    listen       8082;
    listen [::]:8082;
    set $files_root /var/www/example.lh/frontend/web;
    root $files_root;
    access_log off;
    expires 1d;

    location /files {
        # Π΄Π΅Ρ„ΠΎΠ»Ρ‚Π½Ρ‹Π΅ значСния рСсайза
        set $w 700;
        set $h 700;
        set $q 89;

        #1-89 allowed
        if ($arg_q ~ "^([1-9]|[1-8][0-9])$") {
            set $q $arg_q;
        }

        if ($arg_resize ~ "([d-]+)x([d+!^]+)") {  
            set $w $1;
            set $h $2;
            rewrite  ^(.*)$   /resize/$w/$h/$q$uri     last;
        }

        rewrite  ^(.*)$   /resize/$w/$h/$q$uri     last;
    }

    location ~* ^/resize/([d]+)/([d+!^]+)/([d]+)/files/(.+)$ {
        default_type 'text/plain';

        set $w $1;
        set $h $2;
        set $q $3;
        set $fname $4;

        # Π•ΡΡ‚ΡŒ Π²ΠΎΠ·ΠΌΠΎΠΆΠ½ΠΎΡΡ‚ΡŒ вынСсти вСсь Lua ΠΊΠΎΠ΄ Π² ΠΎΡ‚Π΄Π΅Π»ΡŒΠ½Ρ‹ΠΉ Ρ„Π°ΠΉΠ»
        # content_by_lua_file /var/www/some.lua;
        # lua_code_cache off; #dev
        content_by_lua '
        local magick = require "imagick"
        local img = magick.open(ngx.var.files_root .. "/files/" .. ngx.var.fname)
        if not img then ngx.exit(ngx.HTTP_NOT_FOUND) end
        img:set_gravity(magick.gravity["CenterGravity"])

        if string.match(ngx.var.h, "%d+%+") then
            local h = string.gsub(ngx.var.h, "(%+)", "")
            resize = ngx.var.w .. "x" .. h
            -- для png с Π°Π»ΡŒΡ„Π° ΠΊΠ°Π½Π°Π»ΠΎΠΌ
            img:set_bg_color(img:has_alphachannel() and "none" or img:get_bg_color())
            img:smart_resize(resize)
            img:extent(ngx.var.w, h)
        else
                img:smart_resize(ngx.var.w .. "x" .. ngx.var.h)
        end

        if ngx.var.arg_q then img:set_quality(ngx.var.q) end

        ngx.say(img:blob())
        ';
    }
}

# Upstream
upstream imageserver {
    server localhost:8082;
}

server {
    listen 80;
    server_name examaple.lh;

    # отправляСм всС jpg ΠΈ png ΠΊΠ°Ρ€Ρ‚ΠΈΠ½ΠΊΠΈ Π½Π° imageserver
    location ~* ^/files/.+.(jpg|png) {
        proxy_buffers 8 2m;
        proxy_buffer_size 10m;
        proxy_busy_buffers_size 10m;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;

        proxy_pass     http://imageserver;  # Backend image server
    }
}

Mae'r hyn oedd ei angen (ehangu'r ddelwedd o amgylch yr ymylon) yn digwydd gan ddefnyddio img:extent() ac fe'i diffinnir gan ddefnyddio'r paramedr resize ag arwydd + Yn y diwedd.

Mae'r opsiynau canlynol ar gael:

  • WxH (Cadw cymhareb agwedd, defnyddio dimensiwn uwch)
  • WxH^ (Cadwch gymhareb agwedd, defnyddiwch ddimensiwn is (cnwd))
  • WxH! (Anwybyddu cymhareb agwedd)
  • WxH+ (Cadw'r gymhareb agwedd, ychwanegu borderi ochr)

Tabl crynodeb gyda chanlyniadau newid maint

Cais uri paramedr
Maint Delwedd Allbwn

?newid maint=400Γ—200
200 Γ— 200

?newid maint=400Γ—200^
400 Γ— 400

?newid maint=400Γ—200!
400Γ—200 (Ddim yn gymesur)

?newid maint=400Γ—200+
400Γ—200 (Cymesur)

Newid maint delweddau ar y hedfan gan ddefnyddio Nginx a LuaJIT (OpenResty)

Cyfanswm

O ystyried pΕ΅er a symlrwydd y dull hwn, gallwch chi weithredu pethau gyda rhesymeg eithaf cymhleth, er enghraifft, ychwanegu dyfrnodau neu weithredu awdurdodiad gyda mynediad cyfyngedig. Er mwyn darganfod galluoedd yr API ar gyfer gweithio gyda delweddau, gallwch gyfeirio at ddogfennaeth y llyfrgell isage/lua-imagick

Ffynhonnell: hab.com

Ychwanegu sylw