JavaRush /Blog Java /Random-PL /Dlaczego rejestrowanie jest potrzebne?

Dlaczego rejestrowanie jest potrzebne?

Opublikowano w grupie Random-PL
Cześć! Pisząc wykłady, szczególnie zwracam uwagę, czy dany temat na pewno będzie wykorzystany w prawdziwej pracy. Dlaczego potrzebujesz logowania - 1 Zatem UWAGA! Temat, który dzisiaj poruszymy, na pewno przyda Ci się przy wszystkich Twoich projektach już od pierwszego dnia pracy. Porozmawiamy o logowaniu. Temat ten wcale nie jest trudny (powiedziałbym nawet, że łatwy). Ale w pierwszej pracy stresu będzie już wystarczająco dużo, żeby uporać się z oczywistymi sprawami, więc lepiej to już teraz dokładnie uporządkować :) Zatem zaczynajmy. Co to jest rejestrowanie? Logowanie to zapisywanie gdzieś danych o działaniu programu. Miejsce, w którym zapisywane są te dane, nazywane jest „ dziennikiem ”. Od razu pojawiają się dwa pytania: gdzie i jakie dane są rejestrowane? Zacznijmy od „gdzie”. Dane dotyczące działania programu można zapisywać w wielu różnych miejscach. Na przykład podczas studiów często wysyłasz dane do konsoli za pomocą plików System.out.println(). To jest prawdziwe rejestrowanie, choć najprostsze. Oczywiście nie jest to zbyt wygodne dla klienta lub zespołu wsparcia produktu: oczywiście nie będą chcieli instalować IDE i monitorować konsoli :) Istnieje również bardziej znany format zapisywania informacji - w pliku tekstowym. Ludziom jest o wiele łatwiej je czytać w ten sposób, a na pewno znacznie łatwiej je przechowywać! Teraz drugie pytanie: jakie dane o działaniu programu należy zapisywać w logu? Ale tutaj wszystko zależy od Ciebie! System rejestrowania Java jest bardzo elastyczny. Możesz skonfigurować go w taki sposób, aby cały postęp Twojego programu był rejestrowany. Z jednej strony to dobrze. Ale z drugiej strony wyobraź sobie, jaki rozmiar mogą osiągnąć logi Facebooka lub Twittera, jeśli wszystko jest tam zapisane. Tak duże firmy prawdopodobnie mają możliwość przechowywania nawet takiej ilości informacji. Ale wyobraź sobie, jak trudno będzie wyszukać informacje o jednym krytycznym błędzie w logach o objętości 500 gigabajtów tekstu? To nawet gorsze niż igła w stogu siana. Dlatego logowanie w Javie można skonfigurować tak, aby w dzienniku (dzienniku) zapisywane były wyłącznie dane o błędach. A nawet o błędach krytycznych! Chociaż stwierdzenie „logowanie w Javie” nie jest do końca poprawne. Faktem jest, że potrzeba logowania pojawiła się wśród programistów, zanim ta funkcjonalność została dodana do języka. Zanim Java miała własną bibliotekę rejestrowania, wszyscy korzystali już z biblioteki log4j. Historia pojawienia się logowania w Javie jest właściwie bardzo długa i pouczająca, w wolnej chwili możesz przeczytać ten post na Habré . Krótko mówiąc, Java ma swoją własną bibliotekę logującą, ale prawie nikt jej nie używa :) Później, gdy pojawiło się kilka różnych bibliotek logujących i wszyscy programiści zaczęli używać różnych, pojawił się problem z kompatybilnością. Aby uniemożliwić ludziom robienie tego samego przy użyciu kilkunastu różnych bibliotek z różnymi interfejsami, stworzono framework abstrakcji slf4j(„Fasada rejestrowania usług dla języka Java”). Nazywa się to abstrakcją, ponieważ chociaż używasz klas slf4j i wywołujesz ich metody, pod maską działają wszystkie poprzednie frameworki rejestrujące: log4j, standardowe java.util.logging i inne. Jeśli obecnie potrzebujesz jakiejś specyficznej funkcji log4j, której nie mają inne biblioteki, ale nie chcesz ściśle łączyć projektu z tą konkretną biblioteką, po prostu użyj slf4j. I już „wyciągnie” metody log4j. Jeśli zmienisz zdanie i zdecydujesz, że nie potrzebujesz już funkcji log4j, wystarczy ponownie skonfigurować „wrapper” (czyli slf4j), aby korzystać z innej biblioteki. Twój kod nie przestanie działać, ponieważ wywołujesz w nim metody slf4j, a nie konkretnej biblioteki. Mała dygresja. Aby poniższe przykłady zadziałały, musisz pobrać bibliotekę slf4j stąd i bibliotekę log4j stąd . Następnie musimy rozpakować archiwum i dodać potrzebne pliki jar do ścieżki klas za pośrednictwem Intellij IDEA. Pozycje menu: Plik -> Struktura projektu -> Biblioteki Wybierz potrzebne słoiki i dodaj je do projektu (w archiwach, które pobraliśmy, jest wiele słoików, spójrz na te, których potrzebujesz na zdjęciach) Dlaczego potrzebujesz logowania - 2Dlaczego potrzebujesz logowania - 3Uwaga - ta instrukcja jest dla tych studenci, którzy nie wiedzą, jak korzystać z Mavena. Jeśli wiesz, jak z niego korzystać, lepiej spróbować od niego zacząć: zwykle jest to znacznie łatwiejsze.Jeśli używasz Mavena , dodaj tę zależność:
<dependency>
            <groupId>org.apache.logging.log4j</groupId>
            <artifactId>log4j-slf4j-impl</artifactId>
            <version>2.14.0</version>
