RxJS i nie tylko
Streszczenie odcinka:
Piotr to Full Stack Web Developer od 2007, konsultant i szkoleniowiec. Zaczynał od PHP i MySQL lecz szybko dostrzegł potęgę JavaScript i NoSQL. Obecnie pisze backend w Node.js a front w Angular. Miłośnik RxJS oraz grafowej bazy danych OrientDB, ortodoksyjny ewangelista TypeScript 🙂
Poza pracą zawodową skacze na trampolinach, nurkuje na bezdechu, żongluje i balansuje na slackline. Jeden z organizatorów Urban Highline Festival w Lublinie.
Transkrypcja odcinka:
Cześć, z tej strony Łukasz Kobyliński. Witam Was w kolejnym odcinku podcastu „Stacja IT”. Dzisiaj porozmawiamy o frontendzie, JavaScripcie, TypeScripcie i o podejściu reaktywnym w tych technologiach. Naszym gościem jest Piotr Błaszczak.
Cześć, Piotr.
Cześć.
Powiedz na początek parę słów o sobie.
Nazywam się Piotr Błaszczak. Pochodzę z Lublina – tam się urodziłem, tam skończyłem studia. W 2005 r. zacząłem uczyć się programowania. W 2007 r. dostałem pierwszą pracę jako programista, wtedy w PHP jako full stack. Do dzisiaj zajmuję się programowaniem, z małym wyjątkiem, bo w 2015 r. przerzuciłem się na pełny JS, czyli Node.js po stronie serwera. I wszystko w TypeScripcie, więc jestem wielkim fanem TypeScriptu.
Jak to się stało, że zająłeś się programowaniem? Czy interesowałeś się tym w młodości, na studiach?
Pierwszy komputer – lata 99. Studia informatyczne, pierwszy internet, który był jeszcze wtedy z Neostrady. To było drogie, więc trzeba było postawić swoje małe serwery, rzucić kabel przez płot do sąsiadów i dzielić się internetem. Tak też pierwszy Linux został zainstalowany u mnie w komputerze, który pod biurkiem cały czas buczał. To była pierwsza inspiracja.
Później, gdy w internecie zacząłem obserwować linki, pojawiła się „.php” w URL-ach. Teraz już tego nie ma, ale wtedy jeszcze była to dosyć powszechna praktyka. Na forach dopytywałem, co to jest. Bawiłem się trochę z HTML-em, żeby tę naszą lokalną sieć postawić, małą stronkę statyczną. Wytłumaczyli mi, że tam można to wszystko dynamicznie robić, bazę danych, która na początku mnie przeraziła – co, po co i jak. Ale tak to się zaczęło. Kupiłem książkę PHP i MySQL – biblia, chyba 1400 stron. Dwa tygodnie zajęło mi, żeby ją przeczytać.
Nie miałem z kim rozmawiać o programowaniu, uczyłem się sam, korzystając z książek. Pamiętam, że grałem wtedy na gitarze i dwa tygodnie budowałem formularz rejestracji naszych zespołów. Budowaliśmy platformę, która pozwalała lokalnym zespołom dodać się do listy zespołów w takiej małej społecznościówce.
Dlaczego nie miałeś kogo się zapytać, skoro byłeś na studiach informatycznych?
Na początku studiów było dosyć ogólnie. Dużo matematyki, programowania jeszcze nie było. Miałem pecha, bo obiecano nam możliwość wyboru, czyli albo programowanie, albo sieci, albo grafika itd. Później okazało się, że jedyna dostępna specjalność to sieci. Z programowaniem znowu więc zostałem sam. Miałem tylko podstawy, które sam z książki przerobiłem. Później na studia magisterskie poszedłem na programowanie. Niestety po roku zamknęli mi uczelnię i musiałem znowu się przenieść. A tam, gdzie mogłem się przenieść, były dostępne tylko sieci, więc studiowałem, inżyniera magistra zrobiłem z sieci, a duszą cały czas byłem programistą. Do wszystkiego musiałem dojść samemu.
Z perspektywy trenera zazdroszczę trochę kursantom, w jakim łatwym, fajnym świecie żyją. Sama technologia tak się rozwinęła, że nauka jest obecnie bardzo prosta i przyjemna, jeśli chodzi o programowanie frontu. Dzisiaj mamy technologię frontendową, w której budujemy aplikacje desktopowe, aplikacje mobilne. A ja miałem pod górkę, każdy miał, kto zaczynał w tamtych czasach. A druga sprawa: mamy dziś YouTube, Udemy i e-learningowe źródła, z których możemy czerpać wiedzę. Dzisiaj liczą się tylko chęci, każdy ma takie same możliwości.
W tamtych czasach były głównie książki, wiedza od kolegów czy ta zdobyta na studiach, jeśli miało się szczęście do dobrych studiów.
Nie było jeszcze GitHuba, skąd czerpiemy teraz dużo wiedzy i przykładów. Były fora takie jak phpBB. Tam trzeba było dzielić się wiedzą, ale od początku pamiętam, że społeczność była dosyć przychylna i bardzo miły był odbiór.
Charakterystyczne jest to, że uczyłeś się przez praktykę. Znalazłeś sobie pierwszy projekt, który nie był ćwiczebnym z książki, ale było to faktycznie dla kogoś przydatne. Pewnie można było zdobyć na tym pierwsze doświadczenia.
Gdy przychodzi do mnie znajomy i mówi, że chętnie by się przebranżowił i zaczął programować, to go pytam: „A jaki problem chcesz rozwiązać?”, „Co chciałbyś zbudować?”. Jeśli myśli tylko o tym, że jako programista może fajnie zarabiać, to nie do końca tak jest. Tu się fajnie zarabia, ale na początku są krew, pot i łzy. To nie jest tak, że informatyk dostaje pieniądze za nic. On naprawdę musi nad sobą pracować i to jest praca, której na pierwszy rzut oka nie widać. Trzeba się temu poświęcić.
Powiedziałeś, że zacząłeś od PHP. Jak to się dalej potoczyło? Przeszedłeś potem na technologie frontendowe i JavaScript?
Tak. Zacząłem od PHP i MySQL-a, bo to było w książce. JavaScript był tam opisany pobieżnie, wspomniano jedynie, że istnieje. W 2007 lub 2008 r. poszedłem do pracy i budowaliśmy system, w którym szukałem lepszych rozwiązań. Strasznie mnie irytowało, że jak chciałem zrobić paginację, to cały stan aplikacji musiałem jakoś przegazować w URL-u między przejściami, między stronami. Gdy odkryłem, że kliknięcie w URL to przerywanie całej strony, złapałem się za głowę – „ale dlaczego?!”, „ale po co?!” – to było moje pierwsze pytanie świeżaka. Na samym początku kariery z JavaScriptem odkryłem Single Page Application. Wtedy to był Framework Ext JS oparty na bibliotece YUI od Yahoo. Teraz nazywa się to Sencha. Można to jeszcze odnaleźć w czeluściach bankowych korporacji. I zacząłem się tym bawić. Tak naprawdę składni JavaScriptu uczyłem się, przeklejając przykłady, jak robić nowe okienka, formularze. Było to o tyle przyjemne, że wszystko robiło się w JSON-ie, programowało się bardzo obiektowo. HTML-a i CSS-a nie musiałem tykać, może czasami małe poprawki, a budowałem naprawdę fajne panele administracyjne do zarządzania treścią.
Gdy w 2011 r. przyjechałem do Warszawy z Lublina, to żyjąc trochę jak taki freelancer, trochę na etacie, postanowiłem, że w Warszawie spróbuję pójść do firm, żeby zobaczyć, jak one działają. Będąc szefem dla siebie jako freelancer, strasznie wyidealizowałem sobie świat. Jak poszedłem do pracy – pierwszą pracę miałem w banku w Warszawie – to pomyślałem: „Wow, a więc tak to wygląda”. Niezbyt idealnie. Wtedy nauczyłem się, że kod nie zawsze jest piękny, kod ma działać, ma dostarczać rozwiązanie biznesowe. To był taki wewnętrzny zgrzyt w mojej karierze.
Teraz doceniam te frameworki, tę naszą technologię, która pozwala bardzo wiele rzeczy schować pod spodem. Na szkoleniu z JavaScriptu, z dobrych praktyk, gdzie większość osób to angularowcy, tak naprawdę czują się oni obco w świecie czystego JavaScriptu, jQuery, w świecie, gdzie nie ma Angulara, gdzie nie ma Reacta ani Vue. Z jednej strony gubią się, bo to wszystko jest nowe, tak jakbyśmy uczyli się programować od początku. To jest jednak miecz obosieczny. Z jednej strony jest to dobre, ponieważ taka osoba nauczyła się Angulara i dostarcza już produkty, wartość firmie, w której pracuje, ale nie jest ekspertem w JavaScripcie. Ale nie musi nim być, ważne, że produkt działa, jest bezpieczny.
Mamy speców od Angulara, którzy nam całą logikę zamknęli w środku pod spodem, a my tylko uczymy się używać tego narzędzia. Wtedy mamy fajne wejście na rynek, od razu możemy być produktywni. Z czasem, jeśli nas to kręci, możemy stawać się ekspertem i zaglądać w Angulara, patrzeć w JavaScript, patrzeć, jak kiedyś jQuery było napisane, jakie były problemy, żeby tak historycznie się poduczyć, zobaczyć, co piszczy we frontendzie.
Czasy są więc o tyle fajne, że możemy być produktywni i od razu wejść na rynek, a później zdobywać wiedzę ekspercką. Za moich czasów tak nie było. Trzeba było mocno siedzieć, znajdować kruczki, problemy w JavaScripcie, różnice między przeglądarkami. Później zaczęły pojawiać się jQuery i frameworki, więc trochę nam upraszczały życie. Ale gdy chcieliśmy coś customowego napisać, to musieliśmy dużo walczyć. Te czasy były trudniejsze.
Można na to patrzeć z różnych perspektyw. Z jednej strony łatwiej wejść w te technologie, bo są bardziej przystępne, wysokopoziomowe, nie trzeba dokładnie analizować, co dzieje się pod spodem. Natomiast generalnie jest tego dużo. Mamy mnóstwo frameworków do wyboru, różnych technologii, które pozwalają utrzymywać czy testować aplikacje. Natomiast kiedyś świat był o tyle prostszy, że był JavaScript i jakaś tam najwyżej pojedyncza biblioteka. Pod tym względem jest to pewnie bardziej skomplikowane. Ale faktem jest, że łatwiej zacząć. Czy uważasz, że bez głębokiego zrozumienia, co leży u podłoża tych technologii, można być dobrym programistą i dobrze realizować zadania, programując w Angularze czy React’cie, ale nie rozumiejąc do końca, co tam się pod spodem dzieje?
Zdefiniujmy zatem, kim jest dobry programista.
To jest dyskusyjne.
Jeśli aplikacja ma być wydajna i piszemy w Angularze, to bardzo łatwo napisać niewydajną aplikację. Więc pytanie, czy programista jest zły, czy jeszcze nie nauczył się podstaw optymalizacji, tego zone.js, który jest w Angularze, który dla mnie jest zmorą. Złapałem się za głowę, jak zobaczyłem, że znowu poszli, był $scope w Angularze jedynce, a tu mamy zone.js. Znowu musimy się tym bawić. Ale musimy nauczyć się obsługiwać change detection w Angularze, żeby nie zajechać aplikacji. Ale jeśli aplikacja jest zwykłym CRUD’em, jest adminem, change detection może odpalać się często i to nas nie spowalnia, to programista do tego zastosowania biznesowego jest dobry.
Poza tym zły programista to programista, który nie chce się uczyć. Tylko o tym bym powiedział, bo tak naprawdę jak coś zrobiliśmy źle, to w obecnym stacku i tym flow wytwarzania oprogramowania, gdzie mamy code review, testy, continuous integration, wszystko jest zautomatyzowane, to nie powinniśmy w firmie obawiać się, ponieważ cała struktura firmy powinna być już ułożona tak, żeby wyłapać błędy na wczesnym etapie, dać możliwość ich naprawy, uczenia się.
Wspomniałeś o swojej historii rozwoju i zmian technologii, z których korzystałeś. Teraz to są technologie frontendowe, mówiłeś o JavaScripcie. Jaki jest podstawowy stos technologiczny, z którego obecnie najczęściej korzystasz i w którym się specjalizujesz?
Największa zmiana pojawiła się w momencie, gdy na rynku pojawił się Node.js, czyli mieliśmy nagle JavaScript po stronie serwera, po stronie konsoli, mogliśmy pisać narzędzia dla frontendowców, dalej pisząc we frontendzie, czyli JavaScripcie. I od tamtej pory pojawiły się preprocesory, postprocesory do CSS-a w postaci SaaS-a, LaaS-a. Teraz mamy Babel, Webpack, czyli narzędzia do pakowania i do transpilacji kodu. Mamy TypeScript, którego osobiście używamy – to coś, w co moim zdaniem na pewno warto zainwestować, pomijając fakt, że Angular jest napisany w TypeScripcie, że Vue, następna wersja, trójka, już będzie w TypeScript, że mamy wsparcie w React, w TypeScripcie. Mamy VS Code, który staje się – jeśli już nim nie jest – najbardziej popularnym frontendowym edytorem, open-source’owy edytor, który jest napisany w TypeScripcie, w HTML-u i CSS-ie, a dzięki elektronowi kompilowany jako desktopowa aplikacja na trzy platformy. Więc świat robi się stabilny w ten sposób, że TypeScript daje nam możliwość pisania w najnowszym JavaScripcie – ECMAScript – kompilacji tego na starszy kod, nawet ES5, i odpalenia tego w starym kodzie. Dzięki temu dzisiaj jako programiści nie musimy znać się na tym, co jest nie tak z przeglądarkami, jakie są różnice, gdzie to będzie odpalane. Po prostu piszemy, uczymy się, jesteśmy na bieżąco ze światem JavaScriptu. I to bezkarnie sobie kompilujemy na starszych wersjach.
Jak to działa? Czy piszemy w TypeScripcie i później to jest kompilowane do różnych wersji JavaScriptu, ładowane do przeglądarki w zależności od tego, jaka to wersja lub z jakiej wersji korzysta użytkownik?
Natywnie ani Node.js, ani przeglądarki nie obsługują TypeScriptu. Więc tak, mamy napisane w Node.js kompiler, który bierze nam nasze pliki źródłowe, indeks z rozszerzeniem „.ts” i kompiluje to do katalogu dist, distribution jako już indeks.js. I ten indeks.js możemy załadować w przeglądarce. Można przekompilować na kilka wersji, czyli jeśli wiemy, że mamy jakichś użytkowników, możemy zrobić ifa – że jak jest nowa przeglądarka, to ładujemy kod przekompilowany do nowszej wersji, a jeśli mamy starszą, to możemy też zrobić oddzielną kompilację, czyli dwa katalogi dist, dla starszej przeglądarki, ale nie wiem, czy ktoś tak robi. Chyba jeśli jest wymóg, że ma być obsługiwane ES5, bo jakieś stare będą, to po prostu kompilujemy wszystko do ES5. Oczywiście wszystkie przeglądarki i silniki JavaScriptu są w pełni kompatybilne wstecz, więc bezkarnie możemy sobie to kompilować wstecz, ile możemy, bo niektórych feature’ów nie dałoby się zrobić w bardzo starych przeglądarkach, a do ES5 spokojnie możemy każdy kod obecnie przekompilować. Tam już automatycznie dodadzą się tzw. polifile, czyli patche na przeglądarkę, czyli jak któraś przeglądarka czegoś nie używa, to zostanie automatycznie dodany skrypt, który ten brakujący feature albo jakieś rozbieżności nam naprawi. Dzięki temu skompilowany kod będzie działał stabilnie. To wszystko jest jakby zaszyte w TypeScripcie i my już tym nie musimy się martwić.
Są też eksperci, którzy pracują nad tym społecznie. Oczywiście to wszystko jest open-source’owe. Pracuje nad tym społeczność, która się tym interesuje, ma w tym doświadczenie i to za nas robi, a my możemy koncentrować się nad naszą aplikacją. Przeważnie większość frameworków, wszystkie znaczące, daje nam narzędzia comand line’owe, czyli robimy po prostu ng serve i automatycznie nasz kod TypeSkrypt’owy jest kompilowany w locie i serwowany do przeglądarki. W momencie gdy dokonamy jakiejś zmiany, automatycznie to się odświeża. Development jest więc tak naprawdę bardzo prosty. Narzędzia CLI też mają komendy new, dzięki której możemy stworzyć nowy projekt bardzo szybko. Tak naprawdę w 10 minut możemy być gotowi, żeby zrobić ng build i mieć prostą aplikację zbudowaną i gotową do deploymentu na jakiś serwer. I możemy zacząć dewelopment. Od razu mamy tam testy skonfigurowane, lint’owanie, więc całe środowisko jest gotowe za sprawą kilku komend w konsoli.
Czyli ten bieżący, najbardziej aktualny stos, z którego korzystasz, to TypeScript, Angular i Node.js.
Po stronie Node.js – też TypeScript. Obecnie używam frameworka NestJS, który jest inspirowany bardzo mocno, jego dependency injection, jest mocno inspirowane Angularem. Myślę, że to jest bardzo dobrze zaprojektowany framework, jeśli chodzi o backend. Można wspomnieć jeszcze historycznie o CoffeeScripcie. CoffeeScript może był poprzednikiem TypeScriptu, ale niestety już umarł albo jeszcze umiera, nikt już na pewno nie podejmie decyzji, że chce zacząć w tym pisać. A tu teraz przychodzi kolejny – TypeScript.
I teraz pytanie: dlaczego miałbym inwestować w TypeScript, skoro CoffeeScript umarł? Odpowiedź jest bardzo prosta: ponieważ TypeScript jest supersetem JavaScriptu, czyli jest poprawnym JavaScriptem. Możemy wziąć plik javascriptowy, zmienić jego rozszerzenie z „.js” na „.ts” i możemy już to kompilować, to będzie działało.
Tu jeszcze zaznaczę, że jeśli tak zrobimy z domyślnymi ustawieniami, to oczywiście będziemy mieli błędy kompilacji, bo domyślnie compiler jest ustawiony dosyć rygorystycznie. Musimy więc popatrzeć trochę w konfiguracji, odpuścić. Wtedy możemy JavaScript od razu zamienić na TypeScript, skompilować i pomału dodawać typy, refaktoryzować. W tym momencie TypeScript wali się tylko wtedy, kiedy rzeczywiście mamy błąd składniowy albo błąd typów i chcemy zrobić coś, co w JavaScripcie by nam się wywaliło. To już jest ten plus TypeScriptu, że on krzyczałby o takich rzeczach. I to jest właśnie sukces TypeScriptu – jakby nie zabrał nam nic starego, jest w pełni kompatybilny wstecz z JavaScriptem. Dał nam niesamowite rzeczy, takie jak właśnie typy statyczne, dzięki czemu bardzo łatwo możemy po projekcie refakturyzować się, generować kod, bo na TypeScripcie jest teraz oparta większość angularowych generatorów. To jest jakby rozszerzenie JavaScriptu.
To samo zrobił NestJS, jeśli chodzi o frameworki do pisania backendu w Node – dał tylko nową architekturę, taki nowy syntactic sugar, czyli to wszystko ładnie wygląda, ładnie się komponuje, ale tak naprawdę w środku niewiele swojego napisał. Po pierwsze korzysta z Expressa, najbardziej popularnego frameworka. Wszystkie pluginy do Expressa jak najbardziej w Neście działają. Możemy nawet wziąć naszą aplikację, napisaną obecnie w Expressie, na niej odpalić Nesta – to będzie działało. I kolejne feature’y, kolejne moduły pisać w Neście i mało refakturyzować. Więc tak jak TypeScript jest popularny, ponieważ docenia to, co już jest w JavaScripcie, a nie próbuje budować świata na nowo, tak samo Nest wziął to, co jest najlepsze w świecie backendu, frameworka, pluginów i bibliotek, i ubrał to w nową, lepszą architekturę, lepsze szaty.
Gdzie ten framework umieścić? Czy jest to alternatywa do Angulara, czy jest to po stronie backendowej?
Angular – jeśli mówimy o froncie, a NestJS to backendowy framework do pisania aplikacji webowych po stronie serwera.
Czyli takie rzeczy jak pisanie jakichś usług, chociażby nestowych.
Mamy kontrolery, czyli miejsca, gdzie piszemy obsługę requestów, mamy dependency injection, wszystko jest oparte na adnotacjach takich jak w Angularze, po prostu klasy adnotujemy. Architekturę mamy bardzo fajnie modułowo podzieloną, czyli to wszystko jest ładnie spięte. Tak jak wspomniałem, głównie Nest wykorzystuje narzędzia, które już są napisane. Pozwala ładnie konfigurować i układać w całość z klocków, nie pisząc tej logiki od nowa.
Niewątpliwą zaletą tego, że piszemy frontend w JavaScripcie czy TypeScripcie i backend w tym samym języku, jest pewnie łatwość utrzymania wszystkiego i to, że mamy programistów, którzy znają jeden język, mogą się na nim skoncentrować. Czy są inne zalety tego, że mamy TypeScript po obu stronach? Czy takie technologie jak Angular w jakiś sposób preferują w komunikacji z backendem takie frameworki jak NestJS? Czy mamy tu jeszcze dodatkowe ułatwienia, które normalnie by się nie pojawiły, gdyby na tym backendzie było PHP, Java?
Na pewno to, co wspomniałeś: że mamy jedną technologię, czyli odpada nam już taki context switching, że tu już PHP, tu w JavaScripcie kropka, żeby propertiesy wziąć, tu jakieś strzałki trzeba było robić. Nie oszukujmy się, to trochę nas spowalnia, to już są dwa światy. Ja jestem wielkim fanem świadomego działania na nawykach. Czyli nie chcę myśleć, jak mam napisać, tylko chcę, aby w mojej głowie pojawił się pomysł i żeby to przelało się automatycznie na kod. Po pierwsze wtedy potrzebujemy nawyków pisania na klawiaturze, po drugie – komponowania klas, pisania samej składni języka. Jak mamy jedną technologię, to wszystko jest zautomatyzowane, czyli sami jesteśmy bardziej produktywni, mamy więcej zasobów umysłowych, mentalnych na sam biznes i sam problem, który rozwiązujemy.
Druga sprawa: obecnie przygotowuję szkolenie z prowadzenia projektów fullstackowych, javascriptowych przy pomocy monorepo, czyli jest taka biblioteka od Nrwl Extensions, Nx. Ta biblioteka Nx jest rozszerzeniem tego, co nam daje Angular, na Angular CLI. Pozwala prowadzić duże projekty jednym Monorepo. Duże projekty w takim sensie, że mamy kilka aplikacji, dużo bibliotek, które są współdzielone – biblioteka może być współdzielona między aplikacjami backendowymi, czyli mamy połączenie do bazy danych klienta, do jakiejś zewnętrznej usługi REST’owej, i tego klienta możemy współdzielić między wieloma aplikacjami backendowymi, mikroserwisami. Tak samo biblioteka może być współdzielona między backendem i frontendem, czyli jeśli napiszemy bibliotekę w czystym TypeScripcie, to bez problemu możemy ją zaciągnąć w Angularze i w Neście. Tak samo angularowe moduły UI możemy współdzielić między kilkoma aplikacjami frontendowymi, np. frontend dla klienta i backend administracyjny, i administracyjne UI w naszej firmie. Takie narzędzia jak Nx dostarczają sposób na niezagubienie się w takim dużym monorepo, bo tu już będzie to wszystko rosło, jeśli chodzi o codebase. To narzędzie dostarcza nam komendy takie jak test affected, te affected build, czyli możliwość odpalenia buildów tylko na fragmentach aplikacji bibliotek, które zostały zmienione. Czyli jeśli zmieniliśmy jedną małą bibliotekę, która jest używana tylko w jednym mikroserwisie na backendzie, w Neście, to affected test przetestuje nam tylko tę bibliotekę oraz aplikacje, które z tej biblioteki korzystają, zakładając, że to jest mała zmiana w jednym mikroserwisie. Jeślibyśmy tych narzędzi nie mieli, to musielibyśmy przetestować całość. Więc to jest bardzo fajne rozwiązanie.
Odsyłam, aby wygooglać „Google Monorepo”, taką prezentację, w której Google opowiada, że u nich w całej firmie jest jedno repozytorium, w którym trzymają cały codebase. Ogromnym plusem tego rozwiązania jest to, że możemy jednym commitem zrefaktoryzować całą naszą aplikację od backendu poprzez klientów restowych aż do frontendu. U mnie wszystko jest w jednym repozytorium, robimy szybki refaktoring, robimy commit, pull request, i jak jest pull request zaakceptowany, to wszystko jest refaktoryzowane. Kiedyś musieliśmy wejść do repozytorium biblioteki współdzielonej, zmienić modele, później wejść do każdej – do backendu, frontendu, do każdego repozytorium, zaimportować najnowszą wersję tej biblioteki, zaaplikować zmiany, dostosowanie, później trzeba było to zsynchronizować, że jak to wchodzi na produkcję, to żeby gadało ze sobą w odpowiednich wersjach. To było kłopotliwe. Tak samo jak zrefakturyzowałem swój projekt, na którym pracuję właśnie z trzech repozytoriów na jedno, zauważyłem, jak to jest proste i przyjemne. Po pierwsze – pisanie aplikacji, po drugie – właśnie zarządzanie infrastrukturą. Jest to więc duży plus.
Facebook, Google używają monorepo, na pewno polecam to startupom. W startupie zależy nam, żeby jak najszybciej móc wprowadzić zmiany, żeby bardzo szybko zmieniać kierunek rozwoju aplikacji. Czasem musimy być elastyczni w startupie, aby szybko wprowadzić produkt na rynek i zobaczyć, jak się sprzedaje, czy się sprzedaje, czy jest użyteczny, a po wyciągnięciu wniosków szybko iść dalej. Do startupów takie rozwiązanie, po pierwsze, fullstackowe javascriptowe, to jest to, bo mamy jednych ekspertów od TypeScriptu. I drugie – szybkość deploymentu, szybkość zmiany aplikacji i refaktoringu.
Chociaż na pierwszy rzut oka takie podejście, że wszystko jest w jednym repozytorium, wydaje się dziwne. Pewnie trzeba się przyzwyczaić do tej koncepcji. Bo tu jest kwestia uprawnień, utrzymania różnych wersji bibliotek. Powstają pytania, jak takie rzeczy zrobić. Czy wszystko da się w tej koncepcji zrealizować, czy też musimy się pogodzić z ograniczeniami?
Na pewno jednym z ograniczeń jest to, że mamy jeden package JSON, czyli miejsce, gdzie instalujemy zależności dla wszystkich naszych aplikacji. To jest i plus, i minus. Plus jest taki, że wszystkie aplikacje korzystają z jednej wersji. Zakładam, że już piszemy test, więc jak podnosimy wersję, to możemy odpalić testy na wszystkich aplikacjach i zobaczyć, czy nic się nam nie wysypało. To jest duży plus, ponieważ jeśli mamy problemy z bezpieczeństwem w jakiejś naszej zależności, trzeba szybko zrobić patcha na zależności, to jest to jeden package JSON. Robimy patcha, continuous integration, nam to builduje, instaluje i deployuje bardzo szybko na nasze maszyny, gdzie przy wielu repozytoriach musimy do każdego projektu wejść, podnieść tę zależność i ewentualnie albo siąść i napisać do tego skrypty, albo ręcznie to zrobić. To jest duży plus.
To się sprawdza przy aplikacjach, które są rozwijane, i są zasoby programistów na każdą aplikację. Ale są firmy, w których np. pisze się aplikację, która będzie leżała kilka lat i nikt nie będzie miał ani ochoty, ani zasobów, żeby podnosić te zależności. Zakładam, że jakoś rozwiązuje się problem bezpieczeństwa, tego, że jak się pojawi jakaś paczka, która ma w sobie złośliwy kod, to trzeba się jej pozbyć z serwera i ją uaktualnić. Ale jeśli mam dużo aplikacji, które chcemy zrobić, aby one już sobie leżały, to wtedy monorepo może być nie najlepszym wyborem. Musimy mieć test, bo jak podnosimy zależność w aplikacji, w której piszemy, to te aplikacje, które już są maintenance, mają tylko działać, to musimy mieć tam napisane testy, że one będą dalej działały.
Przed nagraniem mówiłeś, że jesteś wielkim fanem podejścia reaktywnego w programowaniu. Jak to się łączy z JavaScriptem? W podcaście mówiliśmy już o programowaniu reaktywnym w kontekście Javy, a jeśli chodzi o JavaScript, to jakie technologie umożliwiają stosowanie tego podejścia i gdzie ono się sprawdza?
JavaScript narodził się po to, żeby robić interfejs użytkownika. Na początku żeby robić śnieg, migające napisy na stronach HTML-owych. Gdy później pojawił się AJAX – technologia robienia requestów w tle – okazało się, że w przeglądarce można robić pełnowartościowe aplikacje. To jest dużo lepsze niż robienie aplikacji desktopowej, rozsyłanie update’ów, każdy musi zainstalować nową wersję. Od tamtego czasu wybuchły takie narzędzia jak Gmail i wszystko to, co zawiera się pod znaczeniem słów „usługi chmurowe”. Tak naprawdę interfejs użytkownika jest czymś bardzo reaktywnym, ponieważ musimy reagować na akcje użytkownika, kliknięcia i wszystko, co on robi z naszym UI’em. Bardzo przyzwyczailiśmy się do reaktywnych aplikacji, które automatycznie wyświetlają nam najnowsze rzeczy w tle. Aplikacja nam się na żywo odświeża tak jak Facebook, Instagram, nowe posty dochodzą na górę i dostajemy powiadomienie „zeskroluj na górę”, bo tam się coś pojawiło. To wszystko samo na siebie reaguje. Można powiedzieć, że jest żywym organizmem. Właśnie tutaj to reaktywne programowanie jak najbardziej nam pasuje.
Obecnie najpopularniejszą biblioteką jest RxJS, który jest jakby zależnością core’ową dla Angulara, jego routing, jego HttpClient jest oparty o RxJS-a, tam już wszystko, co można, jest Observable, a nie Promis’em. Tak samo Nest po stronie backendu też wprowadził to, że można z kontrolera zwrócić value, które zostanie zwrócone, lub Promise, lub Observable. Żyjemy w czasach, w których przyzwyczajamy się do reaktywności bardzo szybko. I to nam daje RxJS i obecne frameworki. Angular ma async pipe, dzięki czemu w templatce możemy przekazać stream i async pipe automatycznie subskrybuje się do tych danych, prosi o te dane, bo musi wyświetlić w templatce. Tak naprawdę musimy zadać sobie pytanie, jaką aplikację robimy, bo czasami zwykły CRUD można dalej napisać na serwisach i na Promis’ach.
Ja obecnie pracuję nad SlackMap’em – jest to aplikacja mapowa. Chcę, żeby automatycznie wyświetlał na mapie punkt – jak zsumuję na dany punkt mapy, to żeby na tej mapie automatycznie pojawiły mi się punkty, które ludzie tam umieszczają. Samo przesuwanie mapy, ładowanie w to miejsce nowych punktów i zarządzanie tym wszystkim to wiele źródeł danych, które trzeba zmerdżować i obsłużyć. Wtedy programowanie reaktywne jak najbardziej nam się przydaje, aby to bezpiecznie ogarnąć, ponieważ musimy pamiętać, że skomplikowana aplikacja będzie miała skomplikowany kod.
Nie ma więc złotych rozwiązań, że reaktywne programowanie pozwoli mi bardzo ciężką aplikację napisać w banalny sposób. Tak niestety nie ma. Złożona aplikacja będzie miała równie złożony kod. Jedynie możemy użyć lepszych narzędzi, jak Observable, jak RxJS, żeby kod był łatwiejszy w utrzymaniu i w zrozumieniu.
Czy w stosie technologicznym, z którego korzystasz, są jakieś narzędzia ułatwiające testowanie aplikacji wykorzystujących podejście reaktywne do programowania? Bo to jest zwykle utrudnione, gdyż mamy asynchroniczne zdarzenia, które mogą wystąpić lub nie. Jak sobie poradzić z przetestowaniem tej aplikacji, sprawdzeniem, czy ona działa tak, jak powinna?
Zaczynając od testowania, to po pierwsze musimy zacząć pisać aplikację z myślą, że będzie ona testowana. Dzięki temu będzie architektonicznie tak zrobiona, że będzie można ją testować. Tu z pomocą przychodzi taki pattern jak Redux. W Angularze mamy NgRx, implementację Redux’ową. Sam pattern narzuca nam już rozdzielenie logiki biznesowej i odpowiedzialności na różne miejsca kodu, który jest bardzo łatwo testowany. Do tego mamy takie narzędzie jak RxMarbles (marble-testing) do testowania streamów. Możemy tam sobie zaginać czas, testować streamy, zaprojektować stream, że tu co pięć sekund przyjdzie event, a na streamie event – co dwie sekundy. I projektujemy stream, który ma być wyjściowy. To wszystko już nie czeka na odpowiedni czas, tylko w testach czas jest automatycznie przyspieszany, więc możemy w bardzo prosty sposób napisać testy streamów i tych Observable.
Do tego dochodzą później testy end to end. Obecnie narzędzia są wbudowane w Angulara, jak np. Protractor. Jeśli użyjemy narzędzia NX, to oprócz Protractora możemy testować aplikację w Cypress, możemy użyć Jesta lub Karmy. Czas minął, więc mamy ogromne możliwości. I to jest już automatycznie wpięte w nasz stack developmentu. Jedynie trzeba poświęcić trochę czasu, żeby poszukać informacji, jak się pisze testy, i można to testować. Odkąd mamy Google Chrome Headless, a Google Chrome możemy odpalić na serwerze w konsoli bez otwierania okienka, narzędzia poszły dużo do przodu. Nasze chęci, możliwości nauki i testów, i całe środowisko jest obecnie super spięte. Gdy zaczynałem przygodę z JavaScriptem, o testach jeszcze się nie słyszało. Może trochę, ale to wszystko to była wiedza tajemna, chowana gdzieś po kątach. Dzisiaj to jest wiedza wyłożona na stół. Coraz częściej spotykamy się z podejściem: „Jak to, nie piszesz testów?”.
Wspomniałeś o tym, że rozwijasz własną aplikację. Jak to obecnie wygląda w twoim przypadku? Pracujesz na etacie czy jesteś freelancerem, czy masz swój projekt?
W zeszłym roku, po 10 latach pracy na etacie i w projektach, postanowiłem spróbować nowej ścieżki kariery. Zostałem trenerem, więc obecnie przygotowuję szkolenia. Mam swoje trzy autorskie programy w Sagesie. Jest to reaktywne programowanie z RxJS, zarządzanie reaktywne stanem aplikacji z NgRx w Angularze i oczywiście pisanie backendu w NestJS. Teraz przygotowuję czwarty program, którym jest zarządzanie projektem fullstackowym, z Monorepo i z narzędziem Nx. Na tym oparty jest też mój projekt SlackMap. SlackMap to aplikacja mapowa, która pozwala odnajdywać osoby o tych samych zainteresowaniach sportowych. Gdy zacząłem programować w 2007 r., trafiłem do grupy wolontariatu studenckiego, gdzie uczyłem dzieci żonglować. Dorabiałem na festynach, chodziłem na szczudłach, byłem mocno związany z kuglarstwem, takie były początki. W Lublinie współorganizuję Urban Highline. Jest to część karnawału sztukmistrzów. Odbywa się zawsze w ostatni weekend lipca, trwa od czwartku do niedzieli. Moim zadaniem jest na cztery dni wyjąć okna z trzeciego piętra na lubelskiej Starówce, postawić tam belki, powiesić taśmy. I co roku z dwudziestu krajów przyjeżdżają do nas chętni, żeby pospacerować sobie nad naszymi głowami na tej taśmie. To się nazywa slackline, a my ćwiczymy jego odmianę highline, czyli taśma slackline jest zawieszona wysoko. Oczywiście jesteśmy zabezpieczeni, mamy na sobie uprząż, jesteśmy przywiązani do lonży. Lonża ma na drugim końcu dwa ringi stalowe, które ciągniemy za sobą, spacerując po taśmie. Jeśli odpadniemy, to na tym zawiśniemy. Później musimy się wdrapać, wstać i możemy iść dalej. Taśma oczywiście jest podwójna. Jak coś zawiedzie, to zawsze z boku coś nas wyłapie.
W tym roku będzie już jedenasta edycja. Jak dotąd udało nam się bez większego uszczerbku organizować ten festiwal. I właśnie SlackMap to taka aplikacja, w której postanowiłem połączyć razem te dwie pasje. Dzięki temu slacklinerzy mogą wejść na mapę, zzoomować miejsce, w którym są, i zobaczyć, czy ktoś ćwiczy slackline, gdzie są możliwości powieszenia taśmy, jakiś park, kanion albo drzewa nad wodą.
Tę aplikację zacząłem w 2011 r. i pomału robiłem ją jako projekt poboczny. Obecnie jest już przepisana z PHP. W 2015 r. przepisałem to na TypeScript Node.js, grafową bazę danych OrientDB. Obecnie kończę refaktoring na najnowszą wersję Angulara. Wszystkie szkolenia, które prowadzę, są oparte na kodzie na przykładzie SlackMap. To jest interesujące z perspektywy uczestnika. Często w ankietach kończących szkolenie dostaję: „Bardzo fajnie zobaczyć, że to, czego nauczyłem się dzisiaj, ma zastosowanie w ciekawej aplikacji”.
Druga sprawa: najnowsza wersja SlackMapy jest open-source’owana, czyli gdy na każdym szkoleniu robimy ćwiczenie, to odsyłam do kodu na GitHubie, gdzie uczestnik może w produkcyjnej wersji zobaczyć, jak w większym kontekście całej aplikacji dane zagadnienie wygląda. Oczywiście każdy może się przyłączyć, zrobić pull requesta i kontrybuować, odpalić kod lokalnie u siebie na maszynie.
Musisz zrobić hackathon! Wtedy część funkcjonalności będzie zrealizowana przez uczestników hackathonu.
Tak, jest to w planach. Bardzo chciałbym robić boot campy albo hackathony, w ramach których jedziemy na Gran Canarię, gdzie jest duże środowisko highline’owe. Rano programujemy, po południu wieszamy taśmy i ćwiczymy. Obecna wersja SlackMapy też jest rozszerzona na inne sporty, ponieważ sam żongluję, chodzę po taśmie, skaczę na trampolinach. Obecnie robię kurs nurkowania na bezdechu, freedivingu. SlackMap w najnowszej wersji będzie miał możliwość dodania innych sportów. Jeśli pojadę prowadzić warsztat do Wrocławia, to na SlackMapie mogę znaleźć osoby, które chodzą po taśmie. Slackline plus nurkowanie i możemy razem pójść na trening. Projekt jest obecnie dość popularny. Mam ponad 800 użytkowników, ponad 3,5 tys. spotów oznaczonych w 75 krajach. Jak się spojrzy na mapę slackmapową, to ona jest już cała w punktach.
Czy też jest aspekt czasowy? Czy wiadomo, że ta lina jest w danym momencie rozciągnięta, czy chodzi o to, że jest możliwość jej rozciągnięcia?
Obecnie chodzi o możliwość. Bo jak chcę powiesić 200-metrową taśmę w jakimś mieście, to nie jest łatwo znaleźć park, w którym akurat są idealne drzewa, a teren jest tak ukształtowany, że jest troszkę wklęsły. Druga sprawa to pozwolenie. Na przykład w Lublinie na placu Litewskim jest to zabronione, ponieważ drzewa są pod ochroną. Osoba, która podróżuje i ma ze sobą taki podręczny zestaw, mogłaby tam narobić nam, lokalnym slacklinerom, szkody. Więc plac Litewski oznaczony jest na czerwono, czyli osoba, która podróżuje, może sobie zzoomować, kliknąć i zobaczyć info, że tu jest zabronione. Jeśli chcesz w Lublinie rozwiesić taśmy, musisz iść do następnego parku. To pozwala dzielić się lokalną wiedzą, a po drugie – bezpieczeństwem, czyli dodawać wypadki, jeśli coś się stało, albo gdzieś jest coś, na co trzeba mocno uważać, są jakieś problemy z prawem albo z terenem, gdzieś jakaś skała jest ruszana i nie powinno się tam wieszać. To wszystko można umieszczać na SlackMapie i w centralnym miejscu budować bezpieczne społeczności dla danego sportu.
Jak dotąd robiłem to samemu, ale jeśli poświęcam temu czas po pracy, nie do końca jest to dobre dla zdrowia. Postanowiłem zrobić to open-source’owo i już mam pierwszych kontrybutorów. Ze Stanów odezwał się chłopak, który ćwiczy parkur. Mówi, że w parkurze jest kilka takich aplikacji, ale wszystkie umarły, bo to był jakiś pojedynczy projekt studencki. Po studiach poszło się do pracy i wszystko umiera. Jak tylko zopen-source’uje to, to on jest chętny, żeby dorzucić informacje o tym, gdzie można ćwiczyć parkur. Więc jest szansa. Sam kod będzie otwarty, dane, które wprowadzamy, są na Creative Commons Licence, czyli tak jak mamy OpenStreetMapa, który dostarcza nam dane mapowe, tak samo chciałbym, aby SlackMap był miejscem, w którym dane są otwarte.
Te dane mogą być wykorzystywane do tworzenia innych aplikacji. Bo tak naprawdę otwieranie danych sprawia, że pojawiają się nowe pomysły. Tak jak mamy Jakdojade.pl, to gdyby dane MZK i miejskich przedsiębiorstw nie były otwarte, takie aplikacje nie miałyby możliwości powstania. Mocno wierzę w otwartą społeczność. Sam SlackMap będzie komercyjny. Mam kilka pomysłów na jego biznesowe zastosowanie, ale dzięki temu, że kod jest otwarty, chcę być transparentny, że nie sprzedaję niczyich danych. Włożyłem w to mnóstwo pracy, więc chcę, żeby to było jednym z moich źródeł utrzymania. Ale kod jest otwarty, więc można sprawdzić. Jeśli mi ufacie, jeśli chcecie się rozwijać, to moje szkolenia są oparte na tym kodzie. Wtedy można organizować jakieś podcasty, hackathony.
Wydaje się, że taka platforma ma wiele zastosowań. Bo jak sam mówisz, jest wiele sportów, ale też jest kwestia dronów, czyli gdzie można latać, gdzie nie można. To kojarzy mi się z podobną platformą, gdzie mamy zaznaczone jakieś obszary.
My np. mamy konflikt. Obecny rekord – czyli największa taśma slackline, jaka została powieszona – ma 2,8 kilometra, prawie 3 kilometry. Teraz na majówkę planujemy pojechać na Słowację i powiesić 400, może 500 metrów. To robią chłopaki oderwani od komputera. I tu pojawia się problem z miejscami, w które może przylecieć helikopter ratunkowy. Jeśli jesteśmy wyżej w górach, to tam base jumperzy skaczą i latają w wingsuit’ach, gdzie latają paralotniarze. Mamy już dosyć spory konflikt. Jak robi się takie projekty na bardziej otwartych przestrzeniach, to musimy zgłosić, że tam będzie powietrzna przeszkoda, żeby jakiś samolot, np. medyczny, ratunkowy, miał o tym informację. I taka aplikacja będzie idealnym miejscem, żeby to wszystko w jednym miejscu zgrać, najlepiej reaktywnie.
Brzmi bardzo fajnie, zapraszamy w takim razie na slackmap.com i na festiwal w Lublinie, o którym mówiłeś, czyli ostatni weekend lipca. Tam też można cię spotkać.
Jako organizator w większości biegam i jestem zapracowany. Z każdym rokiem organizacja idzie coraz lepiej. Okazało się, że zyskaliśmy taką popularność, że mieliśmy lata, w których było ponad 300 uczestników. Fizycznie nasz trybunał koronny, z którego najwięcej taśm wychodzi, po prostu pękł w szwach. Od zeszłego roku mamy ograniczenie do 250 osób. To sprawiło, że mam już troszkę spokojniejszą głowę. Czasami jak jest wolna chwila, wchodzę na taśmy. Wszystkie osoby, które to organizują, jak najbardziej aktywnie ten sport uprawiają. W zeszłym sezonie byliśmy w Banja Luce w Bośni. Tam jest kanion o głębokości 250 metrów i szerokości 400 metrów i tam właśnie w zeszłym roku udało nam się pokonać rekord Polski, czyli 413 metrów. Polega to na tym, że wstaje się na początku i bez upadku dochodzi do samego końca. Z moim kolegą we dwóch udało nam się pokonać tę taśmę. Kolega jest studentem i jest młodszy, więc już pobił nasz wspólny rekord. Obecnie wynosi on 610 metrów. Zobaczymy, majówka się zbliża, może pobijemy kolejne rekordy.
Na jednej linie staje jedna osoba czy może chodzić po niej kilka naraz?
To bardzo ciekawe, bo obecny rekord świata wynosi 1,9 kilometr, czyli udało się przejść ten dystans od początku do końca. To było w Kanadzie. Przy tak dużej długości osoba, która jest na środku, nie czuje, że ktoś z tyłu wchodzi. Tam było tak, że był moment, gdy trzy osoby szły po taśmie. Jedna już praktycznie schodziła, była pod koniec, jedna była na środku, a trzecia zaczęła startować. Jak jedna z nich odpadnie, to zrobi falę i rzeczywiście może te inne zrzucić. Ale to byli zawodnicy, którzy mają taki poziom, że to było dla nich dosyć pewne, że mogą wejść i bezpiecznie przejść. Są tzw. tandemy, czyli chodzi się i trzyma za ręce we dwójkę. To jest kolejny level. Czasami robi się tzw. Rumble, czyli dwie osoby startują z obu stron, idą – albo po prostu stoją – i próbują utrzymać się na taśmie, a drugą osobę zrzucić. To są już zawody-zabawy. Czasami na dłuższych taśmach wstaje się, jest się w jednej trzeciej i dwóch trzecich i po prostu się bawi.
Niesamowite, tyle rzeczy do spróbowania w ciągu życia! Zachęcamy do spróbowania i slackline’u.
Dzięki wielkie, Piotr, za rozmowę. Bardzo ciekawe zainteresowania i ciekawa rozmowa o programowaniu frontendu i nie tylko. Do zobaczenia i do usłyszenia!
Zapraszam na warsztaty.