neděle 30. července 2017

Google Cloud a Node.js


V minlém článku jsem představoval Next.js. Dneska bych se chtěl zaměřit na to, jak samotné Next.js provozovat v Google Cloudu. Kromě samotného Next.js / Node.js si ukážeme i možnost, jak horizontálně škálovat naší novou aplikaci.

Cloud vs In-House

V případě, že v roce 2017 zvolíte In-House vývoj, musíte k tomu mít sakra velký důvod. Existuje snad pouze jedna výhoda a tou je fakt, že máte data tam, kde je přesně chcete mít. Tedy v případě cloudu jste často limitováni v tom, kde vaše data leží.

Pokud si ovšem umíte obhájit to, že data máte v cloudu (např s podporou tokenizace), tak neexistuje žádný další důvod, používat vlastní servery. Použití vlastních serverů je stejné, jako běžet maraton s batohem plným kamení.

Ve chvíli, kdy mluvíme o cloudu jako je AWS, Azure či Google, tak mluvíme hlavně o ekosystému kolem. Jestli v cloudu využíváte pouze virtualizaci serverů a zbytek si řešíte sami, vězte, že to děláte špatně.

Stačí, když si zodpovíte na tyto otázky:
  1. Jak řešíte deploy aplikací?
  2. Jak řešíte logování?
  3. Jak řešíte monitoring?
  4. Jak řešíte databázi?
  5. Jak řešíte škálování (vertikální i horizontální)?
  6. Jak spravujete load balancing?
  7. Umíte jednoduše část svých requestů přesměrovávat na nové verze?
  8. Jak řešíte bezvýpadkové nasazení?
Pokud vaší odpovědí je všude cloud služba, gratuluji. Pokud ne, tak jaký je důvod, že si to řešíte sami? Není to náhodou neznalostí cloud služeb? Nebo je důvodem to, že používáte cloud od firmy, která poskytuje pouze virtualizaci? Buďte chytří. Tím, že zvolíte jedno z tria AWS, Azure či Google, si můžete dost svojí práci zjednodušit.

Google Cloud

V době, kdy jsem technologicky stavěl startup, tak jsme se shodli na tom, že vše bude v cloudu. Rovnou jsme tím zavrhli, že bychom v budoucnu řešili lokální nasazení, protože by to znamenalo extrémní nároky na infrastrukturu a vývoj.

V té době byla moje znalost cloud služeb dost omezená a žil jsem v tom, že si rozjedeme vlastní virtuální servery a tam si vše budeme spravovat sami.

Proto první volba padla na Compute Engine, což jsou samotné virtuální servery, kde si "naklikáte" vhodnou Linux distribuci a pomocí SSH konzole doinstalujete vše potřebné.

I když tímto způsobem můžete uspět, bude vás stát mnoho úsilí, abyste si vytvořili správnou infrastrukturu a byli schopni spravovat více tenantů, logování, monitoring, škálování, apod.

Díky tomu, že jsem velký odpůrce hesla: "Nesahej na to, co funguje". Tak jsem stále hledal způsob, jak to udělat jinak.

Tou variantou je App Engine....

App Engine

App Engine je platforma, která slouží k tomu, že vám sama bude spravovat vaší aplikaci. K tomuto účelu si sama umí vytvořit Docker kontejnery, které spouští a spravuje.

Abychom správně pochopili, jak App Engine funguje, je třeba si danou platformu rozdělit na několik částí.

App Engine - Services

Služby, dříve nazývány jako Moduly, jsou základní hlavní částí. Službu si můžete libovolně pojmenovat a současně s tím nastavit i routování na vlastní domény.

Aby to bylo lépe pochopitelné, tak si představte, že máte dvě aplikace. Backend a Frontend. Každá z nich bude nahrána do vlastní služby.

Kromě tohoto dělení, můžete zvolit i jiné. My jsme například služby využili tak, že každý tenant běží pod vlastní službou. Tedy Firma A je pod službou firma-a a Firma B je pod službou firma-b. Když k tomu použijete správné routování služeb, tak jednotlivé firmy budou vystupovat pod vlastní doménou třetího řádu. Tedy: firma-a.vasedomena.cz.

App Engine - Versions

Verze je podskupina služby. Představte si, že jste právě nahráli svou novou aplikaci. Vše funguje jak má a vy jste mezitím vytvořili novou verzi. Nová verze byla otestována a dostala nálepku "production ready".

Pokud využívate verze v App Engine, máte nyní několik možností:
  1. Po nasazení vypne původní verzi a nová verze se stane výchozí
  2. Po nasazení bude neaktivní a spustí se až na manuální zásah
  3. Po nasazení přesměruje třeba 10% requestů a zjistí se, zda na produkci nezpůsobuje problém
Toto je vlastnost, kterou na App Engine miluji. Máte velice jednoduše pod správou to, jak se budete chovat k novým verzím vaší aplikace.

App Engine - Instances

Instance jsou poslední částí skládanky. Nyní už víme, že naše aplikace beží pod službou X, má třeba dvě verze 1.1 a 1.2, kde se na verzi 1.2 přesměrovává 30% requestů.

