Przejdź do treści

DevStyle - Strona Główna
W czym Git jest lepszy od TFS?

W czym Git jest lepszy od TFS?

Maciej Aniserowicz

18 stycznia 2012

Tools

[

uwaga: w tym poście piszę o aspekcie kontroli wersji w TFS, a nie o TFS jako całym kombajnie do zarządzania projektem; powinno to być oczywiste, ale mimo wszystko zaznaczam żeby nie było zażaleń

]

Programiści znający oba rozwiązania, zobaczywszy tytuł posta, mogą się tylko uśmiechnąć i mruknąć: “a o czym tu w ogóle pisać? we wszystkim!“.

Jednak osoby znające TYLKO TFSa nie chcą, złośliwcy, wierzyć na słowo dopóki nie zobaczą. No cóż, nie będą błogosławieni, ich strata. Postaram się jednak spisać tutaj kilka rzeczy, które być może zaciekawią co bardziej otwarte umysły i skłonią do zainteresowania alternatywą dla ich ukochanego molocha. Nie jest to bynajmniej pełna lista, a raczej zrzut mojego wewnętrznego RAMu po kilkunastu minutach krótkiej refleksji.

DVCS

Wiele z przewag Gita nad TFS wynika z zasadniczych różnic pomiędzy scentralizowanym a zdecentralizowanym podejściem do kontroli wersji. Więcej na ten temat pisałem w postach Git – rozproszony system kontroli wersji oraz Dlaczego już nie lubię SVN. Zapraszam również tam, a póki co…

Praca offline

Wiem, że TFS oferuje koncepcję “pracy offline”. Ale co to za praca? Wielkiej łaski VS mi nie robi że pozwoli zmodyfikować pliki jeśli nie mam połączenia z internetem – tego by jeszcze brakowało, żebym nie mógł tego robić! Nie ma to zbyt wiele wspólnego z kontrolą wersji. Pracując z DVCS mam LOKALNIE dostęp do całej historii. Mogę więc przeglądać commity, robić diffy, chodzić między wersjami, czytać logi – wszystko to bez jakiegokolwiek kontaktu ze zdalnym serwerem. Oprócz samego faktu, że mogę to robić offline, bardzo ważna jest też jeszcze jedna kwestia: WYDAJNOŚĆ. Tego nie da się porównać. Podczas gdy TFS musi skontaktować się z serwerem aby wykonać prawie każdą operację, Git ma wszystko czego potrzebuje u mnie, na mojej maszynie. Jedyne co może ograniczać wydajność takiego rozwiązania to prędkość dysku twardego, która przy coraz większej dostępności SSD powoli staje się czynnikiem pomijalnym.

Lokalne commity

Ten punkt można równie dobrze wciągnąć pod poprzedni akapit, ale jest tak zajebiście istotny, że potraktuję go osobno. Jeśli się tego wcześniej nie doświadczyło to naprawdę trudno jest sobie wyobrazić swobodę i komfort, jaka za tym idzie. Równie trudno jest mi teraz wyobrazić sobie pracę bez takiej możliwości. Mogę robić commity choćby co pięć minut – więc moja working copy jest prawie cały czas “czysta” a stan lokalnego repozytorium – zdatny do użytku. Dzięki temu koniec z problemami typu “dobra, coś spieprzyłem, jak teraz wrócić do stanu, który działał?“. Teraz nie jest to problemem – wiem, że commit z działającym kodem  zrobiłem chwilę temu, zatem mogę spokojnie powrócić do tej wersji i zacząć od początku. To jak nieskończona liczba żyć w grze komputerowej, albo cheat włączający god mode. Mało tego – wcale nie muszę tych wszystkich commitów synchronizować z całym zespołem! Po zakończeniu pracy nad jakimś ficzerem poświęcam kilka chwil na analizę swojej pracy (zorganizowanej w niewielkie commity) i tak nimi manipuluję, żeby ich historia i zawartość nie śmieciła w repozytorium, jednocześnie zachowując całą drogę jaką przebyłem od “nie działa” do “działa”. I taką zmodyfikowaną historię wysyłam w miejsce “kontaktu” z resztą dev-teamu.

Nie można mylić tego z funkcjonalnością “shelve” oferowaną przez TFS. Podobna rzecz jest zawarta również w Gicie (“stash”), ale to zupełnie inna koncepcja.

Pliki readonly? NIE!

