Gdy w bibliotece, której używamy w projekcie, trafiamy na błąd, mamy dwie drogi. Możemy go załatać u siebie i zapomnieć albo zgłosić i odesłać poprawkę do autorów biblioteki. Pierwsza jest szybsza dziś, druga jest tańsza za rok. Wybieramy drugą, a ten tekst wyjaśnia, dlaczego to decyzja ekonomiczna, a nie gest dobrej woli.
Opisujemy też resztę naszej pracy z otwartym kodem: własne narzędzia publikowane na GitHubie, zasady, według których nie publikujemy kodu klientów, i to, co "pełne prawa do kodu" oznaczają w projekcie zbudowanym na bibliotekach z cudzymi licencjami. Na końcu jest lista rzeczy, które warto sprawdzić na GitHubie dowolnego wykonawcy, zanim podpiszesz z nim umowę.
- Poprawkę zostawioną w lokalnej kopii biblioteki trzeba nakładać ponownie przy każdej aktualizacji. Poprawka przyjęta u autorów jest utrzymywana razem z biblioteką.
- Nasz kod trafił do ponad 50 zewnętrznych projektów open source, między innymi PHPMailer, pydantic, Polly, FluentValidation, Monolog, Serilog, NLog, Ebiten, goquery, Pagefind i CommonMark.
- Kod klientów nie jest publikowany. Otwieramy własne narzędzia, takie jak vulp.
- "Pełne prawa do kodu" nie obejmują bibliotek zewnętrznych, które zostają na swoich licencjach. Dlatego licencje zależności sprawdza się przed oddaniem projektu.
Cztery formy pracy z otwartym kodem
Open source to u nas cztery różne rodzaje pracy, które się wzajemnie zasilają. Pierwszy to zlecenia: strony, panele, sklepy i aplikacje pisane dla klientów. Klient dostaje kod na własność z pełną historią commitów, a nie zamkniętą paczkę. Część wzorców i narzędzi, które powstają przy takich projektach, wraca potem do naszych otwartych repozytoriów, oczywiście bez kodu i danych samego klienta.
Drugi to własne projekty open source prowadzone od początku do końca, z publicznym repozytorium, wydaniami i obsługą zgłoszeń. Sztandarowym przykładem jest vulp, o którym piszemy niżej. Obok niego są mniejsze repozytoria: emulatory, biblioteki, boty. Na stronie open source projekty, które jeszcze nie są gotowe do użycia, mają oznaczenie "w budowie", zamiast udawać skończone.
Trzeci to kontrybucje do cudzych projektów. Gdy w bibliotece, na której stoi nasza praca, znajdujemy błąd albo brakującą funkcję, zgłaszamy issue, otwieramy pull request i przechodzimy przez review autorów. Tych projektów jest ponad pięćdziesiąt, a ich łączna liczba gwiazdek na GitHubie przekracza 400 tysięcy. Od razu dopowiadamy, co ta liczba znaczy: to gwiazdki projektów, do których dołożyliśmy kod, a nie gwiazdki naszych repozytoriów.
Czwarty to platformy SaaS, czyli nasze produkty, na których ktoś może założyć konto i pracować. Ich rdzeń często dzieli kod z otwartymi narzędziami, więc poprawka zrobiona przy jednym trafia do drugiego. To także powód, dla którego przy nowym zleceniu nie budujemy wszystkiego od zera: mamy fundamenty, które napisaliśmy sami i rozumiemy do ostatniej linijki.
Łatka u siebie kontra poprawka u autorów biblioteki
Weźmy konkretną sytuację. Biblioteka do walidacji danych w projekcie klienta źle obsługuje jeden przypadek brzegowy: pole z datą w określonym formacie przechodzi walidację, choć nie powinno. Poprawka to kilka linijek. Można ją wprowadzić na trzy sposoby i każdy ma inny koszt rozłożony w czasie.
Pierwszy sposób to obejście w kodzie projektu: dodatkowe sprawdzenie przed wywołaniem biblioteki. Działa od razu, ale zostawia w projekcie kod, który istnieje tylko dlatego, że biblioteka ma błąd. Za rok nikt nie pamięta, po co to sprawdzenie jest, a gdy biblioteka sama naprawi błąd, obejście zostaje jako martwy kod, którego nikt nie odważy się usunąć.
Drugi sposób to własna kopia biblioteki, czyli fork, albo automatyczne nakładanie łatki na zainstalowany pakiet. Poprawka siedzi tam, gdzie powinna, ale przy każdej aktualizacji biblioteki trzeba ją nałożyć ponownie i sprawdzić, czy nadal pasuje do zmienionego kodu. Gdy biblioteka wypuszcza poprawkę bezpieczeństwa, projekt z forkiem dostaje ją dopiero wtedy, gdy ktoś ręcznie przeniesie zmiany. W praktyce oznacza to, że forki starzeją się szybciej niż cokolwiek innego w projekcie.
Trzeci sposób to zgłoszenie błędu i pull request do autorów. Jest najwolniejszy na starcie, bo trzeba napisać test odtwarzający błąd, dopasować kod do stylu projektu i poczekać na review, które bywa kwestią dni albo tygodni. Po przyjęciu poprawka jest jednak utrzymywana przez autorów biblioteki, przechodzi przez ich testy przy każdej kolejnej wersji i trafia do wszystkich innych użytkowników. Projekt klienta wraca do oficjalnej wersji bez żadnych lokalnych modyfikacji.
Te sposoby się nie wykluczają. Projekt klienta nie powinien czekać na review w cudzym repozytorium, więc rozsądny układ wygląda tak: do czasu przyjęcia poprawki projekt działa na tymczasowo przypiętej wersji z łatką, a po wydaniu oficjalnej wersji z poprawką wraca do niej i łatkę usuwa. Ważne jest to, żeby tymczasowe rozwiązanie miało datę ważności, a nie zostało na zawsze.
Biblioteki, do których trafił nasz kod
Lista na stronie open source nie jest przypadkowa. To biblioteki, których używamy w projektach, więc błędy w nich znajdujemy przy normalnej pracy, a nie szukając okazji do kontrybucji. Obejmują kilka ekosystemów, bo piszemy w kilku językach.
| Biblioteka | Ekosystem | Do czego służy |
|---|---|---|
| PHPMailer | PHP | Wysyłanie poczty z aplikacji PHP, w tym przez SMTP z uwierzytelnianiem |
| Monolog | PHP | Logowanie w aplikacjach PHP, standard w wielu frameworkach |
| pydantic | Python | Walidacja i parsowanie danych na podstawie typów |
| Polly | .NET | Odporność na błędy: ponawianie żądań, circuit breaker, limity czasu |
| FluentValidation | .NET | Reguły walidacji obiektów zapisywane w kodzie |
| Serilog | .NET | Logowanie strukturalne |
| NLog | .NET | Logowanie z konfigurowalnymi miejscami zapisu |
| Ebiten | Go | Silnik do gier 2D |
| goquery | Go | Przeszukiwanie i przetwarzanie dokumentów HTML |
| Pagefind | Rust / JavaScript | Wyszukiwarka dla stron statycznych działająca bez serwera |
| CommonMark | wiele języków | Specyfikacja i implementacje formatu Markdown |
Widać tu wzór: dużo jest bibliotek od walidacji, logowania i odporności na błędy. To warstwy, które w projekcie klienta nie są widoczne w interfejsie, ale od których zależy, czy błąd w ogóle zostanie zauważony i czy aplikacja zniesie chwilową awarię usługi zewnętrznej. Właśnie w takich miejscach przypadki brzegowe wychodzą dopiero na produkcji, przy prawdziwych danych.
Znajomość tych bibliotek od środka ma bezpośrednie przełożenie na pracę przy zleceniach. Kiedy logi przestają się zapisywać albo walidacja przepuszcza błędne dane, szukanie przyczyny zaczyna się od kodu biblioteki, a nie od forum z pytaniami. Osoba, która przeszła review w danym projekcie, wie, gdzie są jego testy, jak jest zbudowany i które zachowania są celowe, a które są błędem.
Liczby i lista zmieniają się w miarę pracy, więc aktualny stan jest zawsze na stronie, a nie w tym wpisie. Katalog własnych projektów rośnie w miarę tego, co realnie wydajemy, a nie według planu, ile repozytoriów wypadałoby pokazać.
Review u obcych autorów uczy więcej niż review we własnym zespole
We własnym zespole zasady pisania kodu ustalamy sami. W cudzym projekcie obowiązują zasady autorów i trzeba się do nich dostosować, zanim ktokolwiek przeczyta pierwszą linijkę poprawki. Duże biblioteki mają przewodnik dla kontrybutorów, wymagania co do formatu commitów, czasem obowiązek podpisania umowy licencyjnej kontrybutora albo deklaracji pochodzenia kodu.
Automatyczne testy w dojrzałych projektach sprawdzają poprawkę na wielu wersjach języka i systemach operacyjnych naraz. Zmiana, która działa u nas na jednej wersji PHP albo .NET, potrafi nie przejść na starszej, którą biblioteka nadal wspiera. To uczy myślenia o kompatybilności wstecznej, które przydaje się potem przy każdym projekcie klienta, gdzie aktualizacja jednej usługi nie może zepsuć integracji z drugą.
Autorzy popularnych bibliotek odrzucają zmiany, które są za duże, łączą kilka poprawek naraz albo zmieniają publiczne API bez uzasadnienia. Prośba o rozbicie pull requesta na trzy mniejsze jest standardem. Po kilku takich rozmowach mniejsze, jednotematyczne zmiany stają się nawykiem także we własnych projektach, a to bezpośrednio ułatwia klientowi przeglądanie historii repozytorium, do którego ma dostęp.
Jest też korzyść najprostsza: kod czytany przez kogoś, kto nie ma powodu być uprzejmy, szybko pokazuje słabe miejsca. Maintainer biblioteki z tysiącami użytkowników nie przyjmie poprawki bez testu tylko dlatego, że autor jest miły.
vulp: narzędzie, które najpierw zbudowaliśmy dla siebie
Największy nasz otwarty projekt to vulp, menedżer pracy na wielu repozytoriach naraz, napisany w Rust, z interfejsem tekstowym w terminalu i zwykłym CLI. Rozwiązuje przyziemny problem: przy kilkudziesięciu repozytoriach ręczne sprawdzanie, które mają niezacommitowane zmiany, które są za gałęzią główną, a w których czeka pull request, oznacza wchodzenie do każdego katalogu po kolei.
vulp pokazuje stan wszystkich repozytoriów na jednym ekranie i pozwala wykonywać operacje seriami: synchronizację, commit i push na wielu repozytoriach naraz. Obsługuje pull requesty, zgłoszenia, listy zadań i statystyki bez wychodzenia z terminala. Pilnuje też reguł, żeby do repozytorium nie trafił kod w złym stanie.
Rust dobrze pasuje do takiego narzędzia. Program, który uruchamia się wiele razy dziennie i odpytuje wiele repozytoriów równolegle, powinien startować natychmiast i nie wymagać instalowania środowiska uruchomieniowego na każdej maszynie. Rust kompiluje się do pojedynczego pliku wykonywalnego, a jego model własności pamięci pilnuje poprawności kodu współbieżnego już przy kompilacji.
Otwarcie narzędzia wymaga pracy, której nie wymaga narzędzie wewnętrzne: dokumentacji dla ludzi spoza zespołu, usunięcia założeń pasujących tylko do jednej konfiguracji i komunikatów błędów zrozumiałych dla kogoś, kto nie jest autorem. Z tej pracy korzystają też jego twórcy, bo narzędzie przestaje zależeć od pamięci jednej osoby. Kod na GitHubie VulCodeCom każdy może sklonować, przeczytać i zbudować na nim własne rozwiązanie.
Publiczny kod jako dowód: co da się sprawdzić, a czego nie
Na wielu stronach software house'ów przeczytasz, że piszą czysty i przetestowany kod. Nie da się tego zweryfikować bez dostępu do kodu. Publiczne repozytoria są jednym z niewielu miejsc, gdzie zdanie o jakości pracy można sprawdzić samemu, bez pytania wykonawcy o zgodę.
W publicznym repozytorium widać historię commitów: czy zmiany są małe i opisane, czy przychodzą jednym gigantycznym commitem "initial". Widać, czy są testy i czy automatyczne sprawdzenia przechodzą. Widać, jak autor odpowiada na zgłoszenia. Na naszej stronie open source jest też wykres aktywności z ostatnich 90 dni, więc łatwo sprawdzić, czy praca nad kodem jest regularna, czy zdarzyła się raz przed publikacją strony.
Są też rzeczy, których publiczny profil nie pokaże. Większość kodu firmy, która pisze na zamówienie, należy do klientów i leży w ich prywatnych repozytoriach. Nasze konta mają ponad dwieście repozytoriów na przestrzeni ponad stu projektów, a publiczny profil nie pokaże tych, które są prywatne. Liczba linijek kodu, u nas ponad pięć milionów, mówi o skali pracy, a nie o jej jakości: pięć milionów linijek złego kodu to wciąż zły kod.
Dlatego publiczny kod traktujemy jako próbkę do obejrzenia, a nie jako certyfikat. Pokazuje, jak piszemy, kiedy nikt nie narzuca terminu, i jak zachowujemy się w cudzym projekcie, gdzie nie mamy żadnej władzy. Przy konkretnym zleceniu ważniejsze jest to, że klient ma dostęp do swojego repozytorium i środowiska testowego przez cały czas trwania projektu, a nie dopiero przy odbiorze.
Licencje: co wolno wziąć do projektu, do którego klient dostaje pełne prawa
Klient dostaje od nas pełne prawa do kodu i dokumentację pozwalającą przejąć projekt. Te prawa dotyczą kodu, który napisaliśmy. Biblioteki open source użyte w projekcie zostają na swoich licencjach i to one decydują, co klient może z nimi zrobić. Sklep albo panel oparty na ekosystemie npm czy Composer łatwo dochodzi do setek zależności pośrednich, więc sprawdzenie licencji powinno być osobnym krokiem przed oddaniem projektu, a nie formalnością.
| Licencja | Czy można użyć w zamkniętym projekcie | Co trzeba spełnić |
|---|---|---|
| MIT, BSD | Tak | Zachować informację o prawach autorskich i tekst licencji |
| Apache 2.0 | Tak | Jak wyżej, plus plik NOTICE, jeśli biblioteka go ma, i oznaczenie zmian; licencja zawiera udzielenie praw do patentów |
| MPL 2.0 | Tak | Zmienione pliki samej biblioteki trzeba udostępnić na MPL; własny kod obok nich może pozostać zamknięty |
| LGPL | Tak, przy odpowiednim łączeniu | Zmiany w samej bibliotece udostępnić na LGPL; przy dystrybucji aplikacji umożliwić podmianę biblioteki |
| GPL | Tylko bez dystrybucji | Jeśli program łączący się z kodem GPL jest przekazywany innym, całość musi być udostępniona na GPL z kodem źródłowym |
| AGPL | W praktyce nie w zamkniętej usłudze | Jak GPL, ale obowiązek udostępnienia kodu obejmuje też użytkowników korzystających z programu przez sieć |
Różnica między GPL i AGPL ma znaczenie dla aplikacji webowych. Zwykła GPL wiąże się z dystrybucją, czyli przekazaniem programu komuś innemu. Aplikacja uruchomiona na własnym serwerze i udostępniana przez przeglądarkę nie jest dystrybuowana, więc GPL nie wymusza tu publikacji kodu. AGPL zamyka tę lukę: jeśli użytkownicy korzystają ze zmodyfikowanego programu przez sieć, mają prawo dostać jego kod. Biblioteka na AGPL w panelu klienta może więc oznaczać obowiązek otwarcia panelu.
W aplikacjach mobilnych i desktopowych sytuacja jest odwrotna, bo tam dystrybucja zachodzi zawsze: aplikacja trafia na telefon albo komputer użytkownika. Biblioteka na GPL w aplikacji mobilnej oznacza, że cała aplikacja musi być udostępniona na GPL. Dlatego przy tego typu projektach licencje sprawdza się przy wyborze biblioteki, a nie po napisaniu połowy aplikacji.
Tabela opisuje ogólne zasady, a nie poradę prawną dla konkretnej umowy. Przy nietypowych licencjach, podwójnym licencjonowaniu albo bibliotekach z dodatkowymi warunkami komercyjnymi decyzję warto skonsultować z prawnikiem po stronie klienta.
Listę licencji wszystkich zależności, także pośrednich, da się wygenerować jednym poleceniem w każdym popularnym ekosystemie. Wynik warto dołączyć do dokumentacji projektu, bo przy przejęciu kodu przez inny zespół albo przy audycie u inwestora to pierwsze pytanie, które pada.
Samo wygenerowanie listy to połowa pracy. Druga połowa to przejrzenie pozycji oznaczonych jako nieznane albo niestandardowe, bo narzędzia rozpoznają licencję po polu w pliku pakietu, a autorzy czasem wpisują tam coś, co nie odpowiada plikowi LICENSE w repozytorium. Pakiet bez żadnej licencji nie jest "darmowy do użycia": domyślnie wszystkie prawa zostają przy autorze.
Czego nie publikujemy
Kod napisany dla klienta należy do klienta i nie trafia do publicznego repozytorium, nawet jeśli uważamy, że byłby przydatny innym. Nie publikujemy też jego fragmentów przerobionych tak, żeby nie było widać, skąd pochodzą. Jeśli klient sam zdecyduje, że chce otworzyć swój projekt, to jego decyzja, a pełne prawa do kodu to umożliwiają.
Otwarcie projektu klienta to więcej niż przełączenie repozytorium na publiczne. Trzeba wybrać licencję, usunąć z historii wszystko, co nie powinno być widoczne, i ustalić, kto będzie odpowiadał na zgłoszenia i przyjmował zmiany od obcych osób. Repozytorium opublikowane bez tej decyzji szybko zapełnia się pytaniami, na które nikt nie odpowiada, a to wygląda gorzej niż brak publicznego kodu.
To, co wraca do open source ze zleceń, to wzorce i ogólne narzędzia, a nie konkretny kod. Przykład: jeśli przy trzech panelach pisaliśmy podobny mechanizm eksportu danych, to w otwartym repozytorium może pojawić się ogólna biblioteka do takiego eksportu, napisana od nowa, bez logiki biznesowej któregokolwiek klienta. Poprawki do zewnętrznych bibliotek też nie zawierają niczego z projektu, w którym znaleźliśmy błąd, bo test odtwarzający błąd pisze się na minimalnym, sztucznym przykładzie.
Nigdy nie publikujemy konfiguracji infrastruktury produkcyjnej, kluczy, adresów wewnętrznych usług ani danych testowych pochodzących z prawdziwych systemów. Repozytorium, które ma stać się publiczne, trzeba przed otwarciem przejrzeć w całej historii commitów, a nie tylko w bieżącym stanie plików. Klucz usunięty w najnowszym commicie nadal jest widoczny w historii, więc jeśli kiedykolwiek się tam znalazł, trzeba go unieważnić, a nie tylko skasować z pliku.
Ile to kosztuje czasu i dlaczego się opłaca
Kontrybucja do cudzego projektu kosztuje więcej niż lokalna łatka, i nie ma sensu udawać, że jest inaczej. Trzeba odtworzyć błąd w izolacji, napisać test, który przed poprawką nie przechodzi, a po niej przechodzi, dopasować kod do konwencji projektu i odpowiadać na uwagi w review. Czasem poprawka zostaje odrzucona, bo autorzy mają inny pomysł na rozwiązanie problemu, i praca kończy się na dyskusji w zgłoszeniu.
Zwrot przychodzi później i w mniej oczywistych miejscach. Aktualizacja biblioteki w projekcie klienta nie wymaga ponownego nakładania łatek. Kolejny projekt korzystający z tej samej biblioteki od razu ma poprawioną wersję. Znajomość wnętrza biblioteki skraca szukanie przyczyn przyszłych błędów. Przy aktualizacjach bezpieczeństwa projekt jest na oficjalnej wersji i może przyjąć poprawkę tego samego dnia.
Własne otwarte narzędzia mają inny rachunek. Kosztują dokumentację, obsługę zgłoszeń od ludzi spoza zespołu i dyscyplinę wydań. W zamian dostajemy narzędzia sprawdzone na cudzych konfiguracjach, a nie tylko na naszej, oraz kod, który można pokazać komuś, kto pyta, jak pracujemy. Do testów wirtualizacji mamy homelab, więc narzędzia infrastrukturalne można sprawdzić na prawdziwych maszynach wirtualnych, a nie tylko na laptopie autora.
Nie wszystko się opłaca. Narzędzie tak mocno związane z wewnętrzną konfiguracją, że nikt inny nie mógłby go uruchomić, nie nadaje się do otwarcia. Publiczne repozytorium, którego nie da się użyć, to tylko obowiązek odpowiadania na zgłoszenia bez żadnej wartości dla kogokolwiek.
Osobny przypadek to biblioteka porzucona przez autorów: ostatnie wydanie sprzed kilku lat, pull requesty bez odpowiedzi, zgłoszenia bez reakcji. Wysyłanie tam poprawki to praca, która nigdy nie zostanie przyjęta. W takiej sytuacji uczciwe opcje są dwie: utrzymywać własny fork świadomie, z kimś odpowiedzialnym za niego, albo zaplanować zamianę biblioteki na utrzymywaną alternatywę. Z punktu widzenia klienta druga opcja jest zwykle tańsza, nawet jeśli wymaga więcej pracy od razu.
Jak wygląda porządna kontrybucja, krok po kroku
Jeśli prowadzisz zespół programistów i chcesz, żeby zaczęli odsyłać poprawki do bibliotek, poniższa kolejność oszczędza najwięcej czasu obu stronom. Kolejność jest ważna, bo najdroższa pomyłka to napisana zmiana, o której autorzy biblioteki dowiadują się dopiero z gotowego pull requesta.
bez kodu projektu, w którym go znalazłeś, najlepiej kilkanaście linijek, które każdy może uruchomić.
błąd mógł zostać już zgłoszony, naprawiony w nowszej wersji albo uznany za zamierzone zachowanie.
format commitów, wymagania co do testów, umowy licencyjne, zasady dotyczące zmian w publicznym API.
opisz problem i proponowane rozwiązanie, zanim napiszesz kod. Autorzy mogą mieć plany, o których nie wiesz.
jeden problem na pull request, test, który bez poprawki nie przechodzi, opis odsyłający do zgłoszenia.
pull request porzucony po pierwszej uwadze zostaje zamknięty, a następny od tej samej osoby jest czytany z mniejszym zaufaniem.
Pierwszy krok jest najczęściej pomijany, a daje najwięcej. Minimalny przykład odtwarzający błąd potrafi sam pokazać, że problem leży w naszym użyciu biblioteki, a nie w bibliotece. Wtedy zamiast pull requesta powstaje poprawka we własnym kodzie i nikt nie traci czasu na review.
Czwarty krok chroni przed najbardziej frustrującym scenariuszem: tygodniem pracy nad zmianą, którą autorzy odrzucają, bo planowali przepisać ten moduł w inny sposób. Krótkie zgłoszenie z pytaniem "czy przyjmiecie taką zmianę" kosztuje kilka minut.
Błędów bezpieczeństwa nie zgłasza się w publicznym issue. Opis podatności widoczny dla wszystkich jest instrukcją ataku na każdą aplikację, która jeszcze nie dostała poprawki. Dojrzałe projekty mają plik SECURITY.md z adresem do zgłoszeń albo włączone prywatne zgłaszanie podatności na GitHubie. Jeśli projekt nie ma żadnego z nich, napisz do autora prywatnie i zapytaj o kanał.
Po przyjęciu poprawki praca nie kończy się na zamknięciu pull requesta. W projekcie, w którym błąd został znaleziony, trzeba zaktualizować bibliotekę do wersji z poprawką, usunąć tymczasową łatkę albo przypięcie do forka i sprawdzić, że testy przechodzą na oficjalnym wydaniu. Pominięcie tego kroku kończy się łatką, która po miesiącach żyje obok poprawki w bibliotece i czasem nakłada zmianę drugi raz.
Jak sprawdzić wykonawcę po jego GitHubie
Jeśli wybierasz software house i chcesz zajrzeć w jego kod, poniższe punkty mówią więcej niż liczba repozytoriów czy gwiazdek na profilu.
- Historia commitów. Czy zmiany przychodzą regularnie i są opisane, czy repozytorium ma kilka commitów zrobionych tego samego dnia, tuż przed publikacją.
- Testy i automatyczne sprawdzenia. Czy repozytorium ma testy, czy są uruchamiane przy każdej zmianie i czy ostatnie uruchomienia przechodzą.
- Odpowiedzi na zgłoszenia. Jak autor rozmawia z osobami, które zgłaszają błędy: rzeczowo, z pytaniami o szczegóły, czy wcale.
- Kontrybucje do cudzych projektów. Profil na GitHubie pokazuje pull requesty w repozytoriach innych autorów. Zmiana przyjęta w znanej bibliotece przeszła review kogoś, kto nie miał powodu jej przepuścić.
- README i dokumentacja. Czy da się uruchomić projekt, czytając tylko opis, bez pytania autora.
- Daty. Czy projekty są utrzymywane, czy ostatnia zmiana była kilka lat temu.
Brak publicznego kodu nie dyskwalifikuje wykonawcy. Wiele dobrych zespołów pracuje wyłącznie na prywatnych repozytoriach klientów i ma w umowach zakaz publikacji. Wtedy zapytaj o dostęp do repozytorium i środowiska testowego podczas projektu. Wykonawca, który nie chce go dać nawet klientowi płacącemu za kod, ma zwykle ku temu powód, i rzadko jest to powód dobry dla klienta.
Kontrybucje do cudzych repozytoriów najłatwiej znaleźć wyszukiwarką GitHuba. Zapytanie is:pr is:merged author:NAZWA-UZYTKOWNIKA -user:NAZWA-UZYTKOWNIKA pokazuje przyjęte pull requesty tej osoby w repozytoriach, które do niej nie należą. Dla organizacji zamiast -user: używa się -org:NAZWA-ORGANIZACJI. Otwórz kilka z nich i przeczytaj dyskusję: widać, jak wykonawca reaguje na uwagi i czy poprawka była czymś więcej niż literówką w dokumentacji.
Liczbę gwiazdek traktuj z dystansem. Gwiazdka to jedno kliknięcie, można je zbierać akcjami promocyjnymi, a popularne repozytorium z listą linków ma ich więcej niż solidna biblioteka, której używa się w produkcji. Więcej mówi to, czy repozytorium ma zgłoszenia od ludzi spoza zespołu autora, bo zgłoszenia piszą ci, którzy naprawdę tego kodu używają.
Nasze projekty, liczby i aktywność są na stronie open source. Jak wygląda dostęp do repozytorium i stagingu w trakcie zlecenia, opisaliśmy na stronie jak pracujemy. Jeśli masz projekt, w którym przyda się ktoś, kto zna biblioteki od środka, napisz do nas. Odpowiadamy w godzinę.