Nyní přišel čas na vertikální a horizontální škálování. Při nasazení aplikace máte možnost si zvolit to, kolik instancí bude existovat. Min/Max. Máte například Node.js backend server, který má vysoký traffic a nároky na výkon. Nastavíte mu 3/20 instancí + lepší procesor + větší pamět. Tedy minimálně tři instance, maximálně 20. V případě frontentu to například bude 2/5 + slabší procesor + méně paměti. Asi každý si dovede představit tu úžasnou variabilitu.

Přesně tímto způsobem spravujeme Node.js. Pokud by se mě někdo zeptal na to, jak spravovat Node.js v produkci, toto je odpověď. Byla by hloupost, kdybychom se snažili ladit Node.js v produkci přes PM2, apod. Nikdy se nedostaneme do takového stavu. Zjednodušeně řečeno: "Lidé z Google vědí lépe, jak Node.js nastavit". Já jim pouze deklarativně řeknu, co od toho očekávám.

App Engine - Další možnosti

App Engine toho nabízí samozřejmě mnohem více. Ať už je to samotný monitoring (služeb, verzí či instancí), tak jsou zde takové věci jako je podpora logování do Stackdriver Logging, Cache, sdílené Sessions, apod.

Třešničkou na dortu mohou být různé kvóty na zdroje, vypínaní v čase, apod.

Node.js v Google Cloudu

Nyní se pojďme již konkrétně podívat na to, jak rozeběhnout Node.js v App Engine. Nejprve popíši celé flow a poté si ukážeme samotné kroky:
  1. Mám webovou aplikaci napsanou v Reactu přes Next.js. 
  2. Celý stack je následující: Typescript, React, Redux, Next.js. 
  3. Zdrojové soubory aplikace jsou uložené v GITu přes Bitbucket.
  4. V Google Cloudu je zrcadlení Bitbucketu do Source Repositories.
  5. Poté se v cloud konzoli provede checkout projektu a samotný deploy
  6. To je vše :)
Samotný deploy aplikace lze samozřejmě automatizovat. Ať už pomocí Bitbucket Pipelines či pomocí Jenkinse. Osobně čekám na to, až bude k dispozici API k AppEngine v google-cloud-node. Dokonce jsem před pár dny položil dotaz na vývojáře, kdy toto bude k dispozcici. Důvod proč bych rád toto API zde měl, je ten, že bych v budoucnu rád dělal deploy přes Cloud Lambda Functions, což vnímám jako optimální variantu.

V minulém článku jsem popisoval jak funguje Next.js s Typescriptem. Takže tento krok rovnou přeskočme. Podívejme se raději na to, jak provést samotný deploy.

Nejprve zmíním, že deploy můžete provést i z lokálního stroje. K tomuto účelu vám stačí nainstalovat si gcloud konzoli a v ní se autorizovat. Poté můžete ovládat cloud ze své konzole pomocí příkazu gcloud.

Aby byl deploy úspěšný, musíte ve svém projektu mít soubor app.yaml, který popisuje základní konfiguraci pro AppEngine. Pokud tento soubor nevytvoříte, tak AppEngine si vytvoří vlastní a aplikaci automaticky nahraje do služby s názvem default.

Ukázka, jak může takový jednoduchý app.yaml vypadat:
env: flex
runtime: nodejs
service: firma-a
Pokud vás zajímá, co vše se dá nastavit, doporučuji se podívat do manuálu.

Další věcí je konfigurace samotného package.json.

Zde je ukázka package.json pro Next.js s Typescriptem:
{
  "name": "@irminsul.cz/test_nextjs",
  "version": "1.0.0",
  "author": "Ales Dostal",
  "scripts": {
    "create-build-id": "node -e \"process.stdout.write(require('./package.json').version)\" > dist/.next/BUILD_ID;",
    "prebuild": "tsc && cp -R static dist/",
    "build": "next build dist",
    "predev": "tsc && cp -R static dist/",
    "dev": "concurrently \"tsc --watch\" \"next dist\"",
    "start": "npm run build && npm run create-build-id && next start dist -p 8080",
    "tslint": "tslint -c tslint.json -p tsconfig.json",
    "deploy": "gcloud app deploy --project apitree-test --version 1-0-0"
  },
  "dependencies": {
    "@types/node": "^8.0.8",
    "@types/react": "^15.0.35",
    "concurrently": "^3.5.0",
    "next": "^2.4.7",
    "react": "^15.6.1",
    "react-dom": "^15.6.1",
    "tslint": "^5.5.0",
    "tslint-react": "^3.0.0",
    "typescript": "^2.4.1"
  },
  "engines": {
    "node": ">=8.0.0"
  }
}
Je zde několik důležitých věcí, na které nesmíte nezapomenout.

V package.json se definuje verze node.js, na které naše instance poběží. V tomto případě můžete vidět, že jsme zvolili verzi Node.JS 8 nebo vyšší.

Dále je důležité mít ve scripts správně pojmenované commandy. Tím hlavním je "start". AppEngine se totiž bude snažit přesně tento command spustit. S tím souvisí i nutnost samotného portu. Pokud necháme výchozí nastavení, bude AppEngine čekat, že naše aplikace běží na portu 8080.

Pro to, aby v AppEngine správně běžel Next.js, je nutné zde provést jeden drobný hack. Tím hackem je nastavení BUILD_ID. Důvod proč, je ten, že pokud máte více instancí než jednu, tak by vaše aplikace mohla náhodně končit chybou. Více se dozvíte z následujícího issue.

