Myślenie systemowe
Najprostsze rzeczy bywają najtrudniejsze w modelowaniu, powodem jest ich “pozorna” prostota. Na wielu uczelniach na świecie zaczęły sie pojawiać studia podyplomowe i szkolenia o wdzięcznym tytule “Myślenie systemowe” (System Thinking, np. to na MIT), ich celem jest kształtowanie myślenia zorientowanego na postrzeganie świata jako systemu czyli mechanizmu złożonego z współpracujących obiektów.
Tu pojawia się stosowane w nauce pojęcie “mechanizm” . Po co i kiedy używamy tego pojęcia? “Mechanizmów poszukuje się w celu wyjaśnienia, jak powstaje jakieś zjawisko lub jak działa jakiś istotny proces.” . Innymi słowy analizując lub projektując systemy, odpowiednio odkrywamy lub projektujemy mechanizmy ich działania. Ważna uwaga: system to nie tylko “system informatyczny”, systemem jest każde urządzenie, każda organizacja, każde państwo. To co nazywamy “systemem informatycznym”, bardzo rzadko jest samodzielnym systemem. Z reguły jest to część nadrzędnego systemu jakim jest urządzenie, organizacja, państwo.
Kluczowym etapem analizowania lub projektowania systemu jest zrozumienie i ustalenie, czym ten system jest oraz na co i jak reaguje.
Na dwóch przykładach pokażę czym jest Przypadek Użycia, który w notacji UML i SysML jest abstrakcją reakcji systemu na bodźce. Pokaże też czym jest projektowanie w duchu myślenia systemowego.
W specyfikacji UML czytamy:
Kluczowe elementy to:
- przypadek użycia może być przyporządkowany do wielu modelowanych systemów (subject: modelowany przedmiot), modeluje obserwowalny efekt wywołanej usługi (zachowanie się systemu w odpowiedzi na określony bodziec),
- przypadek użycia to określony zestaw zachowań systemu,
- przypadek użycia reprezentuje określone zachowania bez odwoływania się do wewnętrznej struktury systemu.
Dlatego te diagramy są (powinny być) proste (patrz art. Diagram Przypadków Użycia), w zasadzie jako nazwy, modelują przyszłe menu główne systemu. Diagram przypadków użycia to umowa na zakres. Diagram ten w notacji SysML pełni rolę modelu kontekstu projektu.
Coś małego i prostego czyli email
Od jednego z czytelników dostałem pytanie:
Mam jeszcze jedno pytanie do UC. Czy przypadkami użycia aplikacji poczty e-mail są wysyłanie wiadomości i odbieranie wiadomości?
odpisałem
Wysyłanie i odbieranie to skutek działania systemu email, UC to wyłącznie to co widzi użytkownik czyli formatka email, to to jaki adres jest w polu “Do:” skutkuje tym, gdzie email jest wysłany czy odebrany. Decyduje o tym “reguła biznesowa” (logika systemu):
– można wysłać mail gdziekolwiek (nawet do siebie)
– cudzy mail jest tylko do odczytu
odpowiedź lub przekazanie dalej to tylko logika danego kroku polegająca na ewentualnym skopiowaniu treści.
Półtora roku temu (maj 2021) w artykule Krótka historia pewnego wymagania opisywałem pewną specyfikację wymagań wykonaną tradycyjną opisową metodą, przez pracowników pewnego działu IT pewnej instytucji (tu sugestia by przeczytać ten artykuł). Problem polegał na tym, że ten opis był zbyt detaliczny i mimo to niejednoznaczny i niekompletny, a dotyczył jedynie poczty elektronicznej. Niestety okazuje się, że generalnie wymagania opisane w języku naturalnym, są niespójne i niejednoznaczne i nie jest to dobra metoda wykonania ich opisu .
Jako ludzie komunikujemy się, także pisemnie, narzędzia są wtórne. Narzędzia powstają w odpowiedzi na potrzeby a nie odwrotnie. Jak wygląda komunikacja, elektroniczna także? Poniższy schemat pokazuje prosty proces opracowania i wysłania treści:
Jak już nie raz tu wspominano, słownik pojęć jest fundamentem każdego projektu, a w projekcie z obszaru systemów informacyjnych szczególnie. Poniżej kluczowe pojęcia dla modelowanego obszaru:
dokument: materiał w postaci tekstu, fotografii lub jakikolwiek przedmiot, mający wartość dowodową lub informacyjną, lub plik komputerowy zawierający informacje zapisane w odpowiednim formacie
(źr.: https://sjp.pwn.pl)
formularz: blankiet dokumentu z miejscami do wypełnienia
komunikat: informacja przekazywana w procesie bezpośredniej komunikacji z drugą osobą
tekst: ciąg zapisanych słów i zdań składających się na pewną całość wyrażającą określone treści
Z powyższego wnioskujemy, że
- dokument jako tekst, wyraża określone treści, może być wypełnionym formularzem
- przesłany (przekazany) dokument to komunikat
Technologie informacyjne to automatyczne przetwarzanie treści. Jednak aby było to możliwe, treści te muszą być zwarte i ustrukturyzowane, a robimy to nadając dokumentom strukturę z pomocą formularzy (podział na sekcje, pola itp.). Prowadzone dość regularnie badania i studia literaturowe wskazują, że świat systemów informacyjnych od lat zmierza w stronę danych organizowanych w formularze (dokumenty) opisywane z pomocą ontologii (metadane) i odchodzi od ich rozkładania na sztywne i złożone tabelaryczne struktury pozbawione redundancji, czytane i zapisywane językiem SQL .
Dlatego na powyższym diagramie pojawiły się Szablon dokumentu i Formularz dokumentu. Szablon to wzór formatu (struktura) docelowego dokumentu, Dokument to określona treść o narzuconej przez ten szablon strukturze. Poniżej typowy szablon treści poczty elektronicznej:
Jest to prosta struktura, narzucająca wydzielenie (jawne wskazanie rodzaju treści): nadawcy, adresata, tematu, niestrukturalnego tekstu, pozwalająca opcjonalnie dodać innych adresatów i załączyć do przesłania inne dokumenty (pliki jako załączniki).
Tu bardzo istotna rzecz: zdefiniowany szablon to z zasady nazwa własna w słowniku, oznaczająca określnąa treść i jej strukturę. W efekcie procedura wysłania komunikatu ma postać:
- utwórz nowy Email wg. szablonu
- zredaguj treść
- wyślij naciskając OK
gdzie Email to nazwa szablonu. Z szablonem są powiązane reguły jego poprawnego wypełnienia, dlatego on sam zawsze stanowi sobą część procedury. Nie piszemy w scenariuszu: 1. wstaw adresata, 2. wstaw temat, 3. wpisz treść, 4. opcjonalnie dodaj załącznik……. Punkt scenariusza: “Zredaguj treść”, co do zasady oznacza wykonanie tego zgodnie z szablonem (i jest to – jako jeden formularz – z zasady zawsze jeden krok scenariusza). To dlatego definiowanie dokumentów (ich struktur i reguł poprawności) jest tak wygodne: szablon to nazwa własna struktury i treści danych i zarazem definicja kroku w scenariuszu (procedurze).
Diagram przypadków użycia dla takiego systemu komunikacji:
Dokumentując ten przypadek użycia tworzymy szablon formularza Email (oraz pomocniczy: Lista):
Przypadki użycia dokumentujemy między innymi z pomocą scenariuszy. Często stawiana jest teza, że przypadek użycia ma tylko jeden scenariusz, co nie jest prawdą. Tych scenariuszy może być kilka (w UML: Use Case jest rodzajem, który reprezentuje deklarację zestawu oferowanych zachowań ), wyrażane są jako jeden scenariusz zawierający alternatywne kroki lub jako alternatywne proste scenariusze, wspólną cechą tych scenariuszy jest operowanie na tych samych danych wg. tych samych reguł, różnią sie jedynie kontekstem .
Scenariusz: Nowa wiadomość:
- Użytkownik inicjuje usługę Wymiana treści
- SYSTEM wyświetla Lista wiadomości
- Użytkownik wskazuje opcje “nowa”
- SYSTEM wyświetla formularz Email
- Użytkownik wprowadza dane i OK
- SYSTEM potwierdza zachowanie i wysłanie treści
Scenariusz: Czytaj wiadomość:
- Użytkownik inicjuje usługę Wymiana treści
- SYSTEM wyświetla Lista wiadomości
- Użytkownik wskazuje określoną wiadomość
- SYSTEM wyświetla formularz Email z treścią wiadomości
Wysłanie odpowiedzi lub przekazanie wiadomości, to przejście do Nowej wiadomości, tu system skopiuje treść. Nie są to osobne scenariusze a raczej instrukcja użytkownika, wyrażona np. jako mapa “co ma klikać”:
Z perspektywy repozytorium wiadomości nie ma znaczenia która była wysłana, a która otrzymana, bo mają one identyczną strukturę, to co nazywamy “wysłane” i “otrzymane” zależy wyłącznie od tego czy nasz adres email jest w polu Do czy Od więc maile są “takie same”. W tym przypadku (technologicznie) repozytorium poczty (dokumentów/plików) to serwer IMAP (używając systemu z POP3 musimy mieć swoja lokalną kopię).
Tak więc bez względu na to czy wysyłamy email czy czytamy, jest to ta sama usługa. Sposób prezentacji (wątki, podział na foldery itp.) to jedynie detaliczny projekt interfejsu użytkownika. A spam? A własne lokalne archiwum? Nasze potrzeby realizuje magiczne słowo “architektura”:
Powyższy diagram to model architektury HLD (High Level Design, architektura wysokiego poziomu, więcej w artykule Analiza Biznesowa i Opis Techniczny). Portal to standardowe środowisko (widżety) dostępowe do usług aplikacji. Wymiana treści to komponent realizujący scenariusze pobierania i wysłania maili, organizujący logikę widoków: sortowanie, grupowanie w wątki, archiwizacja, itp.. Filtr antySPAM to z reguły wykorzystany gotowy komponent lub usługa. Email Adapter to komponent separujący naszą aplikacje od “świata”, uniezależnia aplikację (hermetyzuje ją) od detali konfiguracji zewnętrznych usług (IMAP i SMTP).
Szafa grająca czyli myślenie systemowe
Tak zwana Szafa Grająca to (pierwotnie) urządzenie odtwarzające muzykę z płyt winylowych zgromadzonych w specjalnym magazynku. Każda płyta (z reguły singiel) ma numer oraz podane dane dwóch utworów (dwie strony płyty). Wybór utworu polegał na wybraniu jego numeru, a odpowiedni mechanizm pobierał z magazynka płytę i zakładał ją na talerz gramofonu. Po jej odtworzeniu płyta wracała na swoje miejsce w magazynku.
Jeżeli szafa grająca była elementem wyposażenia np. pubu, system udostępniał wybór utworu dopiero po uiszczeniu opłaty: wrzuceniu odpowiedniej monety.
Po prawej stronie widok typowej szafy grającej, poniżej jej mechatroniczny model:
Powyższy diagram to model szafy grającej, diagram bloków wewnętrznych, wykonany w notacji SysML (rozszerzenie UML). Pełny model tej szafy zawierał by także diagram aktywności, diagram maszyny stanowej i diagram parametryczny (nie będę ich tu przytaczał). Celem jest tu pokazanie jej mechanicznej konstrukcji na poziomie głównych bloków. Tu chodziło o elementy wykonawcze, pełny model zawierał by jeszcze blok zasilania.
Jak już nie raz tu pisałem, w literaturze na temat inżynierii programowania autorzy często piszą, że “komputer to uniwersalny mechanizm” . Szafa grająca to konstrukcja elektromechaniczna, którą można w całości zastąpić komputerem (komputer to procesor, pamięć i program). Na jej przykładzie opracujemy jej komputerowy odpowiednik.
Generalnie szafa grająca realizuje dwie usługi:
Powyższe to “umowa na zakres systemu”. Kolejny etap to opis planowanej interakcji aktor-system. Usługę wyboru utworu można opisać scenariuszem:
- Użytkownik inicjuje usługę Wybór utworu
- SYSTEM udostępnia ‘Panel wyboru utworu’
- Użytkownik wprowadza numer wybranego utworu i OK
- SYSTEM potwierdza wybór
- SYSTEM odtwarza wybrany utwór
- SYSTEM wraca do stanu początkowego
Zakładam, że usługa przyjmowania opłaty “z góry” nie wymaga opisu. Stanowi ona osobną i niezależną usługę bo nie przypadkiem efekt wrzucenia monety nazywa się kredytem (z którego korzystamy wybierając utwory do odtworzenia) i nie ma obowiązku jego wykorzystania. Po prostu status szafy zmienia się: przyjmuje zamówienia na odtworzenia muzyki, wyczerpanie kredytu (który jako saldo żyje sobie w tej maszynie “własnym życiem”) spowoduje zmianą statusu na “nie przyjmuje zleceń odtworzenia muzyki”.
Jak już wiemy, mechanizm działania szafy grającej to wskazywanie utworu w określonej ich kolekcji i odtworzenie go z posiadanego nośnika. Do skonstruowania szafy grającej potrzebne jest: zgromadzenie pewnej ilości płyt z muzyką, zbudowanie konstrukcji zawierającej stojak/magazynek na płyty, urządzenie automatyzujące wybór płyty, jej odtworzenie i odłożenie na stojak.
Do napisania programu na komputer, który zastąpi mechaniczną konstrukcję, potrzebne jest jego zaprojektowanie. Albo, nie tyle potrzebne co zalecane. Dlaczego? Bo tworzenie (pisanie kodu) oprogramowania jest najdroższą pracą w inżynierii oprogramowania, podobnie jak wytwarzanie produktów na hali produkcyjnej. Po drugie cykl życia (serwis i rozwój, wprowadzanie zmian) systemu zależy od jego wewnętrznej architektury: szafa grająca mogła by być monolitycznym blokiem konstrukcyjnym, ale nie jest, i warto wiedzieć dlaczego. Nie jest bo urządzenie zbudowane z niezależnych i wymiennych bloków, mimo że ma bardziej skomplikowaną budowę, jest znacznie tańsze w utrzymaniu i rozwoju.
Pojawiło się pojęcie system, definiujemy jak poniżej:
System (z greckiego systema), jest to zestaw wzajemnie powiązanych ze sobą elementów, funkcjonujących jako jedna całość (nakłady, procesy transformacji, wyniki i sprzężenie zwrotne). Systemem jest wszelki skoordynowany wewnętrznie i wykazujący określoną strukturę układ elementów.
żr,: https://mfiles.pl/pl/index.php/System
(Dlatego systemem jest zarówno szafa grająca jak i publiczny lokal, którego jest ona elementem.)
Skoro więc nie chcemy monolitu, wiemy jak i dlaczego zbudowana jest mechaniczna szafa grająca, zaprojektujmy jej komputerowy odpowiednik:
Kluczowe cechy tej architektury:
- odseparowano od siebie i zahermetyzowano odpowiedzialności: za przyjęcie numeru utworu, za sprawdzenie prawa do jego odtworzenia, za repozytorium utworów, za kontrole wnoszonej opłaty, kolejkowanie itp.
- rozwój aplikacji wymaga co najwyżej dodawania kolejnych operacji/metod do już zbudowanych komponentów, można zawsze dodać operację lub nawet nowy komponent nie modyfikując istniejących.
Np. początkowo szafa będzie po prostu powiększała saldo w miarę wrzucanych monet bez względy na to kto je wrzuca. Wybór utworu pomniejszy saldo. Gdyby zaszła taka potrzeba dodajemy możliwość dodawania kolejnych np. numerowanych, obiektów klasy Saldo: modyfikujemy tylko logikę klasy Logika przyjmowania wpłat.
Logika wyboru utworu, korzystając z dostępu do aktualnego salda, kontroluje dodawanie utworów do kolejki. Dlaczego dublujemy utwory (np. pliki mp3) w kolejce do odtwarzania, zamiast budować tylko link do Utworów? Bo każdy z poziomych ciągów klas to osobny mikro-serwis i separujemy je, dzięki czemu są od siebie całkowicie niezależne. Wtedy np. w przyszłości, możemy zamienić parę Kontrola dostępu do Utworów i Utwory, na interfejs do zewnętrznego serwisu oferującego utwory, bez ingerowania w pozostałe komponenty.
Nie było tu moim celem detaliczne opisywanie powyższej konstrukcji a jedynie pokazanie jej. Jednak w razie jakichkolwiek pytań, proszę je zadawać w uwagach pod artykułem.
Podsumowanie
To co nazywamy myśleniem systemowym to tak zwane kompleksowe patrzenie na świat, który traktujemy jak system (patrz definicja wcześniej) oraz projektujemy rozwiązania (aplikacje) także jako systemy, wiedząc że one są częścią większego, nadrzędnego systemu. Pozwala to zapanować nad dowolnej wielkości projektem oraz zapewnić sobie, że jakakolwiek jego zmiana nie będzie pracą porównywalną, lub większą, niż jego pierwotne opracowanie i wykonanie .
Projektowanie w paradygmacie myślenia systemowego nie jest tym samym, czym projektowanie w paradygmacie myślenia projektowego. Wiele rozbieżnych poglądów dotyczy projektowania, istnieje jednak zgoda co do kilku podstawowych zasad, którymi kierują się ludzie myślący systemowo, planując przyszłość. […] ludzie myślący systemowo generalnie dążą do tego, by dziś zrobić coś, co pozwoli im jutro stworzyć system.
To co popularnie ostatnio nazywamy holistycznym podejściem do organizacji, to właśnie traktowanie ich jak systemów. Pozwala to tworzyć i rozwijać systemy w sposób płynny, ewolucyjny, bez potrzeby permanentnego “zamieniania starego na nowe”. Nawet pozornie prosty system wymiany komunikatów, warto przemyśleć i zaprojektować, a później dopiero tworzyć, bo to daje większe zrozumienie tego jak funkcjonuje i jaką role spełnia dla swojego otoczenia. Warto także naśladować “naturę”, która przez miliony lat ukształtowała na świat jako system…