Yii dostarcza elastycznej oraz rozszerzalnej funkcjonalności logowania. Logowane komunikaty mogą być klasyfikowane w zależności od poziomu logu oraz kategorii komunikatu. Używając filtry kategorii oraz poziomów, wybrane komunikaty mogą zostać później przekierowane do różnych miejsc przeznaczenia, takich jak pliki, maile, okno przeglądarki, itp.
Komunikaty mogą być logowane poprzez wywołanie zarówno metody Yii::log jak i Yii::trace. Metody te różnią się tym, że druga loguje komunikat tylko wtedy, gdy aplikacja znajduje się w trybie debugowania.
Yii::log($message, $level, $category);
Yii::trace($message, $category);
Gdy logujemy komunikaty, musimy określić ich kategorię oraz poziom.
Kategoria jest ciągiem w formacie xxx.yyy.zzz
który przypomina
alias ścieżki. Na przykład, jeśli komunikat jest
logowany w kontrolerze CController, możemy użyć kategorii system.web.CController
.
Poziom komunikatu powinien przyjmować jedną z poniższych wartości:
trace
: jest to poziom używany przez metodę Yii::trace. Służy on do śledzenia
przebiegu przepływu wywołań w aplikacji podczas jej tworzenia.
info
: służy do logowania ogólnych informacji.
profile
: jest to profil wydajnościowy, który zostanie krótko opisany później.
warning
: dla komunikatów z ostrzeżeniami.
error
: dla komunikatów o błędach krytycznych.
Komunikaty rejestrowane przy użyciu metod Yii::log oraz Yii::trace trzymane są w pamięci. Zazwyczaj potrzebujemy wyświetlić je w oknie przeglądarki lub też zapisać je w pewnej trwałej pamięci danych takiej jak pliki czy też maile. Nazywamy to przekierowywaniem komunikatów (ang. message routing), np. wysyłanie komunikatów do różnych miejsc przeznaczenia. W Yii przekierowywanie komunikatów zarządzane jest przez komponent aplikacji CLogRouter. Zarządza on zestawem tak zwanych dzienników tras. Każdy dziennik trasy reprezentuje pojedyncze miejsce przeznaczenia dziennika. Komunikaty wysłane przez dziennik trasy mogą zostać przefiltrowane w zależności od swoich poziomów oraz kategorii.
Aby używać przekierowania komunikatów musimy zainstalować i inicjalnie załadować komponent aplikacji CLogRouter. Musimy również skonfigurować jego właściwość routes zawierająca pożądane przez nas dzienniki tras. Następujący kod pokazuje przykład pożądanej konfiguracji aplikacji:
array(
......
'preload'=>array('log'),
'components'=>array(
......
'log'=>array(
'class'=>'CLogRouter',
'routes'=>array(
array(
'class'=>'CFileLogRoute',
'levels'=>'trace, info',
'categories'=>'system.*',
),
array(
'class'=>'CEmailLogRoute',
'levels'=>'error, warning',
'emails'=>'admin@example.com',
),
),
),
),
)
W powyższym przykładzie mamy dwa dzienniki tras. Pierwsza trasa to klasa CFileLogRoute
która zapisuje komunikaty w pliku w katalogu uruchomieniowym aplikacji. Tylko komunikaty,
których poziom to trace
lub info
oraz te, których kategoria rozpoczyna się od ciągu system.
są zapisywane. Druga to klasa CEmailLogRoute, która wysyła komunikaty pod określony adres mailowy.
Wyłącznie komunikaty, których poziom to error
lub warning
są wysyłane.
Następujące dzienniki tras dostępne są w Yii:
Info: Przekierowanie komunikatów odbywa się na końcu aktualnego cyklu żądania kiedy przywoływane jest zdarzenie onEndRequest. Aby wyraźnie zakończyć przetwarzanie aktualnego żądania wywołaj metodę CApplication::end() zamiast używać funkcji
die()
lub teżexit()
, dlatego że CApplication::end() wywoła zdarzenie onEndRequest dzięki czemu komunikaty będą mogły zostać poprawnie zarejestrowane.
Jak już wspominaliśmy komunikaty mogą być filtrowane w zależności od ich poziomów oraz kategorii zanim zostaną wysłane do dziennika trasy. Dzieje się to poprzez ustawienie właściwości levels oraz categories odpowiedniego dziennika trasy. Większa ilość poziomów oraz kategorii powinna zostać rozdzielona przecinkami.
Ponieważ kategorie komunikatów posiadają format xxx.yyy.zzz
, możemy je traktować jak
hierarchię kategorii. W szczególności mówimy, że xxx
jest rodzicem xxx.yyy
, który jest
rodzicem xxx.yyy.zzz
. Możemy zatem użyć xxx.*
w celu reprezentowania kategorii xxx
oraz jej wszystkich kategorii potomnych i ich kategorii potomnych.
Możemy zadeklarować logowanie dodatkowych informacji zależnych
od kontekstu, takich jak predefiniowane zmienne PHP (np. $_GET
, $_SERVER
), ID sesji,
nazwa użytkownika, itp. Osiągamy to poprzez ustawienie odpowiedniego filtru logowania
we właściwości CLogRoute::filter trasy logowania.
Framework dostarcza wygodnego filtru CLogFilter, który może zostać użyty, w większości przypadków,
jako wymagany filtr logu. Domyślnie CLogFilter będzie logował komunikaty zawierające zmienne
takie jak $_GET
, $_SERVER
, które zazwyczaj posiadają cenne systemowe informacje kontekstowe.
CLogFilter może zostać skonfigurowany do dodawania prefiksu do każdego logowanego komunikatu
w postaci ID sesji, użytkownika, itp. co może bardzo uprościć globalne przeszukiwanie
podczas przeszukiwania ogromnej ilości zarejestrowanych komunikatów.
Nastepująca konfiguracja pokazuje jak udostępnić logowanie informacji kontekstowych. Zauważ, że każda trasa logowania może posiadać swój własny filtr logu. Domyślnie trasa logowania nie posiada zdefiniowanych żadnych filtrów.
array(
......
'preload'=>array('log'),
'components'=>array(
......
'log'=>array(
'class'=>'CLogRouter',
'routes'=>array(
array(
'class'=>'CFileLogRoute',
'levels'=>'error',
'filter'=>'CLogFilter',
),
...pozostałe trasy logowania...
),
),
),
)
Yii wspiera logowanie informacji ze stosu wywołani w komunikatach logowanych poprzez
wywołanie Yii::trace
. Domyślnie funkcjonalnośc ta jest wyłączona ze względu na zmniejszanie wydajności. Aby móc
używac tej funkcjonalności, po prostu zdefiniuj stałą nazwaną YII_TRACE_LEVEL
na początku skryptu wejściowego
(zanim załączysz yii.php
) jako wartość całkowita większa niż 0. Yii dołaczy wtedy do każdego śledzonego komunikatu
informację o nazwie pliku oraz numerze linii dla stosu wywołań należącego do danego fragmentu kodu aplikacji.
Liczba przypisana do YII_TRACE_LEVEL
określa ile wartstw każdego stosu wywołań powinno zostać zarejestrowanych.
Opcja ta jest szczególnie przydatna podczas fazy dewelopmentu, ponieważ może pomóc nam zidentyfikować miejsce, które
wywołuje śledzenie wiadomości.
Profilowanie wydajności jest specjalnym typem rejestrowania komunikatów. Profilowanie wydajności może być używane do mierzenia czasu potrzebnego do wykonania określonego bloku kodu oraz znalezienia wąskiego gardła wydajności.
Aby używać profilowania wydajności potrzebujemy określić, które bloki kodu powinny być profilowane. Zaznaczamy początek oraz koniec każdego bloku kodu poprzez wstawienie następujących metod:
Yii::beginProfile('blockID');
...blok kodu, który będzie profilowany...
Yii::endProfile('blockID');
gdzie blockID
jest identyfikatorem, który jednoznacznie określa blok kodu.
Zauważ, że bloki kodów muszą być prawidłowo zagnieżdżone. Oznacza to, że blok kodu nie może się krzyżować z innym blokiem. Musi on sie znajdować na równoległym poziomie lub całkowicie zawierać się w innym bloku kodu.
Aby zobaczyć wynik profilowania potrzebujemy zainstalować komponent aplikacji CLogRouter wraz z dziennikiem trasy CProfileLogRoute. Dokładnie tak samo jak to robimy podczas zwyczajnego przekierowywania komunikatów. Trasa CProfileLogRoute wyświetli wyniki mówiące o wydajności na końcu aktualnej strony.
Profilowanie jest szczególnie użyteczne podczas pracy z bazami danych, ponieważ wywołania SQL
są często główną przyczyną wąskich gardeł w wydajności aplikacji. Chociaż możemy wstawiać
wyrażenia beginProfile
oraz endProfile
w odpowiednich miejscach aby mierzyć czas spędzony na
wykonywaniu danego zapytania SQL, Yii dostarcza porządniejszego podejścia do rozwiązania tego problemu.
Poprzez ustawienie właściwości CDbConnection::enableProfiling na true w konfiguracji aplikacji, każde wyrażenie SQL, które zostanie wywołane będzie profilowane. Rezultat może zostać łatwo wyświetlony przy użyciu wyżej wspomnianej klasy CProfileLogRoute, która potrafi wyświetlić nam jak wiele czasu zostało spędzone na wykonywaniu danego zapytania SQL. Możemy również zawołać metodę CDbConnection::getStats() aby otrzymać całkowitą ilość wywołań zapytań SQL oraz ich całkowity czas wykonania.
Found a typo or you think this page needs improvement?
Edit it on github !
Signup or Login in order to comment.