Git nie traktuje naszego kodu jako “solucji-polucji” edytowalnej z jednego-li tylko, właściwego narzędzia. Git traktuje całe rozwiązanie jako zera i jedynki porozrzucane między plikami. Możemy więc edytować co chcemy i jak chcemy, a Git sam zobaczy co i jak zostało zmodyfikowane. Bez ograniczeń. Mało tego – Git jest na tyle sprytny, że sam wykryje taką choćby operację jak “rename”!

Checkout / exclusive lock? STOP!

Wiem, że niektóre zespoły zmuszone są przez TFS (a raczej jego prymitywny, niedziałający, żenujący merge) do stosowania “exclusive locks”, czyli tylko jedna osoba może pracować nad danym plikiem. Przecież to jest ograniczenie tak durne i tak niesamowicie nielogiczne! Co komu do tego nad czym pracuję? Co mi do tego który plik zmienia ktoś inny? A co jeśli jest to .csproj, albo jeśli robię refactoring dotykający kilkunastu klas? Cały zespół ma czekać aż skończę? Albo, co gorsza, ja mam czekać aż ktoś coś skończy?;) Niech każdy zajmie się swoją robotą, a system kontroli wersji niech domyśli się jak z tym sobie poradzić i pomoże nam w połączeniu zmian.

W Gicie nie jest to problemem – algorytm merge’owania zmian jest tak dobry, że bardzo sporadycznie zachodzi konieczność ręcznej manipulacji plikami przy tym procesie. A nawet jak już zachodzi to bez większego problemu można z tym sobie poradzić.

Czyż nie lepiej jest zająć się swoją robotą zamiast czekać aż kolego z biurka obok (jak mamy szczęście) lub z innego kontynentu (jak mamy pecha) “zwolni” plik?

Branche? TAK!

Gałęzie w TFS traktowane są bardziej jako narzędzie do oznaczania “wersji na produkcji”. Czyli przed wdrożeniem robi się nowy branch, a cały zespół dalej jedzie na jednej głównej gałęzi. Dlaczego? Bo w TFS nie działa merge, przez co programiści nie mają nawet możliwości eksplorować niezwykłej potęgi jaką daje bezbolesne rozgałęzianie kodu.

A co powiecie na lokalne branche? Typowy workflow u programisty pracującego z Gitem wg zasady “branch per feature” wygląda tak: zrób gałąź -> pracuj -> ściągnij najnowszą wersję gałęzi głównej -> połącz swoją gałąź z gałęzią główną -> wypchnij zmiany na zewnątrz. Przy czym krok 2) może być przerwany przez najróżniejsze “wrzuty”. Wyobraźmy sobie, że implementuję jakiś fajny ficzer, aż tu nagle przychodzi zgłoszenie: na produkcji wyskoczył błąd, masz rzucić wszystko i się nim zająć! W Gicie po prostu wracam do głównej gałęzi, zostawiając całą swoją pracę w “feature branch”, robię co jest do zrobienia, i ponownie przełączam się do przerwanej pracy. Nie mówcie że nie znacie tego z autopsji.


To tylko wierzchołek góry lodowej, bo możliwości Gita są po prostu ogromne. I TFS nie jest w NICZYM lepszy (nie zaryzykuję stwierdzenia, że jest gorszy  we WSZYSTKIM).

Naprawdę zachęcam do bliższego poznania Gita. Na blogu pisałem o nim kilkukrotnie pokazując co fajniejsze ficzery (jak modyfikacja historii czy bisect), w necie też jest tego sporo… I wkrótce kolejne kilka słów z mojej strony na ten temat, ponownie w kontekście TFSa.

Teraz chętnie poczytam kolejne komentarze w stylu “używam TFSa i nic z tego co napisałeś nie jest mi potrzebne“. 3, 2, 1 GO!

A tak na serio: jeśli masz, Czytelniku Najsłodszy, ochotę coś takiego napisać, to zrób mi tę przyjemność i naprawdę daj, choćby na kilka dni, szansę Gitowi. Obiecuję: jeśli podejdziesz do tego z odpowiednim nastawieniem (czyli innym niż “udowodnię sobie i wszystkim że TFS mi wystarcza“) – nie zawiedziesz się, a Twój codzienny komfort wzrośnie. Czyż nie na tym m.in. polega nasza praca – szukaniu i stosowaniu coraz to lepszych rozwiązań?

P.S. Oczywiście (prawie) wszystkie powyższe punkty znajdują zastosowanie nie tylko w konfrontacji Git-TFS, ale także Mercurial-TFS czy Git-SVN. Jednak moja obecna sytuacja opiera się na tych dwóch narzędziach, więc i na nich się skupiam.

Zobacz również