V package.json můžete najít i samotný command pro deploy. Když se na něj podíváte blíže, tak si můžete všimnout, že definuje v jakém projektu bude nasazen a v jaké verzi. Projektem se zde míní hlavní projekt v Google Cloudu.

Nyní už nezbývá než spustit samotný deploy:
npm run deploy

Pokud jste vše nastavili správně, tak gcloud konzole provede následující:
  1. Stáhne si k sobě zdrojové soubory
  2. Vytvoří Docker kontejner s Node.js 8 a vyšší
  3. Nasadí do AppEngine
  4. Spustí na službě "firma-a"
  5. Pod verzí 1-0-0
  6. Spustí npm install
  7. Spustí npm start
  8. V tomto výchozím nastavení použije min 2 instance pro Node.JS

Závěr

Popsat, co všechno Google Cloud umí a to zejména App Engine by bylo příliš vyčerpávající. Tento popis berte jako jeden z návodů, jak rozeběhnout svojí aplikaci na platformě, která vás dostatečně odstíní od nutnosti ručně spravovat Node.js server ve vlastním virtuálním serveru.
Dále je nutné zmínit i to, že Google na svém Cloudu stále pracuje. Proto jsou některé jejich služby v Beta verzích, čímž znemožňují vše využít na 100%. Nicméně tím, že vývoj na této platformě jde rychle dopředu, tak bych se příliš neobával toho, že například tento způsob provozování Node.JS aplikací by byl nepoužitelný. Právě naopak.

A co vy? Už jste přešli na služby v cloudu?

pondělí 24. července 2017

Jak si v IT vydělat hodně peněz?

Na začátek by bylo dobré, abych objasnil samotný titulek, který může na někoho působit jako červený hadr. Článek nebude o obecných pravidlech, ale bude vyprávět můj vlastní příběh, na kterém vám zkusím ukázat, jak se dá docílit úspěchu, či alespoň správně nastartovat svojí vlastní kariéru v IT.

I když se z názvu článku dá dedukovat, že se vše bude točit kolem peněz, není tomu tak. Alespoň ze dvou třetin určitě ne. Ale to už předbíhám, pojďme to raději vzít hezky popořadě...

Kdybychom měli mluvit o roce 2017 jako o přelomové době, nejspíše to nebude pravda. I když pro někoho to může být rok plný úspěchů a štěstí v podobě narození zdravých dětí, svatby či první velké lásky, tak z pohledu lidstva se jedná o rok, který jen kopíruje předešlé a v oblasti technologií nás posouvá stejným tempem jako rok předtím.

Jsem naprosto přesvědčen o tom, že i když se současná doba tak nenazývá, tak prožíváme dobu, která jednou bude označena za revoluční, a to zejména díky vynálezu internetu, který je stále ještě v plenkách. Naše generace prožívá změny, které jsou tak velké, že se s nimi často neumíme ani pořádně sžít. Už samotný vznik mobilních telefonů či sociálních sítí nás naprosto změnil. I když se často mluví o tom, že to má negativní vliv na lidstvo, nemyslím si, že by to bylo tak tragické. S těmito vynálezy, byť v pozměněné formě, se budeme muset pouze naučit žít a vědět, jak je využít ke svému prospěchu.

V digitálním věku vznikl jeden fenomén a tím, jsou všeobecně ajťáci nebo chcete-li konkrétněji programátoři, kteří tvoří něco, co je často nehmotné a těžko uchopitelné. Lidé jim často nerozumí a jejich práci považují za něco nadpozemského, co je mimo běžné chápání. Ať to zní sebepodivněji, tak tento pohled je naprosto běžný. Na základě těchto představ si často lidé ajťáka představí jako podivína s patnácti dioptriemi, mastným vlasem a absencí holky :)

Kromě tohoto zesměšňování, kterému se i já rád sám zasměji, se ještě o ajťácích ví, že berou "slušný prachy". Nejednou můžete někde zaslechnout něco jako: "Kamarád mého kamarádá má kamaráda a ten se zná s programátorem, co bere sto litrů měsíčně někde v bance." Naši rodiče říkávali: "Až vyrosteš budeš doktorem či právníkem, ty se mají dobře.". Dneska byste spíše zaslechli: "Rád bych své děti dal někam na počítače, ajťáci dneska vydělávají spousty peněz.".

Takže jsme se od řezníků, právníků či doktorů, dostali k ajťákům, kteří dnes často mají nejlukrativnější práci ze všech. Abyste se ale do této pozice dostali, nestačí jen chtít, musí tam být i něco víc.

Proto se tedy pojďte se mnou podívat na můj příběh....

Jako malý kluk jsem se často vymykal bežným standardům. Nejenže jsem byl vždy větší jak učitel či učitelka, ale zejména pro to, že mě škola naprosto nebavila a i když to možná zní divně, tak dodnes mám averzi vůči škole.

V době, kdy jsem začal chodit na základní školu, vládnul zde ještě komunismus. Respektive socialismus, který nám jasně určoval co smíme, co nesmíme a čím v budoucnu budeme muset nejspíše být. Pokud jste na základní škole neměli dobré známky, mělo se za to, že jste hlupáci a vaše budoucí povolání bude muset být buď zedník či obráběč kovů. Tedy měli byste jít na učňák a pak do fabriky, kde budete 8 hodin denně stát u stroje.