</dependency>
Świetnie, uporządkowaliśmy ustawienia :) Przyjrzyjmy się, jak działa slf4j. Jak możemy się upewnić, że postęp programu jest gdzieś rejestrowany? Do tego potrzebujemy dwóch rzeczy – rejestratora i programu dołączającego . Zacznijmy od pierwszego. Rejestrator jest obiektem kompleksowo zarządzającym prowadzeniem ewidencji . Utworzenie rejestratora jest bardzo proste: odbywa się to metodą statyczną - LoggerFactory.getLogger(). Jako parametr metody należy przekazać klasę, której praca będzie rejestrowana. Uruchommy nasz kod:
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class MyTestClass {

   public static final Logger LOGGER = LoggerFactory.getLogger(MyTestClass.class);

   public static void main(String[] args) {

       LOGGER.info("Test log record!!!");
       LOGGER.error("В программе возникла ошибка!");
   }
}
Dane wyjściowe konsoli: BŁĄD StatusLogger Nie znaleziono pliku konfiguracyjnego Log4j 2. Używanie konfiguracji domyślnej (rejestrowanie tylko błędów w konsoli) lub konfiguracji dostarczonych programowo przez użytkownika. Ustaw właściwość systemową „log4j2.debug”, aby wyświetlała wewnętrzne rejestrowanie inicjalizacji Log4j 2. Zobacz https://logging.apache.org/log4j/2.x/manual/configuration.html, aby uzyskać instrukcje dotyczące konfigurowania Log4j 2 15:49:08.907 [main] BŁĄD MyTestClass - Wystąpił błąd w programie! Co tu widzimy? Najpierw widzimy komunikat o błędzie. Pojawiło się, ponieważ obecnie brakuje nam niezbędnych ustawień. Dlatego nasz rejestrator może teraz wysyłać tylko komunikaty o błędach (ERROR) i tylko do konsoli. Metoda logger.info()nie została wykonana. Ale logger.error()zadziałało! Konsola wyświetla aktualną datę, sposób w jaki wystąpił błąd ( main), słowo BŁĄD i nasz komunikat! BŁĄD jest poziomem rejestrowania. Ogólnie rzecz biorąc, jeśli wpis w dzienniku jest oznaczony słowem BŁĄD, oznacza to, że w tym miejscu programu wystąpił błąd. Jeśli wpis jest oznaczony słowem INFO, oznacza to, że jest to po prostu aktualna informacja dotycząca normalnej pracy programu. Biblioteka SLF4J oferuje kilka różnych poziomów rejestrowania, które umożliwiają elastyczną konfigurację rejestrowania. Są bardzo łatwe w zarządzaniu: cała niezbędna logika jest już zawarta w klasie Logger. Wystarczy wywołać niezbędne metody. Jeśli chcesz wysłać zwykłą wiadomość, zadzwoń pod numer logger.info(). Komunikat o błędzie - logger.error(). Wyświetl ostrzeżenie — logger.warn() teraz porozmawiajmy o programie dołączającym . Dodatek to miejsce, do którego trafiają Twoje dane. Można powiedzieć, że przeciwieństwem źródła danych jest „punkt B”. Domyślnie dane są wysyłane do konsoli. Należy pamiętać, że w poprzednim przykładzie nie musieliśmy niczego konfigurować: tekst pojawił się w samej konsoli, ale rejestrator z biblioteki log4j może wysyłać do konsoli jedynie komunikaty na poziomie ERROR. Oczywiście wygodniej jest czytać logi z pliku tekstowego i przechowywać logi w tych samych plikach. Aby zmienić domyślne zachowanie rejestratora, musimy skonfigurować nasz program dołączający pliki . Na początek musisz utworzyć plik log4j.xml bezpośrednio w folderze src lub w folderze zasobów, jeśli używasz Mavena, lub w folderze zasobów, jeśli używasz Mavena. Format xml już znasz, niedawno mieliśmy o nim wykład :) Oto jaka będzie jego treść:
<?xml version="1.0" encoding="UTF-8"?>
<Configuration status="INFO">
   <Appenders>
       <File name="MyFileAppender" fileName="C:\Users\Username\Desktop\testlog.txt" immediateFlush="false" append="false">
           <PatternLayout pattern="%d{yyy-MM-dd HH:mm:ss.SSS} [%t] %-5level %logger{36} - %msg%n"/>
       </File>
   </Appenders>
   <Loggers>
       <Root level="INFO">
           <AppenderRef ref="MyFileAppender"/>
       </Root>
   </Loggers>
