Dobry front-endowy framework

Hej!
Pytanie nie 100% związane z railsami / ruby ale dosyć mocno powiązane. Otóż - tworze już od dłuższego czasu aplikacje w railsach. Na początku do jakichś ajaxowych akcji używałem js.erb i remote: true (nie wiem czy istnieje jakaś ogólna nazwa na ten sposób obsługi ajaxowych requestów?) i jquery jednak z czasem, wiadomo, “widgety” i funkcjonalności javascriptowe stawały się coraz bardziej skomplikowane i używanie czystego jquery z pomocą remote: true przestało dawać radę. Co więcej, chyba nie jest to wskazany sposób obsługi zdarzeń asynchronicznych; wysyłanie ajax requesta pod określony adres i zwracanie już wygenerowanego kodu html - wydawało mi się to po prostu dziwne i nie poprawne. Poszukałem trochę w necie i faktycznie, nie tylko ja miałem podobne wątpliwości.

Postanowiłem więc spróbować embera i angulara. O ile pierwszy framework kompletnie mi nie podszedł, to w angularze praktycznie się zakochałem i zacząłem używać go gdzie tylko się dało. Jednak, niestety, wrażenie “niepoprawności” pozostało.

O co mi chodzi - aplikacje, które tworzę najczęściej składają się z widoków z wygenerowanym już markupem html. Nie są to ani “one-page app” ani żadne takie cuda, po prostu zwykła aplikacja railsowa z jakimiś pojedynczymi angularowymi “widgetami” (np. jakiś względnie skomplikowany formularz filtrowania wyników z select2 i takimi rzeczami), które komunikują się z aplikacją za pomocą jsonowego api. Zazwyczaj tworzę angularową dyrektywę i inicjuje ją w railsowych widokach za pomocą ng-controller.

O ile z angularem pracuje mi się świetnie, o tyle towarzyszy temu nieodparte wrażenie, że zaprzęgnąłem do bardzo prostej rzeczy (małe widgety) potężne narzędzie, stworzone z myślą o znacznie większych zastosowaniach (całe aplikacje z routingiem, autoryzacją itp). W skrócie to tak jak bym kupił sobie lotniskowiec żeby pływać nim z kumplem wędkować na jeziorze; niby się da ale ponton byłby znacznie lepszy.

Kolejną sprawą, która wzbudza moje wątpliwości jest komunikacja na linii rails <–> angular. Z grubsza, zawsze przekazuje do dyrektywy albo ID np. wyświetlanego aktualnie posta na blogu i resztę sobie dociągam z api, albo przekazuje cały obiekt JSON. Obydwie opcje również wydają mi się jakieś bardzo nienaturalne i mam poczucie, że robię to źle.

Ogólnie rzecz biorąc ciężko mi sformułować czego konkretnie szukam, pytanie brzmi raczej co robię źle i czy istnieją jakieś inne sposoby / frameworki o których nie mam pojęcia, a są stworzone właśnie dla takich zastosowań jakich szukam. Czyli nie osobne, kompletnie odizolowane od wszystkiego biekty (jak dyrektywy) a raczej coś, co świetnie wpina się w już wygenerowany markup i doskonale się z nim dogaduje. Bez przekazywania obiektu json jako argumentu.

Tak na pierwszy rzut react.js wydaje się idealne dla mnie (bo bazuje na już wygenerowanym markupie?) ale okropnie nie podoba mi się mieszanie się kodu html z kodem js. Chociaż być może o czymś nie wiem; po prostu nie udało mi się trafić na nic w stylu “react.js templates”. Wszędzie widzę raczej plik js z wymieszanymi znacnzikami html i kodem javascript.

Jak radzicie sobie z podobnymi wyzwaniami? Z góry dzięki za sugestie i podzielenie się swoimi sposobami

Jak Angular wydaje ci się za duży, spróbuj się z Backbone.

