Baza wiedzy
Wirtualizacja, chmura, konteneryzacja czy podejście typu Software Defined Everything stają się nieodłącznym elementem współczesnego IT. Posiadanie infrastruktury w postaci wirtualnej ułatwia życie. Tworzenie nowych serwerów, korzystanie z kopii zapasowych, instalacja aplikacji na maszynach wirtualnych czy wirtualizacja sieci i urządzeń sieciowych bardzo ułatwiają życie.
Niejednokrotnie, znacznie szybsze i wygodniejsze jest postawienie serwera od początku, niż próba naprawy czy aktualizacji istniejącego. Zwłaszcza, jeżeli wykorzystujemy chmurę. Niestety często tak się nie dzieje.
W tradycyjnym podejściu do IT, systemy są na stałe związane z hardware’em. Dostarczanie i utrzymywanie infrastruktury wymaga dużej ilości pracy i czasu. Jakiekolwiek zmiany wymagają wcześniej długiego przygotowania, bo ich odwrócenie nie zawsze jest lekkie, łatwe i przyjemne.
Obecnie, w erze wirtualizacji, zmiany związany z infrastrukturą mogą być wykonywane znacznie prościej i szybciej. Z wykorzystaniem nowoczesnych narzędzi i platform, konfiguracja, dostarczenie i utrzymanie usług zajmuje znacznie mniej czasu niż wcześniej. Jednak spójność i efektywność takiego postępowania trzeba w odpowiedni sposób wypracować, ponieważ nie pojawia się ona automatycznie wraz z wprowadzeniem wirtualizacji.
Oczywiście, większość organizacji posiada odpowiednie procesy i procedury odpowiadające za dostarczanie infrastruktury, ale często wywodzą się one z czasów gdy uruchomienie nowego serwera wymagało napisania wniosku, przyznania zasobów, a następnie pracy zespołu IT odpowiedzialnego za uruchomienie maszyny wirtualnej, konfiguracji sieci, czy konfiguracji reguł na firewallu. Większość z nas wie ile czasu to zajmuje, a nikt nie chce czekać.
Kwestią czasu są więc próby obejścia systemu, które prowadzą do bałaganu. Nie wykorzystujemy więc potencjału wirtualizacji i pomimo posiadanych możliwości, nasza infrastruktura wciąż jest bardziej statyczna, niż dynamiczna.
Obawy przed uczynieniem jej bardziej dynamiczną są spowodowane kilkoma czynnikami. Przede wszystkim jest to brak dbałości o istniejące systemy. Łatwość z jaką możemy powoływać nowe maszyny wirtualne, czy to w chmurze, czy to w lokalnym data center, powoduje, że często mamy ich dziesiątki czy setki, a ich ilość rośnie szybciej niż nasze zdolności zarządzania nimi. Nawet jeżeli początkowo systemy są uruchamiane w ten sam sposób, z tego samego obrazu, to z biegiem czasu rosną różnice między nimi. Na przykład serwer www na jednym z nich wymagał specyficznej poprawki. Została ona wprowadzona, ale tylko na nim, przez co różni się on teraz od innych serwerów www. Kolejny przykład. Jeden z serwerów był zbyt mocno obciążony, więc administratorzy dokonali tuningu konfiguracji. Znowu tylko na jednym serwerze. Nie mówiąc już o tym, że każdy z tych serwerów mógł być instalowany i konfigurowany przez innego administratora i każdy z nich może mieć minimalnie różną konfigurację.
W efekcie możemy mieć dziesiątki systemów z różną wersją poprawek, różnymi wersjami oprogramowania i różnymi konfiguracjami tej samej usługi. Dzięki temu coś co działa na jednym systemie, nie działa na drugim, teoretycznie nawet takim samym. Ostatecznie zawsze prowadzi to do powstania systemu, którego nikt nie zna, nikt nie potrafi się do niego zalogować, ale nikt go nie dotyka, bo kiedyś został wyłączony i przestała działać krytyczna usługa.
Takie maszyny wirtualne są traktowane jak systemy starej daty i raz uruchomiony serwer jest utrzymywany latami. Ponieważ aplikacja, która jest na nim uruchomiona jest krytyczna. Ze strachu przed jej unieruchomieniem zaprzestaje się nawet instalowania krytycznych poprawek bezpieczeństwa (zakładając, że jednak jest w firmie ktoś, kto wie jak się do niej zalogować). Niby są snapshoty, ale jeżeli coś pójdzie nie tak, to przywrócenie systemu daje nam tylko tyle, że mamy działający system, na którym i tak nie wprowadzimy żadnej poprawki, ponieważ teraz już wiemy, że na pewno spowoduje to awarię.
Prowadzi to do sytuacji, w której teoretycznie mamy dynamiczne środowisko, teoretycznie możemy automatycznie usuwać i powoływać różne jego elementy, ale w praktyce jakiekolwiek próby automatyzacji czy oskryptowania zawodzą. Owszem, stosujemy skrypty, ułatwiamy sobie pracę, ale w praktyce każdy taki skrypt przed uruchomieniem jest przystosowywany do bieżących potrzeb. Nie stosujemy pełnej automatyzacji bo nasza infrastruktura nie jest spójna, a nie jest spójna bo nie stosujemy automatyzacji.
W jaki sposób możemy przerwać to błędne koło? Tylko stając oko w oko ze strachem i automatyzując systemy jeden po drugim.
Infrastruktura jako kod
Naprzeciw naszym potrzebom automatyzacji środowisk wirtualnych wychodzi model Infrastructure as Code, czyli po prostu infrastruktura jako kod. Polega on na traktowaniu infrastruktury IT tak jakby była oprogramowaniem. Dzięki temu możemy ją wersjonować, a nawet wprowadzać takie praktyki jak test-driven development, continuous integration czy continuous delivery. Traktowanie infrastruktury jak kodu prowadzi do wielu korzyści:
- infrastruktura IT przestaje być przeszkodą we wprowadzanych zmianach,
- zmiany w infrastrukturze zaczynają być rutynowe, nie wymagają wielu godzin stresującego planowania,
- użytkownicy mogą sami zdefiniować, przydzielić i zarządzać zasobami które potrzebują, odciążając w ten sposób dział IT,
- wysiłki mające na celu zapobieganie awariom tracą na znaczeniu, ponieważ środowisko może być szybko odtworzone w przypadku awarii,
- usprawnienia są wprowadzane w stylu ciągłym, a nie projektowym,
- wszelkie zmiany czy rozwiązania problemów mogą być przetestowane na żywym środowisku.
Oczywiście, utrzymanie infrastruktury jako kodu, kieruje się pewnymi założeniami i zasadami.
Przede wszystkim, systemy utrzymywane w ten sposób muszą być reprodukowane w prosty sposób i bez zbędnego wysiłku. Nie ma tu miejsca na podejmowanie decyzji o nazwie hosta czy wersji oprogramowania. Wszystko to musi być zapisane w kodzie, żeby środowisko mogło być uruchomione szybko i bez obaw. Działa to również w drugą stronę, czyli dynamicznie uruchomione systemy muszą mieć możliwość szybkiego usunięcia, zastąpienia, przeniesienia czy przeskalowania bez wpływu na resztę infrastruktury. System musi być odporny na awarie i nie powinien odczuć zniknięcia jednego czy kilku serwerów, a my musimy nauczyć się życia ze świadomością, że nasza infrastruktura nie jest niczym stałym.
Z kolei serwery muszą być ze sobą spójne. Dwa dowolne elementy infrastruktury, świadczące podobną usługę, powinny być identyczne poza elementami konfiguracji takimi jak adres IP. Jeżeli potrzebujemy zwiększyć pamięć w serwerze to mamy dwa wyjścia: albo zmieniamy definicję, tak żeby wszystkie maszyny tej klasy miały zwiększoną pamięć, albo definiujemy nową klasę serwerów ze zwiększoną pamięcią. Zapewni to spójność pomiędzy elementami infrastruktury i powtarzalność przy tworzeniu nowych.
Powtarzalność, która jest kolejną ważną zasadą przy automatycznym tworzeniu infrastruktury. Ponieważ każdy element musi być spójny i powtarzalny, wszystkie czynności, które są na nim wykonywane muszą być spójne i powtarzalne. Sytuacja, w które jeden administrator przydzieli na pliki tymczasowe 50GB przestrzeni dyskowej, a drugi tworząc serwer tej samej klasy, na te same pliki przydzieli 100GB, jest niedopuszczalna. Z tego powodu, wszelkie powtarzalne czynności muszą być oskryptowane. Jeżeli jest to niemożliwe, być może istnieje inna metoda ich wykonania.
Poza skryptami, nieodzowną częścią infrastruktury w postaci kodu są pliki z definicjami elementów. W zależności od używanego narzędzia, mogą mieć one różną nazwę, ale sprowadzają się do tego samego, czyli do opisania infrastruktury w postaci pliku konfiguracyjnego. W przypadku serwera może on zawierać między innymi:
- typ i rola serwera,
- używany obraz systemu operacyjnego,
- segment sieci,
- porty na których słuchają usługi.
Takie podejście pozwala na wersjonowanie infrastruktury, wycofywanie zmian konfiguracji, porównywanie wersji czy śledzenie zmian. Ponieważ wszystkie zmiany są przechowywane w systemie kontroli wersji, każdy z administratorów widzi kiedy zmiany są przesyłane do systemu i ma świadomość zaistnienia. Dodatkowo, system śledzenia wersji może wywołać określone akcje kiedy zmiany są zatwierdzone.
Co można z tym zrobić?
Po tym przydługim wprowadzeniu nasuwa się pytanie, jak można praktycznie wykorzystać model Infrastructure as Code? Pozwolisz, że posłużę się przykładem.
Wyobraź sobie, że masz farmę serwerów WWW na których musisz np. zwiększyć ilość jednocześnie pracujących procesów Apache i zwiększyć pamięć RAM dla tychże serwerów. Oczywiście cała infrastruktura jest opisana w postaci kodu, więc to co musisz zmienić to plik konfiguracyjny dla Apache oraz definicję dla serwerów www, które będą od teraz miały więcej pamięci. Po zatwierdzeniu zmian w systemie kontroli wersji, proces wywoła stworzenie testowych serwerów i wykona skrypty, które przetestują wprowadzone zmiany.
Jeżeli wszystko będzie w porządku, pracujące do tej pory serwery będą niszczone, a na ich miejsce będą uruchamiane nowe, ze zmienionymi parametrami. Ponieważ żadne pliki nie są przechowywane lokalnie, nie wpłynie to na działanie hostowanej aplikacji. Kod aplikacji zostanie pobrany z systemu kontroli wersji i uruchomiony lokalnie na serwerach.
Operacja taka może być przeprowadzona w ciągu dnia roboczego, ponieważ prawidłowo przygotowany proces spowoduje, że klienci nie zauważą, że coś się zmieniło. Przyznasz, że taka perspektywa przeprowadzania zmian w infrastrukturze jest całkiem obiecująca?
Deployment nowej wersji aplikacji również staje się dzięki temu łatwy i bezpieczny. Po prostu uruchamiamy aplikację na nowych instancjach (oczywiście takich samych jak te już pracujące, bo powołanych z tego samego pliku z definicją), testujemy i jeżeli wszystko działa uruchamiamy nowe serwery z nowym kodem w puli serwerów aplikacyjnych i wyłączamy stare serwery.
Ostatnie słowo
Nie chciałem, żeby artykuł był zbyt długi, dlatego świadomie nie wspomniałem o narzędziach do definiowania elementów, sposobach przygotowywania szablonów obrazów systemu operacyjnego dla serwerów czy wreszcie o sposobach wymuszania konfiguracji na uruchamianych serwerach. Tematy te pojawią się w kolejnym artykule na ten temat, a tymczasem to tyle jeżeli chodzi o zgrubne pokazanie możliwości, jakie daje nam uruchamianie infrastruktury jako kodu. Odpowiednio zastosowane zdecydowanie przyspiesza i ułatwia pracę, wymaga jednak od nas pewnego przystosowania i zmiany nastawienia. Nie tylko nasza infrastruktura musi być dynamiczna, ale także procesy obowiązujące w naszej organizacji. Jeżeli powołanie nowej instancji serwera każdorazowo wymaga założenia zgłoszenia serwisowego, jego akceptacji, ręcznego stworzenia i konfiguracji instancji, a w końcu ręcznej konfiguracji sieci i firewalla, to to nie zadziała. Rozpoczęcie korzystania z chmury publicznej ułatwia i przyspiesza zmianę tych procesów, aczkolwiek nie oznacza, że z dobrodziejstwa infrastruktury w postaci kodu nie możemy skorzystać na przykład w środowisku VMWare. Oczywiście możemy, jednak może to od nas wymagać większej ilości pracy u podstaw.
Zainteresował Cię ten wpis?
Chcesz dowiedzieć się więcej?
Paweł Piotrowski
Od ponad 14 lat zajmuje się projektowaniem, budową i zarządzaniem sieciami teleinformatycznymi oraz bezpieczeństwem IT. Swoje doświadczenie zdobywał w polskich i międzynarodowych projektach. Certyfikowany inżynier Cisco, Vmware, AWS Solution Architect.
Pawel.Piotrowski(at)monolit-it.pl
Zobacz wszystkie artykuły danego autora »