</Configuration>
Nie wygląda to na szczególnie skomplikowane :) Ale mimo to przyjrzyjmy się zawartości.
<Configuration status="INFO">
Jest to tak zwany rejestrator stanu. Nie jest on powiązany z naszym rejestratorem i jest używany wewnętrznie przez log4j. Możesz ustawić status=”TRACE” zamiast status=”INFO”, a wszystkie informacje o wewnętrznym działaniu log4j zostaną wyprowadzone na konsolę (status-logger wysyła dane do konsoli, nawet jeśli naszym appenderem dla programu jest plik -na podstawie). Nie potrzebujemy tego teraz, więc zostawimy wszystko tak, jak jest.
<Appenders>
   <File name="MyFileAppender" fileName="C:\Users\Евгений\Desktop\testlog.txt" append="true">
       <PatternLayout pattern="%d{yyy-MM-dd HH:mm:ss.SSS} [%t] %-5level %logger{36} - %msg%n"/>
   </File>
</Appenders>
Tutaj tworzymy nasz appender. Znacznik <File>wskazuje, że będzie to plik. name="MyFileAppender"- imię naszego appendera. fileName="C:\Users\Username\Desktop\testlog.txt"— ścieżka do pliku dziennika, w którym będą zapisywane wszystkie dane. append="true"— czy konieczne jest dopisanie dodatkowych danych na końcu pliku. W naszym przypadku tak właśnie będzie. Jeśli ustawione na false , stara zawartość dziennika zostanie usunięta przy każdym ponownym uruchomieniu programu. <PatternLayout pattern="%d{yyy-MM-dd HH:mm:ss.SSS} [%t] %-5level %logger{36} - %msg%n"/>- To są ustawienia formatowania. Tutaj możemy użyć wyrażeń regularnych, aby dostosować format tekstu w naszym dzienniku.
<Loggers>
       <Root level="INFO">
           <AppenderRef ref="MyFileAppender"/>
       </Root>
</Loggers>
Tutaj określamy poziom logowania (poziom root). Mamy ustawiony poziom INFO: czyli wszystkie wiadomości na poziomach wyższych niż INFO (zgodnie z tabelą, którą przeglądaliśmy powyżej) nie będą uwzględniane w logu. W naszym programie będziemy mieli 3 komunikaty: jeden INFO, jeden WARN i jeden ERROR. Przy bieżącej konfiguracji wszystkie 3 komunikaty zostaną zapisane w logu. Jeśli zmienisz poziom główny na ERROR, zarejestrowany zostanie tylko ostatni komunikat z LOGGER.error(). Dodatkowo w tym miejscu znajduje się link do załącznika. Aby utworzyć taki link należy wewnątrz tagu <Root>utworzyć tag <ApprenderRef>i dodać do niego parametr ref=”Nazwa твоего аппендера”. Stworzyliśmy tutaj nazwę appendera, na wypadek gdybyś zapomniał: <File name="MyFileAppender" A oto kod naszego programu!
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class MyTestClass {

   public static final Logger LOGGER = LoggerFactory.getLogger(MyTestClass.class);

   public static void main(String[] args) {

       LOGGER.info("Начало работы программы!!!");

       try {
           LOGGER.warn("Внимание! Программа пытается разделить одно число на другое");
           System.out.println(12/0);
       } catch (ArithmeticException x) {

           LOGGER.error("Ошибка! Произошло деление на ноль!");
       }
   }
}
Oczywiście jest to trochę pokrętne (złapanie RuntimeException to przeciętny pomysł), ale do naszych celów jest idealne :) Uruchommy naszą metodę main()4 razy z rzędu i spójrzmy na nasz plik testlog.txt. Nie ma potrzeby tworzenia go wcześniej: biblioteka zrobi to automatycznie. Wszystko zadziałało! :) Teraz masz skonfigurowany rejestrator. Możesz pobawić się niektórymi programami, które napisałeś wcześniej, dodając wywołania rejestratora do wszystkich metod i spojrzeć na wynikowy dziennik :) W celu dodatkowej lektury gorąco polecam ten artykuł . Tam temat logowań jest szczegółowo omówiony i nie będzie łatwo go przeczytać za jednym posiedzeniem. Zawiera jednak wiele przydatnych dodatkowych informacji. Dowiecie się na przykład jak skonfigurować logger tak, aby tworzył nowy plik tekstowy, gdy nasz plik testlog.txt osiągnie określony rozmiar :) I to już koniec naszej lekcji! Dziś dowiedziałeś się o bardzo ważnym temacie, a wiedza ta na pewno przyda Ci się w Twojej przyszłej pracy. Do zobaczenia! :)
Komentarze
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION