dotenv

Dzisiaj poruszę temat stosunkowo prosty, ale bardzo ważny – chodzi o zarządzanie konfiguracją aplikacji internetowej. Jak wiadomo w 90% przypadków konfiguracja aplikacji (np. dane dostępowe do bazy) różnią się między środowiskiem produkcyjnym a developerskim jakie programista ma skonfigurowane na komputerze. Aby rozwiązać ten problem można napisać kilka linijek własnego kodu, który będzie odpowiadał za zarządzanie konfiguracją. Można także zaoszczędzić ten czas i użyć gotowego rozwiązania jakim jest phpdotenv, którego autorem jest Vance Lucas. Biblioteka ta jest portem rozwiązania PHP biblioteki dotenv napisanej w Ruby przez Brandona Keepersa. Spotkać ją można także we frameworku Laravel.

Cała idea działania biblioteki polega na umieszczeniu danych konfiguracyjnych w pliku .env, który będzie ładowany podczas uruchomienia aplikacji. Takie pliki nie powinny być commitowane do repozytorium ponieważ każda instancja naszej aplikacji powinna mieć swój własny plik .env.

Instalacja

Instalacji za pomocą Composera można dokonać następujący sposób:

Plik .env

Teraz możemy stworzyć plik .env dodać do niego interesujące nas zmienne. Każdy wpis w pliku powinien mieć następującą strukturę:

Dozwolone jest tworzenie w pliku komentarzy, ale należy je poprzedzić znakiem #. Możemy także wykorzystać zmienne, które zostały wcześniej zdefiniowane w pliku. Przykład poniżej:

Wykorzystanie w projekcie

Gdy plik mamy już przygotowany należy go załadować i aby to uczynić w zasadzie wystarczy jedna linijka kodu:

Napisałem „w zasadzie” ponieważ tak naprawdę należało by tą funkcję zamknąć w bloku try – catch.

Wracając jednak do samej funkcji – jako parametr podajemy katalog, w którym  przechowujemy plik .env. Jako drugi opcjonalny parametr możemy podać nazwę pliku, w którym przechowujemy konfigurację. Nie jesteśmy ograniczeni do plików z rozszerzeniem .env – równie dobrze możemy użyć env.ini lub inny.

Od teraz w tablicach superglobalnych $_ENV, $_SERVER są przechowywane zmienne, które zawarliśmy w pliku konfiguracyjnym (i nie tylko). Skoro zmienne dostępne są w/w tablicach to znaczy, że możemy je pobrać także za pomocą funkcji getenv().

Wymuszenie inicjalizacji/wartości określonych zmiennych

Biblioteka umożliwia także wymuszenie inicjalizacji określonych zmiennych w pliku konfiguracyjnym. Można tego dokonać w następujący sposób:

Lub używając tablicy:

Funkcja ta gdy stwierdzi, że w pliku konfiguracyjnym nie ma wymaganej zmiennej wyrzuci RuntimeExeption.

To nie wszystko na co ta funkcja pozwala –  za jej pomocą można także sprawdzić czy określona zmienna posiada dozwolone wartości. Przykład poniżej:

.env

.php

Można w ten sposób sprawdzić także kilka zmiennych (podając pierwszy parametr jako tablicę).

Trochę o wadach

Ze sprawdzaniem kilku zmiennych jednocześnie jest jeden problem. Chodzi o to, że funkcja traktuje drugi parametr jako wartości dozwolone dla wszystkich zmiennych podanych w pierwszym parametrze. Jeśli zdarzy się, że razem w tablicy znajdą się dwie zmienne i dla pierwszej zmiennej pewna wartość drugiej zmiennej jest niedozwolona to w takim przypadku nie zostanie wyrzucony wyjątek. Z tego też powodu lepiej sprawdzać wartości zmiennych pojedynczo.

Biblioteka ta ma też inny problem – wszystkie zmienne będą traktowane jako string. Nie ma znaczenia czy wpiszesz 45, false czy null. Jeszcze inny problem polega na tym, że Dotenv nie widzi wartości po znaku nowej linii w obrębie tej samej zmiennej.

Alternatywny praser plików .env

Na szczęście nie tylko pan Lucas stworzył bibliotekę, która parsuje pliki .env. Alternatywne rozwiązanie o podobnej nazwie (php-dotenv) zaprezentował Jose Diaz-Gonzalez. Biblioteka ta nie jest portem a autorskim rozwiązaniem.

Instalacja

Za pomocą Composera jest analogiczna jak w przypadku wcześniej omawianej biblioteki i wygląda następująco:

Różnice w konstrukcji pliku .env