Jelikož jsem na základní škole příliš nevynikal, měla tahle budoucnost čekat i mě. Však jsem byl dítě, které mělo v první třídě v pololetí známku 3, což znamenalo, že bych se spíše hodil do zvláštní školy. Dokonce o to byl i pokus, abych tam skončil. Naštěstí psycholožka, která měla určit mou budoucnost, řekla, že jsem nadprůměrně inteligentní, akorát hrozně líný. Ta známka tedy byla více způsobena tím, že mě soudružka učitelka neměla moc v oblibě.

Ta lenost se se mnou táhla i dál. V osmé třídě jsem měl čtyřky snad ze všech předmětů, takže bych měl skončit spíše jako pomocník šikovnému zedníkovi. Díky mým rodičům se ovšem nic takového nestalo. Takže, ač jsem se hlásil na střední školu elektrotechnickou, skončil jsem na soukromé chemické, kde moje známky přiliš neřešili.

V té době jsem se začal zajímat o to, jak třeba funguje televize. Nejlepší způsob byl, že jsem jí rozebral. Skvělé, avšak problém byl, že jsem nevěděl, jak ji zase složit. Podobných pokusů jsem jako dítě udělal spousty. Často s negativním výsledkem, protože znalost, která mi chyběla, mi nedovolila můj cíl dokončit.

Střední škola s sebou přinesla jednu věc, která ovlivnila můj další život. Tou věcí byl počítač. V prváku na střední jsem dostal svůj první počítač 286, což i na tu dobu byl už docela historický stroj.

A co s takovým počítačem dělat, když je vám cca 14 let? No přece budete hrát hry. A to jsem přesně dělal. Hraní her byla zábava, kterou jsem do té doby znal jen z maringotek, když k nám přijela pouť a vy jste si za korunu či dvě mohli zahrát svou oblíbenou hru.

Nicméně kromě hraní her mě zajímalo i to, jak to vlastně funguje. Takže jsem opět rozebral počítač a podíval se na něj blíže. Tenkrát se mi podařilo ho sice složit, ale to mi nestačilo. Zjistil jsem, že existuje jakýsi BIOS a v tom se prý dá něco nastavit a třeba ho i zrychlit. Tak jsem nelenil a jal se provést novou konfiguraci. Výsledek? Počítač nefungoval. Musel jsem do nejbližšího krámku s výpočetní technikou, kde mi jeden starší pán pomohl a věnoval mi celý den, aby můj stroj zase uvedl do chodu. A cena? Nic. Jsem rád, že se o to zajímáš, jen v tom pokračuj. Tohle byste dneska už asi nezažili.

Jak jsem získával znalosti, začal jsem i více rozumět tomu, co dělám. Takže jsem se naučil nastavovat lépe konvenční pamět, aby mi fungovala nová hra, či jsem si psal jednoduché skripty v basicu, které sloužily pro různé drobné účely.

Ač se to zdá jako malichernost, přesně tohle byla ta doba, kdy jsem v sobě objevil svou vlastnost, o které jsem do té doby neměl ponětí. Tou vlastností bylo to, že mě hrozně bavilo věci zkoumat a učit se je. Splněný cíl byl jen třešnička na dortu. Byl to skvělý pocit, že fungovalo to, co jsem si přál, aby fungovalo. Nicméně tím cílem byla víc ona cesta.

A to je přesně první část k úspěchu. Pokud chcete dosáhnout úspěchu, musí vás v první řadě bavit samotná cesta. Nakonec zjistíte, že ač máte svůj cíl, tak ve skutečnosti je tím cílem ona cesta.

V IT a vůbec v jakékoli oblasti nemůže člověk uspět, pokud ho nebaví samotná cesta. To poznání je onou drogou. To zkoumání je to, co vás motivuje.

Pokud tohle v sobě nemáte, bude pro vás cokoli dalšího mnohem těžší. Každý máme své okruhy zájmů a pokud to není IT, tak v IT prostě a jednoduše nedělejte. Nestojí to za to. Věřte, že peníze se dají vydělat i jinde. Ale v první řadě hledejte to, co vás skutečně baví.

Střední školou jsem tak nějak proplul a zázrakem dokončil i maturitu. I když známky opět kopírovaly můj běžný standard, tedy žádný zázrak.

Poté jsem chtěl splnit sen rodičů. Půjdu na vysokou školu a budu mít titul.

Bohužel jsem se sice na vysokou školu dostal, ale hned od začátku jsem věděl, že tam nechci být. Nebaví mě to. Počítače máme jednou týdně a ještě tam píšeme v Pascalu diferenciální rovnice, což mně nepřipadalo nijak zajímavé.

Takže jsem opět jako student selhal a odešel. Abych alespoň částečně splnil sen rodičů, šel jsem na vyšší odbornou školu. Pravdou je, že to byla další ztráta mého času, a proto jsem se víc věnoval zábavě v podobě hospody či hraní her. Sice jsem už studoval školu zaměřenou na počítače, ale měli jsme i předměty jako byla ekonomie či právo. Sakra, jak mě to nebavilo.

Jediné, na co jsem se těšil byly počítače, protože v učebnách byly výkonnější stroje a daly se tam hrát lepší hry. To, co jsme tam probírali bylo tak nudné, že jsem to stejně neposlouchal. Nicméně jsem neměl problém projít zkouškou. Prostě a jednoduše, měl jsem už dřívějška tolik znalostí, že jsem to často ani poslouchat nemusel.

Na škole jsem strávil 3 roky a ani jí nedokončil. Nejdříve jsem propadnul a poté se nechal vyhodit, protože už jsem věděl co chci dělat.

V té době jsem si od kamaráda půjčil knížku o PHP. Měl jsem totiž plán, že si napíšu vlastní knihu návštěv. Samozřejmě už jsem měl své webové stránky, jenže byly statické a to mi přišlo málo.

Ta knížka mě chytla a to tolik, že jsem si jí bral i do školy a tajně jí četl pod lavicí, místo abych věnoval pozornost výkladu.

Tak jsem byl vyhozen. Neudělal jsem zkoušku z práva, což byl okrajový předmět, který jsme tam tenkrát měli.

Ač to zní divně, bylo to to nejlepší, co se mi mohlo stát. Vyhazov ze školy.

Jelikož jsem nemohl zůstat bez práce a zedníka či chemika se mi dělat nechtělo, tak jsem se rozhodl pro dráhu programátora. Našel jsem v Praze firmu, která mě zaměstnala a to i s tím, že jsem byl pořádné kopyto, co nic neumělo a pěkně se v tom plácalo.

Můj plat tenkrát činil 12 tisíc korun hrubého. Pro mě to bylo spoustu peněz za něco, co mě navíc strašně baví. Myslel jsem, že jsem dosáhnul svého cíle a teď už nic víc nechci. Ale to jsem se mýlil...

Dnešní doba je taková, že lidé v sobě často nemají pokoru a to zejména v IT. Já bych tenkrát pracoval i zadarmo, protože jsem to prostě chtěl dělat. A to je přesně ono. Opět se vrací moje vlastnost, že ono poznání je mým cílem a to je to, co vás nakonec může vést dál. Proto pokud v IT začínáte, neřešte kolik za to dostanete, dělejte to klidně zadarmo. Pokud jste dobří a chytří, nakonec sami přijdete na to, kde je vaše cena. Ale vše má svůj čas.

Moje nadšení z práce začalo pomalu uvadat. Důvodem nebyl jen fakt, že jsem si uvědomil, že i přes moje znalosti nejsem schopen dostat víc peněz, ale také to, že dělám pořád to samé. Tenkrát jsme tvořili různé jednoduché e-shopy a cms systémy. Samozřejmě jsme na to měli připravené různé šablony, a proto se z kreativní práce začala stávat rutina.

Nakonec jsem odešel, protože mi to přestalo stačit.

Zde je další část pro cestu k úspěchu. Nestůjte na místě. Pokud dosáhnete svého cíle, musíte jít dál. A to i za cenu, že vstoupíte do nekonformní zóny.

Abyste snáze pochopili, co je nekonformní zóna, podívejme se na její opak.

Jedná se o stav, kdy si vytvoříme takové prostředí, kdy nás nic nenutí k tomu, abychom se posouvali dál. Často se to stává lidem, kteří zůstanou v jedné práci déle, než je zdrávo. Vytvoří si své pohodlí, svou práci mají v malíku, a tak velkou část své pracovní doby věnují blbostem. Jinými slovy, začnete degenerovat a tím si zavřete cestu k úspěchu.

Poté, co jsem opustil svou práci jsem si během jednoho dne našel novou. Nebylo by to tak, že bych byl tak strašně dobrej, že by se o mě všude prali, ale to, že jsem ten večer potkal kamaráda, který mi řekl: "Hele, tady zrovna hledají ajťáka, tak se zeptej. Dělá tam můj kámoš."

Tak slovo dalo slovo a za pár dní jsem měl novou práci. Nastoupil jsem jako ajťák do velké firmy, kde hlavním byznysem byla slévárenská a strojírenská výroba.

Mým úkolem bylo dodávání hardwaru zaměstnacům, klasické myši, klávesnice, apod. Druhou činností měl být rozvoj interního informačního systému, kterým se nahrazují nedostatky v primárních ERP systémech.

To bych ovšem nebyl já, abych se nesnažil si cestu usnadnit a věnovat se tomu, co mě skutečně bavilo. Takže došlo k tomu, že jsem se přestal starat o to, zda mají všichni své myšky, klávesnice a psal jen ten informační systém.

V té době jsem se již učil nový jazyk a tím byla Java. Věděl jsem, že pokud chci dělat něco většího a zajímavějšího, musím hledat i jiné prostředky, protože v PHP jsem tu cestu neviděl.

Byla to láska na první pohled. Java byla staticky typová a měla i různá řešení na serveru pod názvem J2EE.

Takže opět moje touha po poznání mi pomohla, abych překročil to, kde jsem začal. Z PHP programátora jsem se pomalu stával javistou a tento svět mě uchvátil.

První co jsem udělal bylo, že jsem si na místní tiskárně vytiskl celou dokumentaci k J2EE, což bylo asi tisíc stran a doma se po večerech učil. Bylo to něco nového a opět mě to posouvalo dál, alespoň jsem měl ten pocit.

Takže zde je další ukázka toho, abyste uspěli. Musíte stále vystupovat do nekonformní zóny. Nestačí to, co umíte. Musíte se stále učit. IT svět není o tom, že nastoupíte do firmy, kde vám dají sto tisíc a vy tam jen sedíte a děláte to, co znáte.

Nějakou dobu vám to vydrží, ale věřte, že vám to nakonec zlomí vaz. Je dobré mít na paměti, že v IT světě je to tak, že 50% vašich znalostí vám za 10 let bude úplně k ničemu. Tedy pokud nechcete sedět v jednom korporátu do té doby, než natolik zdegenerujete, že vás nakonec budou muset sami vyhodit.

Pokračování příště....

neděle 16. července 2017

Funkcionální paradigma: React a Redux

V poslední době se stalo funkcionální programování tématem, o kterém se hodně mluví. Z akademické sféry přešlo do praxe a jak se ukazuje, tak je to způsob, který je v určitých oblastech zajímavou alternativou, nahrazující imperativní přístup.

Dnešní článek bude zaměřen na to, co to vlastně je ten funkcionální přístup. I když na toto téma existuje spousty článků, tak často je vše popisováno příliš abstraktně, což zapříčinilo, že ne každý chápe, o co vlastně jde.

Abych byl schopen demonstrovat tuto problematiku, zvolil jsem si k tomu dvě knihovny, které jsou navrženy podle funkcionálního paradigmatu (alespoň z části).

Funkcionální programování

Přesná definice říká, že se jedná o deklarativní programovací paradigma, které chápe výpočet jako vyhodnocení matematických funkcí.

Samotný program si poté můžete představit tak, že je složen z funkcí, které volají další a další funkce a tím se postupně zjednodušují. Pokud bychom hledali jazyk, který je jednou z vlajkových lodí tohoto přístupu, nejspíše bychom skončili u LISPu či Haskellu.

Druhou důležitou vlastností je to, že funkce nevytváří vedlejší efekt. Ve výsledku to znamená, že na stejný vstup vždy dostávám stejný výstup a nemodifikuje žádný stav. Toto je jedna z důležitých vlastností, kterou se dá odlišit funkcionální a objektový přístup.

Lambda funkce

Abychom byli schopni deklarativního programování, budeme k tomu potřebovat jednu zásadní věc a tím jsou lambda funkce.

Při mém prvním studiu toho, co to vlastně lamba funkce jsou, jsem skončil s plnou hlavou různých teoretických a abstraktních pojmů a stále jsem nechápal, co to vlastně znamená.

Postupně jsem si vytvořil jednoduchou pomůcku, která mi osvětlila tuto problematiku. Tou pomůckou je, že funkci mohu přiřadit do proměnné a tím se proměnná stává funkcí.

Zkusím uvést příklad:

const hello = function(param) {
    return `Hello ${param}`;
};
console.log(hello('World'));

Na tomhle příkladě je vidět, že jsme vytvořili proměnnou s názvem "hello",  která je funkcí.

Příklad je vcelku jednoduchý, tak si ho pojďme trochu rozšířit:

const hello = function(param) {
    return `Hello ${param}`;
};
const helloFromLanguage = function(param) {
    return param('from Javascript');
};
console.log(helloFromLanguage(hello));

Nyní si můžeme všimnout, že jsme vytvořili druhou funkci s názvem "helloFromLanguage", která jako parametr přijímá funkci, kterou sám zavolá.

Nyní si ještě tento příklad přepišme pomocí arrow functions z ES6:

const hello = (param) => `Hello ${param}`;
const helloFromLanguage = (param) => param('from Javascript');
console.log(helloFromLanguage(hello));

To je vše. Lambda funkce a deklarativní programování je vcelku jednoduchá záležitost. Na rozdíl od imperativního přístupu se dá říct, že stále dokola vytváříme callbacky, které se reálně vykonají jinde, než na místě, kde jsme je definovali.

Javascript a funkcionální programování

Pokud bychom o javascriptu mluvili jako o funkcionálním jazyce, tak bychom to museli dát do uvozovek. Přesnější definicí je, že Javascript je hybridní jazyk, ve kterém můžete programovat jak objektově, tak funkcionálně.

I když se často porovnává, zda je lepší objektový či funkcionální přístup, tak si s tím nemusíme lámat hlavu. Osobně si myslím, že se tyto dva přístupy mohou kombinovat a tím těžit z obou paradigmat.

React a funkcionální přístup

Psát o tom, že je React skvělá knihovna pro psaní frontendu, je asi zbytečné. Všichni, co to jednou zkusí a pochopí jeho fungování, tak už nechtějí jinak. Je to stejné, jako když si zvyknete na MacBook, ... ale o tom až jindy :)

V Reactu naleznete několik míst, které "přiznávají" funkcionální přístup.

Pojďmě si několik těchto míst ukázat....

Stateless komponenty

Stateless komponenty jsou funkcí a ničím jiným. Díky tomu nemají žádný interní stav a pokud danou komponentu budeme volat se stále stejnými parametry, budete vždy dostávat stejný výstup.

Pojďme si ukázat jednoduchou komponentu:

interface Props {
    title: string;
}
export const InboxDetailBlock: React.SFC<Props> = ({title, children}) => (
    <fieldset>
        <legend><FormattedMessage id={title}/></legend>
        {children}
    </fieldset>
);

Komponenta přijímá jako vstup props s "title" a "children". Sama nic nemodifikuje, nemá interní stav a pokud jí předáme stejný vstup, vždy bude stejný výstup.

React props

Druhým místem, který lze zmínit jsou samotné props. Props jsou uvnitř komponenty v immutable stavu a tím pádem žádná komponenta nemůže způsobit vedlejší efekt v podobě mutace vstupu. K tomuto účelu slouží callbacky, kterými oznamujeme, že se v komponentě "něco stalo".

Rozšíříme náš příklad o ukázku s callbackem:

interface Props {
    title: string;
    onClick: () => void;
}
export const InboxDetailBlock: React.SFC<Props> = ({title, children, onClick}) => (
    <fieldset onClick={onClick}>
        <legend><FormattedMessage id={title}/></legend>
        {children}
    </fieldset>
);

interface PropsDetail {
}
export const Detail: React.SFC<Props> = () => (
    <InboxDetailBlock title="My block" onClick={() => console.log('Clicked!')}>
        <p>Hello world!</p>
    </InboxDetailBlock>
);

Zde můžete vidět, že komponenta "InboxDetailBlock" má událost na kliknutí na fieldset. Tato událost je směrem k rodiči oznámena pomocí callbacku. Tím se eliminuje nutnost mutace jakéhokoli stavu, který by tuto událost vykonal. Tomuto přístupu se říká "one way binding", kde se událost oznamuje pomocí callbacku a nikoli mutací.

Redux jako globální stav

Pokud jsme se bavili o tom, že metody nemají vedlejší efekt, který by mutoval stav, tak přesně tímto způsobem funguje i Redux. Redux, jakožto implementace Fluxu, vychází z jednoduché myšlenky, která říká: "Máme pouze jeden zdroj pravdy (globální stav) a pokud ho chceme měnit, tak musíme vytvořit jeho kopii, nikoli ho mutovat."
Ve funkcionálním paradigmatu bychom totiž globální stav neměli nikdy mutovat, ale pouze vytvářet jeho nové kopie. Tedy změna stavu je tvorba nového stavu.
V Reduxu k tomuto účelu slouží takzvané reducery, což jsou jednoduché funkce, které přijímají aktuální stav a payload akce. Návratovou hodnotou je poté nový stav.
Jednotlivé React komponenty, které jsou na Redux state navěšeny, poté automaticky reagují na změnu stavu.
Díky tomuto přístupu máte v čase vždy pouze jeden stav. S nadsázkou se dá říci, že pro debugování vám často stačí sledovat redux state a díky tomu víte v jakém stavu je celá vaše aplikace.
Pokud svou aplikaci programujete podle těchto pravidel, tak se vám nemůže stát, že by React či Redux vytvářel vedlejší efekty a čímž vám dost sjednodušuje život.

Závěr

Ve funkcionálním přístupu naleznete spoustu zajímavých témat, viz třeba monády. Cílem tohoto článku nebylo vysvětlit celou problematiku, ale pouze nastínit, jak to vlastně s tímto paradigmatem je.
Funkcionální a deklarativní přístup není spásou pro vše. Nicméně zde je krásně vidět, že existují oblasti vývoje, kde se tento přístup může hodit a ba co víc, může být i hodně prospěšný.
Existuje ještě jedna hezká ukázka a tou je implementace GraphQL, kde pomocí deklarativního zápisu, přes callback "resolve", je velice snadné, aby za GraphQL API byl jakýkoli zdroj, který by byl velice jednoduše měnitelný. Každopádně o GraphQL se ještě něco dozvíte v následujících článcích...

čtvrtek 13. července 2017

Next.js, SSR a Typescript

Existuje jeden hlavní důvod, proč většina lidí s javascriptem skončí dříve, než vůbec začne. Tím důvodem je: "Kde mám sakra začít?".

Gulp, Grunt, Webpack, NPM, Yarn, ES5, ES6, ES2015, Babel, Typescript, Flow, React, Angular, Node.js, Next.js, Redux, Express, Koa, Hapi, .... uff. Nemá cenu si nic nalhávat, svět kolem javascriptu je rozsáhlý a plný slepých uliček. Viz Angular.

V dnešním článku bych se chtěl podívat na knihovnu Next.js, která je úzce spjata s Reactem. A je právě určena k tomu, aby vás odstínila od velkého množství konfigurace, kterou byste sami museli jinak udělat.

Co je Next.js?

Jednou větou: "Next.js je knihovna pro React, která za vás řeší server side rendering a konfiguraci." Server side rendering nebo-li SSR je věc, kterou byste měli sami chtít. Pojďme si nejdříve popsat několik důvodů, proč bychom SSR měli použít.

SEO

Pokud používáte javascriptové knihovny jako je React či Angular a stavíte veřejný web, tak narazíte na to, že Vám ho vyhledávače nebudou chtít správně indexovat. Je velká pravděpodobnost, že zůstanete pro zbytek světa neviditelní. A to přeci nechcete. Zde přichází na řadu SSR, které spočívá v tom, že Vám dopředu vygeneruje "kostru" webové stránky a až poté řeší samotný javascript.
Díky tomu vyhledávač vidí html stránku, ze které si je schopen přečíst informace, které potřebuje pro indexaci.

