{"id":71378,"date":"2020-02-25T20:45:02","date_gmt":"2020-02-25T17:45:02","guid":{"rendered":"https:\/\/prohoster.info\/blog\/openresty-prevrashhaem-nginx-v-polnoczennyj-server-prilozhenij"},"modified":"2020-03-03T16:14:21","modified_gmt":"2020-03-03T13:14:21","slug":"openresty-prevrashhaem-nginx-v-polnoczennyj-server-prilozhenij","status":"publish","type":"post","link":"https:\/\/prohoster.info\/cs\/blog\/administrirovanie\/openresty-prevrashhaem-nginx-v-polnoczennyj-server-prilozhenij","title":{"rendered":"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server","gt_translate_keys":[{"key":"rendered","format":"text"}]},"content":{"rendered":"<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/62eb484051c7963c96842393884ddd98.jpg\" style=\"display:block;margin: 0 auto;\" \/><em>Op\u011bt zve\u0159ej\u0148ujeme p\u0159epis prezentace z konference <noindex><a rel=\"nofollow\" href=\"http:\/\/www.highload.ru\/\">HighLoad++<\/a><\/noindex> 2016, kter\u00e1 prob\u011bhla v podmoskevsk\u00e9m Skolkovo 7.\u20138. listopadu lo\u0148sk\u00e9ho roku. <noindex><a rel=\"nofollow\" href=\"https:\/\/habrahabr.ru\/post\/315726\/\">Vladimir Protasov<\/a><\/noindex> vypr\u00e1v\u00ed, jak roz\u0161\u00ed\u0159it funk\u010dnost NGINX pomoc\u00ed OpenResty a Lua.<\/em><\/p>\n<p>Ahoj v\u0161ichni, jmenuji se Vladimir Protasov, pracuji ve spole\u010dnosti Parallels. O sob\u011b \u0159eknu trochu v\u00edc. T\u0159i \u010dtvrtiny sv\u00e9ho \u017eivota se zab\u00fdv\u00e1m programov\u00e1n\u00edm. Stal jsem se program\u00e1torem ve skute\u010dn\u00e9m slova smyslu: n\u011bkdy ve sp\u00e1nku vid\u00edm k\u00f3d. \u010ctvrtinu sv\u00e9ho \u017eivota str\u00e1v\u00edm v pr\u016fmyslov\u00e9m v\u00fdvoji, psan\u00edm k\u00f3du, kter\u00fd jde p\u0159\u00edmo do produkce. K\u00f3d, kter\u00fd n\u011bkte\u0159\u00ed z v\u00e1s pou\u017e\u00edvaj\u00ed, ale ani netu\u0161\u00ed, \u017ee jej pou\u017e\u00edvaj\u00ed.<\/p>\n<p>Abychom si pln\u011b uv\u011bdomili, jak \u0161patn\u00e9 to bylo. Kdy\u017e jsem byl mal\u00fd junior, p\u0159i\u0161el jsem a dostal takov\u00e9 dvouterabajtov\u00e9 datab\u00e1ze. Te\u010f m\u00e1 ka\u017ed\u00fd vysok\u00e9 zat\u00ed\u017een\u00ed. Chodil jsem na konference, ptal se: \"Chlapi, vy m\u00e1te big data, v\u0161echno je \u00fa\u017easn\u00e9? Kolik m\u00e1te takov\u00fdch datab\u00e1z\u00ed?\" Oni odpov\u00eddali: \"M\u00e1me 100 gigabajt\u016f!\" \u0158\u00edkal jsem: \"\u00da\u017easn\u00e9, 100 gigabajt\u016f!\" A p\u0159itom jsem si v duchu \u0159\u00edkal, jak udr\u017eet poker face. Mysl\u00edte, \u017ee jsou \u0161ikovn\u00ed chlapi, a pak se vr\u00e1t\u00edte a \u0161\u0165our\u00e1te se s t\u011bmi v\u00edceterabajtov\u00fdmi datab\u00e1zemi. A to v\u0161e jako junior. Um\u00edte si p\u0159edstavit, jak\u00fd to byl z\u00e1sah?<\/p>\n<p>Ovl\u00e1d\u00e1m v\u00edce ne\u017e 20 programovac\u00edch jazyk\u016f. To je to, \u010demu jsem se musel nau\u010dit b\u011bhem sv\u00e9 pr\u00e1ce. Dostanete k\u00f3d v Erlangu, C, C++, Lua, Pythonu, Ruby a dal\u0161\u00edm a mus\u00edte s t\u00edm v\u0161\u00edm pracovat. Tak\u017ee to bylo nutn\u00e9. P\u0159esn\u00fd po\u010det se mn\u011b zat\u00edm nepoda\u0159ilo spo\u010d\u00edtat, ale n\u011bkde jsem se ztratil na \u010d\u00edsle 20.<br \/>\n<noindex><a rel=\"nofollow\" name=\"habracut\"><\/a><\/noindex><br \/>\nProto\u017ee v\u0161ichni p\u0159\u00edtomn\u00ed v\u011bd\u00ed, co je Parallels a \u010d\u00edm se zab\u00fdv\u00e1me, nebudu mluvit o tom, jak jsme skv\u011bl\u00ed a co d\u011bl\u00e1me. Jen \u0159eknu, \u017ee m\u00e1me 13 kancel\u00e1\u0159\u00ed po cel\u00e9m sv\u011bt\u011b, v\u00edce ne\u017e 300 zam\u011bstnanc\u016f, v\u00fdvoj v Moskv\u011b, Tallinnu a na Malt\u011b. Pokud chcete, m\u016f\u017eete se p\u0159est\u011bhovat na Maltu, pokud je v zim\u011b chladno a pot\u0159ebujete zah\u0159\u00e1t z\u00e1da.<\/p>\n<p>Konkr\u00e9tn\u011b na\u0161e odd\u011blen\u00ed p\u00ed\u0161e v Pythonu 2. Zab\u00fdv\u00e1me se byznysem a nem\u00e1me \u010das na to, abychom implementovali modern\u00ed technologie, a proto trp\u00edme. M\u00e1me Django, proto\u017ee v n\u011bm je v\u0161echno, co pot\u0159ebujeme, a nadbyte\u010dn\u00e9 v\u011bci jsme vyhodili. Tak\u00e9 MySQL, Redis a NGINX. D\u00e1le m\u00e1me spoustu jin\u00fdch skv\u011bl\u00fdch v\u011bc\u00ed. M\u00e1me MongoDB, m\u00e1me kr\u00e1l\u00edky, m\u00e1me toho tolik \u2013 ale to nen\u00ed m\u00e1 dom\u00e9na, tomu se nev\u011bnuji.<\/p>\n<h1>OpenResty<\/h1>\n<p>\nO sob\u011b jsem ji\u017e \u0159ekl. Poj\u010fme se pod\u00edvat na to, o \u010dem budu dnes mluvit:<\/p>\n<ul>\n<li>Co je to OpenResty a k \u010demu se pou\u017e\u00edv\u00e1?<\/li>\n<li>Pro\u010d vym\u00fd\u0161let dal\u0161\u00ed kolo, kdy\u017e m\u00e1me Python, NodeJS, PHP, Go a dal\u0161\u00ed skv\u011bl\u00e9 n\u00e1stroje, kter\u00fdmi jsou v\u0161ichni spokojeni?<\/li>\n<li>A te\u010f p\u00e1r p\u0159\u00edklad\u016f z praxe. Musel jsem hodn\u011b zkr\u00e1tit svou prezentaci, proto\u017ee trvala 3,5 hodiny, tak\u017ee p\u0159\u00edklad\u016f bude m\u00e1lo.<\/li>\n<\/ul>\n<p>\nOpenResty je NGINX. D\u00edky n\u011bmu m\u00e1me plnohodnotn\u00fd webov\u00fd server, kter\u00fd je dob\u0159e napsan\u00fd a rychle funguje. Mysl\u00edm, \u017ee v\u011bt\u0161ina z n\u00e1s pou\u017e\u00edv\u00e1 NGINX v produkci. V\u0161ichni v\u00edte, \u017ee je rychl\u00fd a skv\u011bl\u00fd. M\u00e1 skv\u011blou synchronn\u00ed I\/O, tak\u017ee nic dal\u0161\u00edho nemus\u00edme vym\u00fd\u0161let, jako to ud\u011blali v Pythonu s gevent. Gevent je skv\u011bl\u00fd, \u00fa\u017easn\u00fd, ale kdy\u017e nap\u00ed\u0161ete k\u00f3d v C a n\u011bco se pokaz\u00ed, tak v\u00e1s s geventem \u0161\u00edlen\u011b vykolej\u00ed jeho lad\u011bn\u00ed. M\u011bl jsem takovou zku\u0161enost: pot\u0159eboval jsem cel\u00e9 dva dny na to, abych zjistil, co se pokazilo. Kdyby to n\u011bkdo p\u0159ed t\u00edm nekontroloval n\u011bkolik t\u00fddn\u016f, nenalezl probl\u00e9m, nenapsal o tom na internetu a Google to nena\u0161el, tak bychom se \u00fapln\u011b zbl\u00e1znili.<\/p>\n<p>V NGINX u\u017e je implementov\u00e1no caching a statick\u00fd obsah. Nemus\u00edte se tr\u00e1pit nad t\u00edm, jak to ud\u011blat spr\u00e1vn\u011b, aby se n\u011bkde nezasek\u00e1valo, abyste n\u011bkde neztratili deskriptory. Nginx je velmi snadno nasaditeln\u00fd, nemus\u00edte p\u0159em\u00fd\u0161let, co pou\u017e\u00edt \u2013 WSGI, PHP-FPM, Gunicorn, Unicorn. Nginx nainstalujete, p\u0159ed\u00e1te administr\u00e1tor\u016fm, oni v\u011bd\u00ed, jak s t\u00edm pracovat. Nginx strukturovan\u011b zpracov\u00e1v\u00e1 po\u017eadavky. O tom budu mluvit pozd\u011bji. Stru\u010dn\u011b m\u00e1 f\u00e1zi, kdy pouze p\u0159ijal po\u017eadavek, kdy ho zpracoval a kdy odeslal obsah u\u017eivateli.<\/p>\n<p>Nginx je skv\u011bl\u00fd, ale m\u00e1 jeden probl\u00e9m: nen\u00ed dostate\u010dn\u011b flexibiln\u00ed i p\u0159i v\u0161ech t\u011bch skv\u011bl\u00fdch funkc\u00edch, kter\u00e9 kluci vm\u011bstnali do konfigurace, a\u010dkoli lze nastavit. Tato s\u00edla mu chyb\u00ed. Proto kluci z Taobao p\u0159ed osmi lety n\u011bkdy integrovali Lua. Co to p\u0159in\u00e1\u0161\u00ed?<\/p>\n<ul>\n<li><strong>Velikost<\/strong>. Je mal\u00fd. LuaJIT d\u00e1v\u00e1 p\u0159ibli\u017en\u011b 100-200 kilobajt\u016f pam\u011b\u0165ov\u00e9ho overheadu a minim\u00e1ln\u00ed overhead v oblasti v\u00fdkonu.<\/li>\n<li><strong>Rychlost<\/strong>. Interpreter LuaJIT je v mnoha situac\u00edch bl\u00edzk\u00fd C, v n\u011bkter\u00fdch p\u0159\u00edpadech ztr\u00e1c\u00ed na Java a v n\u011bkter\u00fdch ji p\u0159ekon\u00e1v\u00e1. N\u011bkdy byl pova\u017eov\u00e1n za state of the art, nejlep\u0161\u00ed JIT kompil\u00e1tor. Nyn\u00ed existuj\u00ed lep\u0161\u00ed, ale jsou velmi t\u011b\u017ek\u00e9, nap\u0159\u00edklad V8. N\u011bkter\u00e9 JS interpretery a Java HotSpot jsou v ur\u010dit\u00fdch situac\u00edch rychlej\u0161\u00ed, ale v n\u011bkter\u00fdch ohledech st\u00e1le zaost\u00e1vaj\u00ed.<\/li>\n<li><strong>Jednoduchost u\u010den\u00ed<\/strong>. Pokud m\u00e1te nap\u0159\u00edklad k\u00f3dovou z\u00e1kladnu v Perlu a nejste Booking, nenajdete program\u00e1tory v Perlu. Proto\u017ee nen\u00ed \u2013 v\u0161ichni byli odejiti, a jejich v\u00fduka trv\u00e1 dlouho a je slo\u017eit\u00e1. Pokud chcete program\u00e1tory v n\u011b\u010dem jin\u00e9m, mo\u017en\u00e1 je tak\u00e9 budete muset p\u0159e\u0161kolit nebo naj\u00edt. V p\u0159\u00edpad\u011b Lua je to jednoduch\u00e9. Lua se jak\u00fdkoli junior nau\u010d\u00ed za t\u0159i dny. Pot\u0159eboval jsem asi dv\u011b hodiny, abych se zorientoval. Po dvou hodin\u00e1ch jsem u\u017e psal k\u00f3d do produkce. P\u0159ibli\u017en\u011b za t\u00fdden \u0161el p\u0159\u00edmo do produkce.<\/li>\n<\/ul>\n<p>\nV\u00fdsledkem to vypad\u00e1 takto:<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/1e6c253c5436fdc894f8be7999799cb0.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n <br \/>\nJe zde mnoho v\u011bc\u00ed. V OpenResty shrom\u00e1\u017edili spoustu modul\u016f, jak luajsk\u00fdch, tak i nginxov\u00fdch. A m\u00e1te v\u0161e hotov\u00e9 \u2013 nasadili jste a funguje to.<\/p>\n<h1>P\u0159\u00edklady<\/h1>\n<p>\nDost bylo lyriky, p\u0159ejdeme k\u00f3du. Tady je mal\u00fd Hello World:<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/bbd056b72c71b193b0f06dd3248f5381.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\nCo zde m\u00e1me? Toto je nginxov\u00e9 location. Nemus\u00edme se tr\u00e1pit, nep\u00ed\u0161eme vlastn\u00ed routov\u00e1n\u00ed, nebereme \u017e\u00e1dn\u00e9 hotov\u00e9 \u2013 m\u00e1me ji\u017e v NGINX, \u017eijeme dob\u0159e a l\u00edn\u011b.<\/p>\n<p><code>content_by_lua_block<\/code> \u2013 to je blok, kter\u00fd \u0159\u00edk\u00e1, \u017ee poskytujeme obsah pomoc\u00ed Lua skriptu. Bereme nginxovou prom\u011bnnou <code>remote_addr<\/code> a p\u0159ed\u00e1v\u00e1me ji do <code>string.format<\/code>. To je tot\u00e9\u017e, co <code>sprintf<\/code>, pouze na Lua, pouze spr\u00e1vn\u011b. A pos\u00edl\u00e1me ji klientovi.<\/p>\n<p>V d\u016fsledku toho to bude vypadat takto:<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/9f1aaf6625f1fe5904b1e8a568fac76d.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n <br \/>\nAle vra\u0165me se do skute\u010dn\u00e9ho sv\u011bta. Do produkce nikdo nasazuje Hello World. Na\u0161e aplikace obvykle chod\u00ed do datab\u00e1ze nebo n\u011bkam jinam a v\u011bt\u0161inu \u010dasu \u010dek\u00e1 na odpov\u011b\u010f.<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/485f713c0284e16b0817500c8606c104.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\nJednodu\u0161e sed\u00ed a \u010dek\u00e1. To nen\u00ed moc dobr\u00e9. Kdy\u017e p\u0159ijde 100.000 u\u017eivatel\u016f, m\u00e1me to velmi t\u011b\u017ek\u00e9. Proto si v p\u0159\u00edkladu vytvo\u0159\u00edme jednoduchou aplikaci. Budeme hledat obr\u00e1zky, nap\u0159\u00edklad ko\u010dky. Jen\u017ee nebudeme hledat jen tak, budeme roz\u0161i\u0159ovat kl\u00ed\u010dov\u00e1 slova a pokud u\u017eivatel hledal \u201eko\u0165ata\u201c, najdeme mu ko\u010dky, chlupatce a dal\u0161\u00ed. Nejd\u0159\u00edve pot\u0159ebujeme z\u00edskat data dotazu na backendu. Vypad\u00e1 to takto:<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/a2134f86f15764745ae8330f63185367.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n <br \/>\nDva \u0159\u00e1dky v\u00e1m umo\u017en\u00ed zobrat GET parametry, \u017e\u00e1dn\u00e9 slo\u017eitosti. D\u00e1le nap\u0159\u00edklad z\u00edsk\u00e1v\u00e1me tuto informaci z datab\u00e1ze s tabulkou podle kl\u00ed\u010dov\u00e9ho slova a p\u0159\u00edpony b\u011b\u017en\u00fdm SQL dotazem. V\u0161echno je jednoduch\u00e9. Vypad\u00e1 to takto:<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/4543685dc907f30bba2a079a0fadad2c.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\nP\u0159ipojujeme knihovnu <code>resty.mysql<\/code>, kter\u00e1 u\u017e m\u00e1me v bal\u00ed\u010dku. Nic nemus\u00edme instalovat, v\u0161echno je hotov\u00e9. Uv\u00e1d\u00edme, jak se p\u0159ipojit, a d\u011bl\u00e1me SQL dotaz:<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/2234b3a5b2e1d8efafec00a49f1a13b0.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n <br \/>\nTady je to trochu d\u011bsiv\u00e9, ale v\u0161echno funguje. Zde 10 - to je limit. Z\u00edsk\u00e1v\u00e1me 10 z\u00e1znam\u016f, jsme l\u00edn\u00ed, nechceme zobrazovat v\u00edce. Na limit v SQL jsem zapomn\u011bl.<\/p>\n<p>D\u00e1le hled\u00e1me obr\u00e1zky podle v\u0161ech dotaz\u016f. Shroma\u017e\u010fujeme s\u00e9rii dotaz\u016f a vypl\u0148ujeme Lua tabulku, kter\u00e1 se naz\u00fdv\u00e1 <code>reqs<\/code>, a prov\u00e1d\u00edme <code>ngx.location.capture_multi<\/code>.<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/c18171845b3bd3872c4a7a7feae0d4bc.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\nV\u0161echny tyto dotazy jdou paraleln\u011b a vrac\u00ed se n\u00e1m odpov\u011bdi. \u010cas zpracov\u00e1n\u00ed je roven \u010dasu odpov\u011bdi nejpomalej\u0161\u00edho. Pokud se n\u00e1m v\u0161echny vr\u00e1t\u00ed b\u011bhem 50 milisekund, a poslali jsme stovku dotaz\u016f, pak odpov\u011b\u010f p\u0159ijde za 50 milisekund.<\/p>\n<p>Proto\u017ee jsme l\u00edn\u00ed a nechceme ps\u00e1t zpracov\u00e1n\u00ed HTTP a cachov\u00e1n\u00ed, p\u0159in\u00fat\u00edme NGINX, aby to v\u0161echno ud\u011blal za n\u00e1s. Jak jste vid\u011bli, byl tam dotaz na <code>url\/fetch<\/code>, to je ono:<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/ef8fcc6905b2860a7f214c41251582a1.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n <br \/>\nD\u011bl\u00e1me jednoduch\u00e9 <code>proxy_pass<\/code>, uv\u00e1d\u00edme, kam ukl\u00e1dat do cache, jak to ud\u011blat, a v\u0161echno n\u00e1m funguje.<\/p>\n<p>Ale to nesta\u010d\u00ed, mus\u00edme tak\u00e9 vr\u00e1tit data u\u017eivateli. Nejjednodu\u0161\u0161\u00ed my\u0161lenka - to v\u0161e serializovat do JSON, snadno, ve dvou \u0159\u00e1dc\u00edch. Vrac\u00edme Content-Type, vrac\u00edme JSON.<\/p>\n<p>Ale je tu jedna komplikace: u\u017eivatel nechce \u010d\u00edst JSON. Je t\u0159eba p\u0159it\u00e1hnout frontendov\u00e9 v\u00fdvoj\u00e1\u0159e. N\u011bkdy se n\u00e1m to na za\u010d\u00e1tku nechce d\u011blat. A SEO specialist\u00e9 \u0159eknou, \u017ee pokud hled\u00e1me obr\u00e1zky, je to jim jedno. Ale pokud n\u011bjak\u00fd obsah p\u0159ed\u00e1v\u00e1me, \u0159eknou, \u017ee na\u0161e vyhled\u00e1va\u010de nic neindexuj\u00ed.<\/p>\n<p>Co s t\u00edm d\u011blat? Samoz\u0159ejm\u011b, \u017ee budeme u\u017eivateli vracet HTML. Generovat to ru\u010dn\u011b - nen\u00ed to stylov\u00e9, tak\u017ee chceme pou\u017e\u00edt \u0161ablony. K tomu je tady knihovna <code>lua-resty-template<\/code>.<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/66a6cffc402575d286cb00d138dc201a.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\nUr\u010dit\u011b jste si v\u0161imli t\u0159\u00ed d\u011bsiv\u00fdch p\u00edsmen OPM. OpenResty p\u0159ich\u00e1z\u00ed se sv\u00fdm bal\u00ed\u010dkov\u00fdm mana\u017eerem, p\u0159es kter\u00fd lze nainstalovat je\u0161t\u011b spoustu r\u016fzn\u00fdch modul\u016f, konkr\u00e9tn\u011b <code>lua-resty-template<\/code>. Je to jednoduch\u00fd \u0161ablonov\u00fd engine, bl\u00edzk\u00fd Django templates. M\u016f\u017eete napsat k\u00f3d a prov\u00e9st substituci prom\u011bnn\u00fdch.<\/p>\n<p>V\u00fdsledkem bude v\u0161e vypadat p\u0159ibli\u017en\u011b takto:<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/b54497e4f1ab5a80183dc49c172a7f15.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n <br \/>\n\u00dadaje jsme vzali a zrenderovali \u0161ablonu op\u011bt ve dvou \u0159\u00e1dc\u00edch. U\u017eivatel je spokojen\u00fd, dostal ko\u010dky. Jeliko\u017e jsme roz\u0161\u00ed\u0159ili dotaz, dostal k kitten\u016fm nav\u00edc je\u0161t\u011b i mo\u0159sk\u00e9ho lva. Kdo v\u00ed, mo\u017en\u00e1 ho hledal pr\u00e1v\u011b tohoto, ale nedok\u00e1zal spr\u00e1vn\u011b formulovat sv\u016fj dotaz.<\/p>\n<p>V\u0161echno je skv\u011bl\u00e9, ale jsme p\u0159ece ve v\u00fdvoji a zat\u00edm nechceme u\u017eivatel\u016fm ukazovat. Ud\u011blejme tedy autorizaci. Abychom to provedli, pod\u00edvejme se, jak NGINX zpracov\u00e1v\u00e1 po\u017eadavek v term\u00ednech OpenResty:<\/p>\n<ul>\n<li>Prvn\u00ed f\u00e1ze\u00a0\u2014 <strong>access<\/strong>, kdy\u017e u\u017eivatel pr\u00e1v\u011b p\u0159i\u0161el a my jsme se na n\u011bj pod\u00edvali podle hlavi\u010dek, podle IP adresy, podle dal\u0161\u00edch \u00fadaj\u016f. M\u016f\u017eeme ho okam\u017eit\u011b od\u0159\u00edznout, pokud se n\u00e1m nel\u00edb\u00ed. To lze pou\u017e\u00edt pro autorizaci, nebo pokud k n\u00e1m p\u0159ich\u00e1z\u00ed spousta po\u017eadavk\u016f, m\u016f\u017eeme je snadno od\u0159\u00edznout v t\u00e9to f\u00e1zi.<\/li>\n<li><strong>rewrite<\/strong>. P\u0159episujeme n\u011bjak\u00e9 \u00fadaje po\u017eadavku.<\/li>\n<li><strong>content<\/strong>. Dod\u00e1v\u00e1me obsah u\u017eivateli.<\/li>\n<li><strong>headers filter<\/strong>. M\u011bn\u00edme z\u00e1hlav\u00ed odpov\u011bdi. Pokud jsme pou\u017eili <code>proxy_pass<\/code>, m\u016f\u017eeme p\u0159epsat n\u011bkter\u00e1 z\u00e1hlav\u00ed, ne\u017e je dod\u00e1me u\u017eivateli.<\/li>\n<li><strong>body filter<\/strong>. M\u016f\u017eeme zm\u011bnit t\u011blo.<\/li>\n<li><strong>log<\/strong>\u00a0\u2014 protokolov\u00e1n\u00ed. M\u016f\u017eeme zapisovat protokoly do elasticsearch bez dal\u0161\u00ed vrstvy.<\/li>\n<\/ul>\n<p>\nNa\u0161e autorizace bude vypadat zhruba takto:<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/f6c16665b75ce0fa0ee69e07ab6a4a61.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n <br \/>\nToto p\u0159id\u00e1me do toho <code>location<\/code>, kter\u00e9 jsme popsali d\u0159\u00edve, a vlo\u017e\u00edme tam takov\u00fd k\u00f3d:<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/126d8411c92afa92f3c4f5b9791b3e9c.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n <br \/>\nPod\u00edv\u00e1me se, jestli m\u00e1me cookie token. Pokud ne, pos\u00edl\u00e1me na autorizaci. U\u017eivatel\u00e9 jsou mazan\u00ed a mohou uhodnout, \u017ee je pot\u0159eba nastavit cookie token. Proto ji je\u0161t\u011b ulo\u017e\u00edme do Redis:<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/b876372412d648885c2f7d53e712a85b.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n <br \/>\nK\u00f3d pro pr\u00e1ci s Redis je velmi jednoduch\u00fd a nijak se neli\u0161\u00ed od ostatn\u00edch jazyk\u016f. V\u0161echny vstupy\/v\u00fdstupy jsou jak tam, tak i tady, neblokuj\u00edc\u00ed. Pokud p\u00ed\u0161ete synchronn\u00ed k\u00f3d, funguje asynchronn\u011b. P\u0159ibli\u017en\u011b jako s gevent, jen to je ud\u011bl\u00e1no dob\u0159e.<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/74066c9c750c718f368617faacbe0acc.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\nUd\u011bl\u00e1me tedy samotnou autorizaci:<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/0b3b486ca3c417716ebdaac189bfdcbf.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n <br \/>\n\u0158ekneme, \u017ee pot\u0159ebujeme \u010d\u00edst t\u011blo po\u017eadavku. Z\u00edsk\u00e1me POST argumenty, zkontrolujeme, \u017ee p\u0159ihla\u0161ovac\u00ed jm\u00e9no a heslo jsou spr\u00e1vn\u00e9. Pokud nejsou spr\u00e1vn\u00e9, pos\u00edl\u00e1me na autorizaci. A pokud jsou spr\u00e1vn\u00e9, zapisujeme token do Redis:<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/bcf470d84791b6d1d01152d5ad511dbd.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n <br \/>\nNezapom\u00ednejte nastavit cookie, to se tak\u00e9 d\u011bl\u00e1 ve dvou \u0159\u00e1dc\u00edch:<\/p>\n<p><img decoding=\"async\" alt=\"OpenResty: prom\u011b\u0148ujeme NGINX v plnohodnotn\u00fd aplika\u010dn\u00ed server\" src=\"\/wp-content\/uploads\/2020\/02\/efe06a113de28bacd14b26d6bb62a037.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\nP\u0159\u00edklad je jednoduch\u00fd, teoretick\u00fd. Samoz\u0159ejm\u011b nebudeme d\u011blat slu\u017ebu, kter\u00e1 lidem ukazuje ko\u010dky. A\u010dkoli kdo v\u00ed. Tak\u017ee projdeme, co lze ud\u011blat v produkci.<\/p>\n<ul>\n<li><strong>Minimalistick\u00fd backend<\/strong>. N\u011bkdy pot\u0159ebujeme v backendu poskytnout jen mal\u00e9 mno\u017estv\u00ed dat: n\u011bkde je pot\u0159eba doplnit datum, n\u011bkde vypsat n\u011bjak\u00fd seznam, \u0159\u00edct, kolik je te\u010f u\u017eivatel\u016f na webu, p\u0159ipojit po\u010d\u00edtadlo nebo statistiku. N\u011bco takov\u00e9ho men\u0161\u00edho. Minim\u00e1ln\u00ed kousky lze ud\u011blat velmi snadno. Na tom to p\u016fjde rychle, snadno a skv\u011ble.\n<\/li>\n<li><strong>P\u0159edzpracov\u00e1n\u00ed dat<\/strong>. N\u011bkdy bychom cht\u011bli integrovat do na\u0161\u00ed str\u00e1nky reklamu, p\u0159i\u010dem\u017e tuto reklamu bereme pomoc\u00ed API dotaz\u016f. To se d\u00e1 ud\u011blat pr\u00e1v\u011b tady velmi snadno. Nez\u00e1t\u011b\u017eujeme n\u00e1\u0161 backend, kter\u00fd u\u017e tak t\u011b\u017ece pracuje. M\u016f\u017eeme vz\u00edt a sestavit to tady. M\u016f\u017eeme slepit n\u011bjak\u00e9 JS nebo naopak rozd\u011blit, n\u011bco p\u0159edzpracovat, ne\u017e to p\u0159ed\u00e1me u\u017eivateli.\n<\/li>\n<li><strong>Fas\u00e1da pro mikroservis<\/strong>. To je tak\u00e9 velmi dobr\u00fd p\u0159\u00edpad, kter\u00fd jsem realizoval. P\u0159edt\u00edm jsem pracoval ve spole\u010dnosti Tenzor, kter\u00e1 se zab\u00fdv\u00e1 elektronick\u00fdm \u00fa\u010detnictv\u00edm a zaji\u0161\u0165uje \u00fa\u010detnictv\u00ed p\u0159ibli\u017en\u011b poloviny pr\u00e1vnick\u00fdch osob v zemi. Vytvo\u0159ili jsme slu\u017ebu, kde pomoc\u00ed tohoto mechanizmu bylo ud\u011bl\u00e1no mnoho v\u011bc\u00ed: sm\u011brov\u00e1n\u00ed, autorizace a dal\u0161\u00ed.<br \/>\nOpenResty lze pou\u017e\u00edt jako lepidlo pro va\u0161e mikroservisy, kter\u00e9 zajist\u00ed jednotn\u00fd p\u0159\u00edstup ke v\u0161emu a jednotn\u00ed rozhran\u00ed. Vzhledem k tomu, \u017ee mikroservisy mohou b\u00fdt naps\u00e1ny r\u016fzn\u011b, zde m\u00e1te Node.js, zde PHP, zde Python, zde n\u011bco na Erlangu, ch\u00e1peme, \u017ee nechceme p\u0159episovat stejn\u00fd k\u00f3d v\u0161ude. Proto lze OpenResty nasadit na frontend.<\/p>\n<\/li>\n<li><strong>Statistika a analytika<\/strong>. Obvykle je NGINX na vstupu a v\u0161echny dotazy jdou p\u0159es n\u011bj. Pr\u00e1v\u011b v tomto m\u00edst\u011b je velmi pohodln\u00e9 shrom\u00e1\u017edit data. M\u016f\u017eeme n\u011bco hned spo\u010d\u00edtat a n\u011bkam to poslat, nap\u0159\u00edklad do Elasticsearch, Logstash, nebo jen zapsat do logu a pak poslat n\u011bkam jinam.\n<\/li>\n<li><strong>Multiplayerov\u00e9 syst\u00e9my<\/strong>. Nap\u0159\u00edklad online hry se tak\u00e9 velmi dob\u0159e d\u011blaj\u00ed. Dnes v Kapsk\u00e9m M\u011bst\u011b bude Alexandr Hlady\u0161 vypr\u00e1v\u011bt, jak rychle prototypovat multiplayerovou hru pomoc\u00ed OpenResty.\n<\/li>\n<li><strong>Filtrace dotaz\u016f (WAF)<\/strong>. V dne\u0161n\u00ed dob\u011b je m\u00f3dou vytv\u00e1\u0159et r\u016fzn\u00e9 webov\u00e9 aplika\u010dn\u00ed firewally, existuje mnoho slu\u017eeb, kter\u00e9 je poskytuj\u00ed. Pomoc\u00ed OpenResty m\u016f\u017eete vytvo\u0159it webov\u00fd aplika\u010dn\u00ed firewall, kter\u00fd snadno a efektivn\u011b filtruje po\u017eadavky podle va\u0161ich pot\u0159eb. Pokud m\u00e1te Python, v\u00edte, \u017ee PHP nelze snadno injektovat, pokud ho samoz\u0159ejm\u011b nespust\u00edte z konzole. V\u00edte, \u017ee m\u00e1te MySQL a Python. Pravd\u011bpodobn\u011b se mohou pokusit prov\u00e9st n\u011bjak\u00fd directory traversal a injektovat n\u011bco do datab\u00e1ze. Proto je mo\u017en\u00e9 rychle a levn\u011b filtrovat podez\u0159el\u00e9 po\u017eadavky p\u0159\u00edmo na front-endu.\n<\/li>\n<li><strong>Komunita.<\/strong> Jeliko\u017e je OpenResty postaven na NGINX, m\u00e1 bonus \u2013 <strong>NGINX komunitu<\/strong>. Ta je velmi rozs\u00e1hl\u00e1 a zna\u010dn\u00e1 \u010d\u00e1st ot\u00e1zek, kter\u00e9 se v\u00e1m zpo\u010d\u00e1tku objev\u00ed, ji\u017e byla vy\u0159e\u0161ena komunitou NGINX.\n<p><strong>Lua v\u00fdvoj\u00e1\u0159i<\/strong>. V\u010dera jsem mluvil s lidmi, kte\u0159\u00ed p\u0159i\u0161li na vzd\u011bl\u00e1vac\u00ed den HighLoad++, a sly\u0161el jsem, \u017ee na Lua je naps\u00e1n pouze Tarantool. To ale nen\u00ed pravda, na Lua je naps\u00e1no hodn\u011b v\u011bc\u00ed. P\u0159\u00edklady: OpenResty, XMPP server Prosody, hern\u00ed engine Love2D, Lua m\u016f\u017ee b\u00fdt skriptov\u00e1na ve Warcraftu a na jin\u00fdch m\u00edstech. Lua v\u00fdvoj\u00e1\u0159\u016f je opravdu hodn\u011b, maj\u00ed velkou a aktivn\u00ed komunitu. V\u0161echny m\u00e9 dotazy ohledn\u011b Lua byly zodpov\u011bzeny b\u011bhem n\u011bkolika hodin. Kdy\u017e nap\u00ed\u0161ete na mailing list, doslova za n\u011bkolik minut u\u017e je spousta odpov\u011bd\u00ed, podrobn\u011b popisuj\u00ed, co a jak, co k \u010demu. To je skv\u011bl\u00e9. Bohu\u017eel, ne v\u0161ude je tak laskav\u00e1 a vst\u0159\u00edcn\u00e1 komunita.<br \/>\nK OpenResty existuje GitHub, kde m\u016f\u017eete zalo\u017eit issue, pokud n\u011bco nefunguje. Existuje mailing list na Google Groups, kde m\u016f\u017eete diskutovat o obecn\u00fdch ot\u00e1zk\u00e1ch, a je tak\u00e9 mailing list v \u010d\u00edn\u0161tin\u011b \u2013 kdo v\u00ed, mo\u017en\u00e1 anglicky nevl\u00e1dnete, ale \u010d\u00ednsky zn\u00e1te.<\/li>\n<\/ul>\n<p><\/p>\n<h1>Z\u00e1v\u011bry<\/h1>\n<p><\/p>\n<ul>\n<li>Douf\u00e1m, \u017ee jsem dok\u00e1zal sd\u011blit, \u017ee OpenResty je velmi pohodln\u00fd framework zam\u011b\u0159en\u00fd na web.<\/li>\n<li>M\u00e1 n\u00edzk\u00fd pr\u00e1h vstupu, proto\u017ee k\u00f3d se podob\u00e1 tomu, na \u010dem p\u00ed\u0161eme, jazyk je pom\u011brn\u011b jednoduch\u00fd a minimalistick\u00fd.<\/li>\n<li>Nab\u00edz\u00ed asynchronn\u00ed I\/O bez callback\u016f, nebudeme m\u00edt nudli, jak ji n\u011bkdy m\u016f\u017eeme napsat v NodeJS.<\/li>\n<li>M\u00e1 jednoduch\u00e9 nasazen\u00ed, proto\u017ee pot\u0159ebujeme pouze NGINX s pot\u0159ebn\u00fdm modulem a n\u00e1\u0161 k\u00f3d, a v\u0161e funguje hned.<\/li>\n<li>Velk\u00e1 a vst\u0159\u00edcn\u00e1 komunita.<\/li>\n<\/ul>\n<p>\nNedok\u00e1zal jsem podrobn\u011b popsat, jak se d\u011bl\u00e1 routov\u00e1n\u00ed, dostalo by se to do velmi dlouh\u00e9ho vypr\u00e1v\u011bn\u00ed.<\/p>\n<p>D\u011bkujeme za pozornost!<\/p>\n<p><center><div class=\"youtube-placeholder\" data-id=\"silrEB0Brvo\" onclick=\"loadVideo(this)\">\r\n        <img decoding=\"async\" src=\"https:\/\/img.youtube.com\/vi\/silrEB0Brvo\/hqdefault.jpg\" alt=\"P\u0159ehr\u00e1t video\" loading=\"lazy\" width=\"480\" height=\"360\" style=\"width:100%;height:auto;\">\r\n        <div class=\"play-button\"><\/div>\r\n    <\/div><\/center><br \/>\n<em><noindex><a rel=\"nofollow\" href=\"http:\/\/www.highload.ru\/2016\/abstracts\/2432.html\">Vladimir Protasov \u2013 OpenResty: m\u011bn\u00edme NGINX na plnohodnotn\u00fd aplika\u010dn\u00ed server<\/a><\/noindex><\/em><br \/>\n<br \/>Zdroj: <a content=\"nofollow\" rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/post\/321864\/\">habr.com<\/a> <\/p>","protected":false,"gt_translate_keys":[{"key":"rendered","format":"html"}]},"excerpt":{"rendered":"<p>\u041c\u044b \u0432\u043d\u043e\u0432\u044c \u043f\u0443\u0431\u043b\u0438\u043a\u0443\u0435\u043c \u0440\u0430\u0441\u0448\u0438\u0444\u0440\u043e\u0432\u043a\u0443 \u0434\u043e\u043a\u043b\u0430\u0434\u0430 \u0441 \u043a\u043e\u043d\u0444\u0435\u0440\u0435\u043d\u0446\u0438\u0438 HighLoad++ 2016, \u043a\u043e\u0442\u043e\u0440\u0430\u044f \u043f\u0440\u043e\u0445\u043e\u0434\u0438\u043b\u0430 \u0432 \u043f\u043e\u0434\u043c\u043e\u0441\u043a\u043e\u0432\u043d\u043e\u043c \u0421\u043a\u043e\u043b\u043a\u043e\u0432\u043e 7\u20148 \u043d\u043e\u044f\u0431\u0440\u044f \u043f\u0440\u043e\u0448\u043b\u043e\u0433\u043e \u0433\u043e\u0434\u0430. \u0412\u043b\u0430\u0434\u0438\u043c\u0438\u0440 \u041f\u0440\u043e\u0442\u0430\u0441\u043e\u0432 \u0440\u0430\u0441\u0441\u043a\u0430\u0437\u044b\u0432\u0430\u0435\u0442, \u043a\u0430\u043a \u0440\u0430\u0441\u0448\u0438\u0440\u0438\u0442\u044c \u0444\u0443\u043d\u043a\u0446\u0438\u043e\u043d\u0430\u043b\u044c\u043d\u043e\u0441\u0442\u044c NGINX \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e OpenResty \u0438 Lua. \u0412\u0441\u0435\u043c \u043f\u0440\u0438\u0432\u0435\u0442, \u043c\u0435\u043d\u044f \u0437\u043e\u0432\u0443\u0442 \u0412\u043b\u0430\u0434\u0438\u043c\u0438\u0440 \u041f\u0440\u043e\u0442\u0430\u0441\u043e\u0432, \u044f \u0440\u0430\u0431\u043e\u0442\u0430\u044e \u0432 Parallels. \u0420\u0430\u0441\u0441\u043a\u0430\u0436\u0443 \u0447\u0443\u0442\u044c-\u0447\u0443\u0442\u044c \u043e \u0441\u0435\u0431\u0435. \u0422\u0440\u0438 \u0447\u0435\u0442\u0432\u0435\u0440\u0442\u0438 \u0441\u0432\u043e\u0435\u0439 \u0436\u0438\u0437\u043d\u0438 \u044f \u0437\u0430\u043d\u0438\u043c\u0430\u044e\u0441\u044c \u0442\u0435\u043c, \u0447\u0442\u043e \u043f\u0438\u0448\u0443 \u043a\u043e\u0434. \u0421\u0442\u0430\u043b [&hellip;]<\/p>\n","protected":false,"gt_translate_keys":[{"key":"rendered","format":"html"}]},"author":1,"featured_media":71379,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[688],"tags":[],"class_list":["post-71378","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-administrirovanie"],"aioseo_notices":[],"aioseo_head":"\n\t\t<!-- All in One SEO 5.0.3 - aioseo.com -->\n\t<meta name=\"description\" content=\"\u041c\u044b \u0432\u043d\u043e\u0432\u044c \u043f\u0443\u0431\u043b\u0438\u043a\u0443\u0435\u043c \u0440\u0430\u0441\u0448\u0438\u0444\u0440\u043e\u0432\u043a\u0443.\" \/>\n\t<meta name=\"robots\" content=\"max-image-preview:large\" \/>\n\t<meta name=\"author\" content=\"Yuri Gagarin\"\/>\n\t<link rel=\"canonical\" href=\"https:\/\/prohoster.info\/cs\/blog\/administrirovanie\/openresty-prevrashhaem-nginx-v-polnoczennyj-server-prilozhenij\" \/>\n\t\t<meta name=\"generator\" content=\"All in One SEO (AIOSEO) 5.0.3\" \/>\n\t\t<meta property=\"og:locale\" content=\"cs_CZ\" \/>\n\t\t<meta property=\"og:site_name\" content=\"ProHoster | \u041a\u0443\u043f\u0438\u0442\u044c \u043d\u0430\u0434\u0435\u0436\u043d\u044b\u0439 \u0445\u043e\u0441\u0442\u0438\u043d\u0433 \u0434\u043b\u044f \u0441\u0430\u0439\u0442\u043e\u0432 \u0441 \u0437\u0430\u0449\u0438\u0442\u043e\u0439 \u043e\u0442 DDoS, VPS VDS \u0441\u0435\u0440\u0432\u0435\u0440\u044b\" \/>\n\t\t<meta property=\"og:type\" content=\"article\" \/>\n\t\t<meta property=\"og:title\" content=\"\ud83e\udd47OpenResty: \u043f\u0440\u0435\u0432\u0440\u0430\u0449\u0430\u0435\u043c NGINX \u0432 \u043f\u043e\u043b\u043d\u043e\u0446\u0435\u043d\u043d\u044b\u0439 \u0441\u0435\u0440\u0432\u0435\u0440 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0439 | ProHoster\" \/>\n\t\t<meta property=\"og:description\" content=\"\u041c\u044b \u0432\u043d\u043e\u0432\u044c \u043f\u0443\u0431\u043b\u0438\u043a\u0443\u0435\u043c \u0440\u0430\u0441\u0448\u0438\u0444\u0440\u043e\u0432\u043a\u0443.\" \/>\n\t\t<meta property=\"og:url\" content=\"https:\/\/prohoster.info\/cs\/blog\/administrirovanie\/openresty-prevrashhaem-nginx-v-polnoczennyj-server-prilozhenij\" \/>\n\t\t<meta property=\"og:image\" content=\"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg\" \/>\n\t\t<meta property=\"og:image:secure_url\" content=\"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg\" \/>\n\t\t<meta property=\"og:image:width\" content=\"350\" \/>\n\t\t<meta property=\"og:image:height\" content=\"350\" \/>\n\t\t<meta property=\"article:published_time\" content=\"2020-02-25T17:45:02+00:00\" \/>\n\t\t<meta property=\"article:modified_time\" content=\"2020-03-03T13:14:21+00:00\" \/>\n\t\t<meta property=\"article:publisher\" content=\"https:\/\/www.facebook.com\/prohoster\" \/>\n\t\t<meta property=\"article:author\" content=\"https:\/\/www.facebook.com\/prohoster\" \/>\n\t\t<!-- All in One SEO -->\n\n","aioseo_head_json":{"title":"\ud83e\udd47OpenResty: p\u0159etv\u00e1\u0159\u00edme NGINX na plnohodnotn\u00fd aplika\u010dn\u00ed server | ProHoster","description":"Op\u011bt zve\u0159ej\u0148ujeme p\u0159epis.","canonical_url":"https:\/\/prohoster.info\/cs\/blog\/administrirovanie\/openresty-prevrashhaem-nginx-v-polnoczennyj-server-prilozhenij","robots":"max-image-preview:large","keywords":"","webmasterTools":{"miscellaneous":""},"schema":null,"og:locale":"cs_CZ","og:site_name":"ProHoster | \u041a\u0443\u043f\u0438\u0442\u044c \u043d\u0430\u0434\u0435\u0436\u043d\u044b\u0439 \u0445\u043e\u0441\u0442\u0438\u043d\u0433 \u0434\u043b\u044f \u0441\u0430\u0439\u0442\u043e\u0432 \u0441 \u0437\u0430\u0449\u0438\u0442\u043e\u0439 \u043e\u0442 DDoS, VPS VDS \u0441\u0435\u0440\u0432\u0435\u0440\u044b","og:type":"article","og:title":"\ud83e\udd47OpenResty: \u043f\u0440\u0435\u0432\u0440\u0430\u0449\u0430\u0435\u043c NGINX \u0432 \u043f\u043e\u043b\u043d\u043e\u0446\u0435\u043d\u043d\u044b\u0439 \u0441\u0435\u0440\u0432\u0435\u0440 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0439 | ProHoster","og:description":"\u041c\u044b \u0432\u043d\u043e\u0432\u044c \u043f\u0443\u0431\u043b\u0438\u043a\u0443\u0435\u043c \u0440\u0430\u0441\u0448\u0438\u0444\u0440\u043e\u0432\u043a\u0443.","og:url":"https:\/\/prohoster.info\/cs\/blog\/administrirovanie\/openresty-prevrashhaem-nginx-v-polnoczennyj-server-prilozhenij","og:image":"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg","og:image:secure_url":"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg","og:image:width":350,"og:image:height":350,"article:published_time":"2020-02-25T17:45:02+00:00","article:modified_time":"2020-03-03T13:14:21+00:00","article:publisher":"https:\/\/www.facebook.com\/prohoster","article:author":"https:\/\/www.facebook.com\/prohoster"},"aioseo_meta_data":{"post_id":"71378","title":null,"description":null,"keywords":null,"keyphrases":null,"primary_term":null,"canonical_url":null,"og_title":null,"og_description":null,"og_object_type":"default","og_image_type":"default","og_image_url":null,"og_image_width":null,"og_image_height":null,"og_image_custom_url":null,"og_image_custom_fields":null,"og_video":null,"og_custom_url":null,"og_article_section":null,"og_article_tags":null,"twitter_use_og":false,"twitter_card":"default","twitter_image_type":"default","twitter_image_url":null,"twitter_image_custom_url":null,"twitter_image_custom_fields":null,"twitter_title":null,"twitter_description":null,"schema":{"blockGraphs":[],"customGraphs":[],"default":{"data":{"Article":[],"Course":[],"Dataset":[],"FAQPage":[],"Movie":[],"Person":[],"Product":[],"ProductReview":[],"Car":[],"Recipe":[],"Service":[],"SoftwareApplication":[],"WebPage":[]},"graphName":"","isEnabled":true},"graphs":[]},"schema_type":null,"schema_type_options":null,"pillar_content":false,"robots_default":true,"robots_noindex":false,"robots_noarchive":false,"robots_nosnippet":false,"robots_nofollow":false,"robots_noimageindex":false,"robots_noodp":false,"robots_notranslate":false,"robots_max_snippet":null,"robots_max_videopreview":null,"robots_max_imagepreview":"large","priority":null,"frequency":null,"local_seo":null,"seo_analyzer_scan_date":null,"breadcrumb_settings":null,"limit_modified_date":false,"reviewed_by":null,"ai":null,"created":"2021-02-28 19:03:22","updated":"2022-09-30 08:39:30","focus_keyword":null,"additional_keywords":null,"truseo_locale":null},"gt_translate_keys":[{"key":"link","format":"url"}],"_links":{"self":[{"href":"https:\/\/prohoster.info\/cs\/wp-json\/wp\/v2\/posts\/71378","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/prohoster.info\/cs\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/prohoster.info\/cs\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/prohoster.info\/cs\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/prohoster.info\/cs\/wp-json\/wp\/v2\/comments?post=71378"}],"version-history":[{"count":0,"href":"https:\/\/prohoster.info\/cs\/wp-json\/wp\/v2\/posts\/71378\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/prohoster.info\/cs\/wp-json\/wp\/v2\/media\/71379"}],"wp:attachment":[{"href":"https:\/\/prohoster.info\/cs\/wp-json\/wp\/v2\/media?parent=71378"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/prohoster.info\/cs\/wp-json\/wp\/v2\/categories?post=71378"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/prohoster.info\/cs\/wp-json\/wp\/v2\/tags?post=71378"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}