Najważniejszą różnicą w porównaniu do biblioteki Lucasa jest to, że gdy jakiemuś kluczowi nadamy wartość null, false, true lub jakąś liczbę całkowitą to zostaną one zinterpretowane jako NULL, wartości typu boolean i integera. Ważne jest jednak to aby nie zapisywać tych wartości w „dużej” wersji (NULL, FALSE / TRUE) i nie zamykać ich w cudzysłowach, ponieważ wtedy zostaną zinterpretowane jako stringi. W tym rzutowaniu jednak brak konsekwencji, ponieważ jeśli kluczowi nadamy wartość typu float bez cudzysłowów to zostanie ona zinterpretowana jako string.

Kolejną różnicą jest możliwość stosowania znaku nowej linii a co za tym idzie „łamania” dłuższych stringów. Aby tego dokonać wystarczy w wybranym przez nas miejscu wstawić znak \n i zamknąć cały string w cudzysłowach.

Trochę inaczej wygląda także wykorzystywanie zdefiniowanych wcześniej kluczy w innych kluczach:

Wykorzystanie w projekcie

Aby odczytać plik .env wystarczy następująca linijka kodu:

 Należy ją zamknąć rzecz jasna w sekcji try – catch ponieważ w przypadku błędów (np. nie odnalezienia pliku) zwraca wyjątki.

Gdy plik zostanie poprawnie załadowany i sparsowany zmienne zostaną dodane jako stałe (decyduje o tym ostania wywołana metoda define()). To jednak nie jedyna możliwość. Możemy wrzucić nasze zmienne do tablicy $_ENV i $_SERVER. Aby tego dokonać zamiast define() należy użyć metody doEnv() lub toServer(). Obie wcześniej wymienione metody  przyjmują drugi opcjonalny parametr, którego ustawienie na TRUE zezwala metodzie na nadpisywanie elementów tablicy już wcześniej zdefiniowanych w przeciwnym przypadku zostanie wyrzucony wyjątek.

To nie jedyne postaci w jakich możemy otrzymać dane z pliku .env – możemy także dostać je w postaci tablicy asocjacyjnej (metoda toArray()) lub w postaci JSONa rzutując na string obiekt zwrócony przez metodę parse(). Przykład poniżej:

Istnieje jeszcze jedna (i chyba najlepsza) możliwość załadowania danych z pliku – metoda statyczna load. Jako parametr przyjmuje tablice asocjacyjną, w której podajemy odpowiednie opcje. I tak w kluczu filepath podajemy adres pliku .env. Klucze to Env, toServer, define odpowiadają za funkcję o tej samej nazwie. Jeśli klucz będzie miał wartość TRUE wtedy funkcja dla tego pliku zostanie wykonana. Klucz expect odpowiednia za funkcję o tej samej nazwie, ale  zamiast TURE lub FALSE podajemy tablicę z nazwami zmiennych jakich oczekujemy (opis samej funkcji w dalszej części tekstu).

Wymuszenie inicjalizacji określonych zmiennych

Podobnie jak w przypadku wcześniej omawianej biblioteki i w tym przypadku możemy wymusić inicjalizację konkretnych zmiennych. Przykład poniżej:

W przypadku gdy któraś ze zmiennych nie będzie zainicjalizowana, zostanie wyrzucony wyjątek.

Włączenie wyrzucania wyjątków

Można wyłączyć wyrzucanie wyjątków (we wszystkich wcześniej opisanych przypadkach) wywołując przed metodą parse() metodę raiseExceptions() z parametrem FALSE. Przykład poniżej:

Prefiksy zmiennych

Warto wspomnieć o tym, że do zmiennych można dodawać prefiksy aby uniknąć kolizji nazw. Dodanie prefiksów jest bardzo proste i sprowadza się do wywołania metody prefix. Przykład poniżej:

Co mi w tej bibliotece nie pasuje…

Nie pasuje mi przede wszystkim to, że nie można sprawdzić czy klucz ma dozwolone wartości tak jak w bibliotece Lucasa. Trochę dziwna jest także niekonsekwencja w rzutowaniu zmiennych opisana wcześniej.

Na zakończenie…

… napiszę, że zdecydowanie bardziej podeszła mi biblioteka pana Gonzaleza ze względu na znacznie więcej możliwości, a w ostatecznym rozrachunku braki, które opisałem nie są zbyt dotkliwe. Zachęcam jednak do wypróbowania obu bibliotek – Wasze wnioski mogą być zupełnie inne niż moje.

Posty które mogą Cię zainteresować:

Dodaj komentarz

Your email address will not be published. Please enter your name, email and a comment.