Kolejny bogaty tydzień w naukę. Sporo projektów w różnych językach z różnymi ludźmi. Takie tygodnie są najlepsze. Każdy projekt ma swoją własną jire. 3 osobne jiry w dodatku każda w innej wersji. Można się od tego mocno zakręcić. Zapraszam na porcję wiedzy z 43 tygodnia. Dużo będzie o Angularze.
AngularCLI
Okazało się, że AngularCLI podczas tworzenia jakiegokolwiek elementu przez ng g tworzy pliki z końcówkami linii dla Linux-a czyli LF. Jest o tyle dziwne, że nie da się tego zmienić. Można wymusić w projekcie w aby tslint-cie sprawdzał jakie są końcówki i krzyczał, że ma być inaczej ale pliki i tak zostaną utworzone z LF. Git zamienia te pliki automatycznie na CRLF (o ile został tak skonfigurowany) i niestety SVN-a też trzeba na siłę skonfigurować aby wszyscy w zespole mieli te same końcówki.
Problem występuje tylko wtedy, gdy mieszamy projekt Angularowy z projektem .Net. Wtedy pliki *.cs są w CRLF a *.ts są w LF.
JavaScript metoda sort
Przykro przyznać ale dopiero wczoraj odkryłem (okupione to było kilku godzinnymi problemami) jak działa metoda sort() w JS. Dla przykładu (można to odpalić w konsoli F12) mamy [„12″,”1″,”3”].sort(). To, jeśli ktoś myśli, że to będzie posortowane dobrze to się myli. Jeśli ktoś chce posortować tablicą string-ów w JS to polecam od razu poczytać to: https://stackoverflow.com/questions/51165/how-to-sort-strings-in-javascript. Krótko mówiąc JS sortuje tak jak .Net i metoda sort musi zwrócić -1, 0 albo 1 i dla stringów różne wartości dają różne liczby i to nie zawsze jest ok. Najszybciej da się to rozwiązać tak: [„12″,”1″,”3”].sort((a,b)=>a-b). Szczegóły są w tym linku. Masakra!
RxJS Observable<T>
Nauczyłem się w końcu, że metoda .subscribe() nie wykonuje się zawsze, gdy obiekt się zmieni jednak działa to tak, że robiąc subscribe() tak naprawdę wykonujemy funkcję. To oznacza, że dopiero w tym momencie zostanie wykonane np: get do api i gdy api coś zwróci to nastąpi wykonanie tego co w subscribe(). Szczegóły są tutaj: https://rxjs-dev.firebaseapp.com/guide/observable
Żeby to jeszcze bardziej uzmysłowić to można założyć, że Observable<T> to taka funkcja, która możne zwrócić klika wartości. Coś podobnego jest w .Net-cie, gdy na funkcji użyjemy yield return. Wtedy funkcja zwraca klika wartości do listy. I tak samo działa Observable<T>. (oczywiście nie jest to idealny przykład ale mi pomogło)
Zdecydowanie polecam dużo czytać o RxJS, bo można wtedy sporo czasu sobie zaoszczędzić.
RXJS Subscription()
Przez klika dni miałem następujący problem. Najpierw pobierałem coś z API_1 potem te wyniki (który były tablicą obiektów) kierowałem do kolejnego wywołania API_2, które dla każdego elementu tablicy wywoływał GET-a a na końcu wyświetlałem listę na widoku. Problem polegał na tym, że robiąc zapytanie API_2 do listy wynikowej trafiały mi obiekty w różnej kolejności (bo API_2 w różnym czasie zwracało elementy dla pojedynczego elementu w liście). Koniec końców okazywało się, że lista wynikowa ma różną kolejność. Każde wywołanie zwracało mi obiekty w różnym układzie.
Jak w takim razie posortować obiekty dla Observable<T>. Trochę to zajęło. Ale rozwiązanie okazało się banalnie proste. Chodziło o metodę subscribe(), którą domyślnie można wywołać tak np: .subscribe(data=> {…..}) jednak takie wywołanie pokrywa tylko pojedynczy obiekt z Observable<T>. Mając tylko jeden element nie mogę tego dobrze posortować. Najlepiej i najprościej jest używać innego przeciążenia tej metody, takiej jak poniżej:
.subscribe( { next: data => notSortUserCompanies.push(data), error: null, complete: () => { this.quicksortService.sort(notSortUserCompanies); this.UserCompanies = notSortUserCompanies; this.loading = false; }});
Parametr next() robi to co robi domyślnie metoda .subscribe(data=> {…..}). Metoda error robi to co powinna robić no i w końcu metoda complete(), która jest uruchamiana na końcu jak dany obiekt przestanie emitować wartości. Tu może być dobry moment na sortowanie. Działa bardzo dobrze. Polecam!
TeamCity – FileContentReplacer
Ostatnim razem pisałem o AssemblyPatcher jednak po 2 tygodniach testów mogę powiedzieć, że to nie jest dobre podejście. TC potrafi podmienić przed budowaniem aplikacji pliki AssemblyInfo i zamienić AssemblyVersion i AssemblyFileVersion. Niestety zamiana AssemblyVersion jest czasem nie dobra, bo ktoś może mieć ustawione, że wczytuje bibliotekę w konkretnej wersji (nie pytajcie, dlaczego, tak się zdarzyło).
Lepszym i bardziej światowym podejściem jest użycie Build Features => File content Replacer.
- Pozwała wybrać pliki, które mają być podmienione.
- Pozwala wybrać wyrażenie regularne, którym można szukać linii, które chcemy podmienić
- Pozwala wybrać na co podmieniamy dane wyrażenie regularne.
Działa bardzo przyzwoicie. Polecam.