Emberjs na początku faktycznie przytłacza, zupełnie jak Railsy przy pierwszym kontakcie. I dokładnie tak samo olśniewa zajebistością swoich rozwiązań kiedy już go trochę poznasz i załapiesz filozofię.

Backbone koniecznie z Marionette. Jest to dobry punkt startowy, żeby poznać jak działa Ember i Angular, jednak nie wydaje mi się, żeby Backbone sprzyjał zwięzłemu kodowi :smiley: .

No właśnie @Tomash próbowałem kilkukrotnie podejść do embera ale niestety za każdym razem kończyło się tak samo - googlowanie rozwiązania jakiegoś problemu w 99% przypadków kończy się znalezieniem np. odpowiedzi na stack overflow, która niestety dotyczy jakiejś poprzedniej wersji z zupełnie innym api. Dlatego zawsze ciężko mi było rozwiązywać problemy - api zmieniało się na przestrzeni wersji 0.x - 1.x zbyt dynamicznie i żaden przykład / odpowiedź mi nie działał.

A swoją drogą - czy ember to nie jest coś “na poziomie” angulara? Czyli framework do pisania całych kompletnych aplikacji bardziej, niż do pojedyńczych widgetów?

Co do backbone’a to miałem plan go spróbować ale natknąłem się w internecie na wiele opinii, że jest spoko (albo raczej był) ale pojawili się godni następcy (angular i react.js) i warto spróbować właśnie ich.

Jakieś doświadczenia z react.js ?

nie jestem specjalistą w tej dziedinie, ale znajomy strasznie poleca właśnie reacta, a na blogu jego firmy (w sumie to nie jego firma , po prostu dla nich pracuje) co chwila pojawiają się coraz ciekawsze materiały w tym temacie. Chętnie więc podpinam się pod zapytanie dot. doświadczeń z react.js, do którego tak czy siak prawdopodobnie niebawem przysiądę :wink:

Jeżeli to ma być tylko do widgetów to jak już przedmówcy powiedzieli Backbone wydaje się być spoko opcją - nie trzeba do niego Marionette. Generalnie jeżeli zaczynasz sięgać Marionette to warto się zastanowić czy to nie jest odpowiedni poziom skomplikowania aby użyć Angulara / Embera.

Jeszcze odnośnie Angulara to on się akurat fajnie integruje z widokami renderowanymi po stronie serwera. Natomiast co do Embera to jak kiedyś szukałem za czymś podobnym to nie udało mi się znaleźć jakiegoś sensownego rozwiązania - different Ember app per server side view.

Odnośnie Reacta to też mam mieszane uczucia co mieszania markupu z kodem JS - używałem czystego JSa (JSX jakoś nie mogłem znieść). Używając Reacta nie masz takiej “eventowej” magii jak przy użyciu Backbone - property zmienia się to następuje automatyczne renderowanie widgetu.

Tak, nadążanie za Emberem przez ostatni rok było trudne.
Teraz są dobre widoki na stabilizację API.

Stackoverflow ma zawsze jedną i tą samą wadę: odpowiada na konkretne pytanie konkretnym rozwiązaniem, bez wyjaśnienia filozofii podejścia do tego problemu w danym frameworku (i tym samym wskazaniu miejsc w dokumentacji gdzie można szukać odpowiedzi).

Jak najbardziej, a nawet bardziej niż angular.

Ponad rok minął od mojej ostatniej wizyty w tym wątku. Zdążyłem stestować chyba wszystkie wiodące frameworki js dostępne na rynku i postanowiłem, że na wypadek gdyby ktoś miał podobny problem do mojego - postanowiłem spisać wnioski.

Generalnie rzecz biorąc nie mogłem się długi czas zdecydować pomiędzy angularem a react. Angular bardziej nadawał się w moim odczuciu do “kompletnych” SPA. Ja szukałem bardziej czegoś prostszego, do tworzenia mniejszych komponentów dlatego super wydawał się react + flux. Niestety wybitnie nie odpowiada mi JSX i generalnie pomieszanie kodu js z widokiem przypomina mi czasy, kiedy pare(naście) lat temu pisałem w PHP i wszystkie dostępne skrypty były kwintesencją “spaghetti-code”. A raczej nie chcę do tego wracać.