Velikost stažené aplikace

Ač žijeme v době, která jednou bude popisována jako "začátek digitálního věku", tak je třeba mít na paměti, že i když máme výkonné počítače, tak nás to nespasí v tom, abychom přestali ladit dostupnost a výkon.
Příkladem budiž mobilní zařízení, které předběhly počítače v prohlížení webových stránek. To je skvělá zpráva, nicméně... Nastává totiž problém s rychlostí připojení, které ještě nemáme na takové úrovni jako v případě přímého připojení v domácnostech. Mobilní operátoři nabízí jen velice omezené zdroje a to jak na úrovni rychlosti, tak i v množství stažených dat.
Zde nastupuje druhý argument, proč byste měli SSR chtít. Tím argumentem je fakt, že pokud je Vaše webová aplikace rozsáhlejší, tak klientovi můžete aplikaci posílat po částech. Tedy těch částech, které zrovna vaše aplikace sama potřebuje.

Bílá stránka při prvním načtení

Tento důvod úzce souvisí s předchozím bodem. Jedná se o to, že pokud aplikaci otevíráte poprvé a nepoužíváte SSR, tak vlastně vidíte pouze bílou stránku a to do té doby, než se stáhnou všechny potřebné soubory, což je běžně celá aplikace. V případě pomalejšího připojení je toto velký problém.
Uživatel nechce čekat. Často si bude myslet, že je někde chyba a bude stále dokola zkoušet tlačítko "refresh". A to do té doby, než z vaší stránky odejde úplně.

Proč tedy Next.js a ne vlastní řešení?

Každý, kdo se s Reactem kdy setkal, tak ví, že vytvořit aplikaci, která by se renderovala ze serveru je vcelku jednoduchá záležitost. Problém ovšem nastává ve chvíli, kdy budete tímto směrem nastavovat i další věci. Myslím tím například CSS, Redux či třeba routování. Všechny tyto věci má Next.js již vyřešen a vy pouze využíváte hotové řešení.
Další výhodu, kterou získáte je funkční nastavení webacku či jednoduché spouštěcí skripty. Next.js za vás vše připraví a díky tomu máte stack, který podporuje jak práci v development řežimu, tak i produkční běh.
Next.js toho umí samozřejmě mnohem mnohem více, každopádně k tomuto účelu doporučuji si projít popis na github.com.

Pojďme se nyní podívat na to, jak je na tom Next.js s podporou Typescriptu...

Next.js a Typescript

Pokud chcete v Next.js 2.0 použít Typescript, tak zde narazíte na jeden zásadní problém. Tím problémem je, že podle jejich ukázky na githubu vychází z toho, že zkompilovaný javascript máte ve stejném adresáři jako zdrojové soubory. Faktem je, že tenhle způsob mi nepřijde zrovna vhodný.
V nové připravované verzi máte možnost spustit next.js s parametrem, kde se daný zdroj nachází. K tomuto stačí jednoduchá úprava.

Pojďmě se nejdříve podívat na definici skriptů v package.json:

"scripts": {
    "prebuild": "tsc && cp -R static dist/",
    "build": "next build dist",
    "predev": "tsc && cp -R static dist/",
    "dev": "concurrently \"tsc --watch\" \"next dist\"",
    "start": "next start dist"
  },

Zde můžete vidět, že před spuštěním next.js jen provedet kompilaci pomocí tsc, který podle tsconfig.json kompiluje do adresáře dist.

Konfigurace tsconfig.json vypádá následovně:

{
  "compilerOptions": {
    "module": "commonjs",
    "target": "es6",
    "jsx": "react",
    "strict": true,
    "moduleResolution": "node",
    "rootDir": "src",
    "outDir": "dist",
    "baseUrl": ".",
    "paths": {
      "*": [
        "node_modules/*",
        "types/*"
      ]
    }
  },
  "include": [
    "src/**/*"
  ]
}

Podle tohoto nastavení jsou zdrojové soubory v adresáři src a výsledek kompilace ve zmíněném adresáři dist.

Závěr

Osobně vnímám Next.js jako posun k dospělosti. Pokud vývojářům něco chybělo, tak je to dev stack, který by za ně řešil spoustu nudné konfigurace, ale přesto by zůstal dostatečně flexibilní. Tím Next.js přesně je. Chcete doplnit pluginy do webpacku? Žádný problém. Chcete změnit Express na straně Node.js serveru? Také můžete a nebude vás to stát ani příliš úsilí.
Pomocné knihovny, jako třeba Create React App splnily svou historickou povinnost, kdy se čekalo na to, až přijde skupina lidí, kteří tuto věc udělají robusněji.
Nakonec bych si dovolil jedno přirovnání ze světa Javy. To co je Spring Boot pro Spring, to je Next.js pro React. Dělejme opravdu jen to, co musíme.

React aplikace od začátku do konce

V poslední době jsme byli nuceni napsat více React aplikací, které vždy vychází ze stejného základu. Díky tomu jsem si uvědomil, že i když...