Ostatnio wpadłem na vue.js i jest on idealnym połączeniem wszystkiego co lubie w angularze i wszystkiego, co lubie w reactcie.

  • oddzielenie widoku od logiki/kodu
  • swoboda w organizacji kodu
  • możliwość tworzenia niezależnych komponentów
  • mało magii
  • prostota i przejrzystość
  • obsługa fluxa (ja akurat używam aktualnie alt.js)
  • …wiele więcej

Osobiście gorąco polecam! Dzięki wszystkim za pomoc.

Czyli pisanie w widoku rzeczy typu ng-if nie jest mieszaniem logiki i widoku ale napisanie <div> w JSX już jest?
Widzę pewną niekonsekwencję. Ogólnie sprawa z JSX jest taka że wszyscy zawsze uważali że musimy mieć jakieś szablony żeby dodać trochę dynamiki do naszych HTML podczas gdy zespół reacta uznał że więcej sensu robi wciągnięcie trochę HTML do naszych JSów. Dzięki temu zamiast szalonych ng-if, ng-repeat i uczenie się całego języka szablonów możemy pisać normalny JS i używać po prostu if, map etc.

EDIT:
Dodam jeszcze tylko że takie totalne rozdzielenie widoku od logiki też wcale nie jest genialnym pomysłem. Umówmy się, te tematy są ściśle powiązane i jedna rzecz której ludzie nauczyli się od jQuery jest to że taka separacja jest problematyczna. Przypomnijmy sobie czasy gdy kliknięcie na element wywoływało masę podpiętych gdzieś w javascriptach lecz nie do konca wiadomo gdzie akcji jQuery.

Tak, jest to mieszanie logiki ale nie w takim stopniu jak w angularze. W angularze jest cała masa takich mikro-języków, w vue praktycznie tylko if, else i pętle (przynajmniej z tego co póki co wiem). Nauczenie się tego to jakieś 3 minuty.

Rozumiem i szanuje podejście reactowe i JSX ale po prostu mi ono nie leży. To jest czysto subiektywna opinia, poparta jedynie osobistymi odczuciami. Spróbowałem, sporo popisałem, potestowałem - to nie to. Co więcej - spora część komponentów reactowych, któych potrzebowałem wymagała require.js i masy innych narzędzi, które nie za dobrze współgrają z railsami (tak wiem, jest kilka projektów, które starają się to usprawnić ale instalowanie tego wszystkiego albo, co gorsza, skonfigurowanie osobnego builda z gruntem/gulpem/webpackiem/whatever tylko po to, zeby dodać na stronie niewielkie widgety to totalny przerost formy nad treścią hehe).

Pytanie z czystej ciekawości, bez żadnych złośliwości (zdajesz się być zwolennikiem reacta/jsx) - czy gdyby zrezygnować w railsach/sinatrze/czymkolwiek z widoków na rzecz wpakowania całego kodu html w kontrolery (albo jakiś inny odpowiednik reactowych komponentów) i pomieszania go z kodem ruby w estetycznie podobny do reacta sposób, to dało by to nam - developerom jakieś korzyści zbliżone do tych oferowanych przez JSX ? Ogólnie nie pisze za dużo w JS i to trochę nie mój świat więc może po prostu czegoś d końca nie rozumiem ale widzę w takim rozwiązaniu głównie syf i zmuszanie frontendowców do używania rubiego (a w reactcie - designerów tnących layouty do używania javascriptu)

Żeby nie było - nie jestem przeciwnikiem reacta, jak pisałem jestem raczej na tak. Po prostu nie wszędzie bym go użył.

Nie odniosłem się w moim poście do Vue i wierzę że jest fajny i prosty. To jest właśnie to co lubie w minimalistycznych frameworkach. Może mój post brzmiał trochę złośliwie ale zapewniam Cię że nie miałem takiego zamiaru.

Na temat odczuć nie ma co dyskutować bo jak sam powiedziałeś są one subiektywne :wink: Chciałem się po prostu odnieść do uczucia mieszania widoku z logiką. Zaznaczyłem jedynie że niezależnie które podejście wybierzemy dzieje się to tak czy siak. Kwiestia jedynie jak rozmieścimy proporcje. Z reactem jest tak że to podejście jest po prostu całkiem inne od tego co znamy dlatego może budzić takie mieszane uczucia.

Odpowiadając na twoje pytanie. Myślę że troszkę źle ująłeś problem. Nie postrzegam reacta i JSX jako pakowanie całego HTML do kontrolerów. Myślę że taki kontroler dużo by się nie zmienił od tego co mamy teraz! Wyobrażam to sobie w taki sposób:

Cześć! Jestem twoim kontrolerem. Wybrałem dla ciebie wszystkie potrzebne dane a teraz proszę wy-renderuj mi z ich użyciem ten komponent bo sam lepiej wiesz jak sobie z nim poradzić

To jest dokładnie to co nasze kontrolery robią teraz.

Pozwole sobię na double posta.

Odnośnie tematu z JSX - Oglądam sobie dzisiaj nowe wideo mpjme (wiele osób go pewnie nie zna. jest to jeden z frontendowców ze spotify i prowadzi całkiem fajną videoserie na youtubie dotyczącą programowania. gorąco polecam)
W połowie 6 minuty wspomina on właśnie o naturalnym wstręcie webdeveloperów do JSX wynikającym z przyzwyczajeń i wierzeń. Ostatecznie argumentuje on że bierze się to z naszego przekonania że należy dążyć - i tutaj brakuje mi polskiego odpowiednika - do separation of concerns. I jest to naturalne. Wszyscy wiemy że lepiej jest nie mieszać ze sobą odrębnych zagadnień. Jednak potrzeba nam chwili, i tutaj jest cała istota potrzebna do zrozumienia JSX, że separation of concerns niekoniecznie znaczy separation of technologies

EDIT: Ah tak. Zapomniałem o linku. Wspomniany fragment

1 Like

JSX jest opcjonalny i ma nic wspólnego z HTML. Stąd nie jest żadne pomieszanie warstw. Była o tym dyskusja na Hashnode: “Why are some developers against mixing HTML and JavaScript (as in React)?

JSX jest opcjonalne, nie ma obowiązku go używać. Zresztą React dziś redukuje się to bezstanowych komponentów UI i jako taki staje się drugorzędny. To, co się liczy to bezstanowe, elastyczne komponenty UI, virtual DOM (jest już kilka rozwiązań), oraz dobre, centralne zarządzanie stanem.

Zobacz Cerebal (tu jest do niego boilerplate), inspirowany silnie Elm’em.

Bardzo dobrą alternatywą jest też sam Elm. Elm jest językiem eleganckim, statycznie typowanym z inferencją typów (jak Haskell), posiada pattern matching (jak Elixir i Erlang) i generuje docelowo bardzo wysokiej jakości, praktycznie bezbłędny JavaScript.

Elm jest bardzo wydajny. Jeśli kompilator przepuści usera, to ma praktycznie pewność że w generowanym JS nie wyskoczy mu żaden runtime exception, który jest zmorą JavaScriptu. Sam kompilator działa jak doradca, podpowiada rozwiązania, a nie tylko informuje o błędzie. Same wyświetlanie błędów jest też genialne. Tu są dwa, bardzo dobre kursy wprowadzające do Elma: https://pragmaticstudio.com/elm

Połączenie Elm’a na frontendzie a Phoenixem na backendzie to jest niezły power. (Nie da się ukrywać, że naturalnym następcą Rails jest Phoenix).

1 Like