tos/logger

There is no license information available for the latest version (v4.2.1) of this package.

Convenție de logare

v4.2.1 2024-07-14 01:54 UTC

This package is auto-updated.

Last update: 2024-10-14 02:27:08 UTC


README

Instalare

Se instalează cu Composer

composer require tos/logger:~4.2

În fișierul app/config/app.php:

  • se comentează Illuminate\Log\LogServiceProvider
  • se adaugă \TravelOS\Support\Logger\ServiceProvider::class
    • sau un service provider propriu care-l extinde pe acesta

În final va fi de forma:

                'Illuminate\Filesystem\FilesystemServiceProvider',
                'Illuminate\Hashing\HashServiceProvider',
                'Illuminate\Html\HtmlServiceProvider',
-               'Illuminate\Log\LogServiceProvider',
+               // 'Illuminate\Log\LogServiceProvider',
+               \TravelOS\Support\Logger\ServiceProvider::class,
                'Illuminate\Mail\MailServiceProvider',
                'Illuminate\Database\MigrationServiceProvider',
                'Illuminate\Pagination\PaginationServiceProvider',

În fișierul app/start/global.php se comentează Log::useFiles(storage_path() .'/logs/laravel.log');, în final va fi de forma:

*
|--------------------------------------------------------------------------
| Application Error Logger
|--------------------------------------------------------------------------
|
| Here we will configure the error logger setup for the application which
| is built on top of the wonderful Monolog library. By default we will
| build a basic log file setup which creates a single file for logs.
|
*/

// Log::useFiles(storage_path().'/logs/laravel.log');

Configurare

Implicit va loga în app/storage/logs/laravel.log doar dacă request-ul întâmpină un WARNING.

O linie de log va fi de forma

[%datetime%] %channel%.%level_name%: %message% %context% %extra%\n

Dacă level-ul, message-ul și context-ul sunt furnizate la folosire, în extra vor apărea informațiile generate de procesatoare.

Folosire

Se folosește trait-ul \TravelOS\Support\Logger\Traits\LoggerAware în orice clasă încărcată prin IoC.

Exemplu:

class LogTester
{
  use \TravelOS\Support\Logger\Traits\LoggerAware;

Acum vom avea acces la metodele:

  • $this->debug($message, array $context = array())
  • $this->info($message, array $context = array())
  • $this->notice($message, array $context = array())
  • $this->warning($message, array $context = array())
  • $this->error($message, array $context = array())
  • s.a.m.d.

Documentație

Handler-e

Se pot folosi oricare Handler-ele de Monolog singurul extins este \TravelOS\Support\Logger\Handlers\Stream care e adaptat pentru StopWatcher.

Procesatoare

Este implicit încărcat cu 4 procesatoare care adaugă informație în spațiul extra.

Acestea sunt:

Environment

[2024-07-12 23:44:40] production.DEBUG  : message     [] {"env":"production"}

Adaugă env-ul aplicației în linia fiecărui log. Util când se configurează mai multe canale și channel-ul nu mai corespunde cu env-ul.

Fingerprint

[2024-07-12 23:44:40] production.DEBUG  : message     [] {"fingerprint":1720827880.645}

Adaugă o semnătură unică a request-ului care a generat log-ul. Util când la un trafic mai mare în care log-urile sunt amestecate vrei să filtrezi doar liniile unui singur request.

StopWatch

Folosește Stopwatch Component pentru a putea parsa logurile și a injecta timpii de execuție ai unui proces.

Convenția de bază este sa se logheze o linie cu sufix-ul - start, urmată de altă logare cu sufix-ul - stop, iar cea din urmă va genera un extra cu timpul și memoria folosite în acel interval.

Exemplu:

        $this->debug('mesaj unic - start');
        sleep(5);
        $this->info('mesaj unic - stop');

Va genera următorul log:

[2024-07-13 00:26:05] production.DEBUG  : mesaj unic                     - start     [] []
[2024-07-13 00:26:10] production.INFO   : mesaj unic                     - stop      [] {"stopwatch":"5s - 8 MB"}
Threshold-ul

Pentru că doar linia de - stop are informație utilă, am convenit ca ea să aibă level INFO pentru a o putea izola în Handler-e dacă dorim.

Dacă folosim sufix-ul - stop! și procesul durează mai mult de 60s de când a fost logat - start-ul level-ul va fi transformat în WARNING.

Exemplu:

$this->debug('mesaj unic - start');
sleep(61);
$this->info('mesaj unic - stop!');

Va genera următorul log:

[2024-07-13 00:33:45] production.DEBUG  : mesaj unic                     - start     [] []
[2024-07-13 00:34:46] production.WARNING: mesaj unic                     - stop!     [] {"stopwatch":"1m 1s!!! - 8MB"}

Putem ajusta threshold-ul in secunde folosind sufix-ul - stop!30

Prefixările

Pentru a face logurile mai lizibile putem prefixa ierarhic liniile asemena unui backtrace.

Exemplu:

Avem un request în care se cer niște rapoarte pe baza informațiilor date.

Se vor petrece următoarele secvențe:

  • validare date
  • interogare DB
  • generare raport
  • trimitere email
  • randare răspuns

Codul ar putea arăta așa:

    public function generateReport()
    {
        try {
            $this->getLogger()->lineBreak()->setPrefix('GenReport');
            // $this->debug('test');
            try {
                $this->getLogger()->setPrefix('Validator');
                $validator = \Validator::make([], []);
                if($validator->fails()) {
                    $this->info('validare eșuată');

                    return Redirect::to('reportGenerator')->withErrors($validator);
                }
                $this->debug('date valide');
            } finally {
                $this->getLogger()->popPrefix();
            }

            $data = $this->getData();
            $pdf  = $this->generatePdf($data);
            $this->sendEmail($pdf);

            return $this->download($pdf);
        } finally {
            $this->getLogger()->popPrefix();
        }
    }

    private function getData(): array
    {
        try {
            $this->getLogger()->setPrefix('Repo');
            $this->debug('aduc date user', [ 'user_id' => '10' ]);
            sleep(1);
            $data = [ 'data' ];
            $this->debug('date aduse', [ 'count' => count($data) ]);

            return $data;
        } finally {
            $this->getLogger()->popPrefix();
        }
    }

    private function generatePdf( array $data ): string
    {
        try {
            $this->getLogger()->setPrefix('PdfMaker');
            $this->debug('generez raport', [ 'rows' => count($data) ]);
            sleep(1);
            $pdfPath = storage_path('report.pdf');
            $this->debug('raport generat');

            return $pdfPath;
        } finally {
            $this->getLogger()->popPrefix();
        }
    }

    private function sendEmail( string $pdf )
    {
        try {
            $this->getLogger()->setPrefix('Email');

            $this->debug('trimit raport');
            Mail::send('emails.report', [ 'key' => 'value' ],
                function ( $message ) use ( $pdf ) {
                    $message->to('foo@example.com', 'John Smith')->subject('Welcome!')
                            ->attach($pdf);
                });
            $this->debug('raport trimis');
        } finally {
            $this->getLogger()->popPrefix();
        }

    }

    private function download( string $pdf )
    {
        try {
            $this->debug('generez răspuns - start');

            return Response::download($pdf);
        } finally {
            $this->debug('generez răspuns - stop');
        }
    }

Iar logul generat așa:

[2024-07-13 23:01:32] production.INFO   : ________________________________________________________________________________ [] []
[2024-07-13 23:01:32] production.DEBUG  : GenReport|Validator :: date valide [] []
[2024-07-13 23:01:32] production.INFO   : GenReport :: Validator - done! [] {"stopwatch":"0ms - 2 MB"}
[2024-07-13 23:01:32] production.DEBUG  : GenReport|Repo :: aduc date user {"user_id":"10"} []
[2024-07-13 23:01:33] production.DEBUG  : GenReport|Repo :: date aduse {"count":1} []
[2024-07-13 23:01:33] production.INFO   : GenReport :: Repo - done! [] {"stopwatch":"1s - 2 MB"}
[2024-07-13 23:01:33] production.DEBUG  : GenReport|PdfMaker :: generez raport {"rows":1} []
[2024-07-13 23:01:34] production.DEBUG  : GenReport|PdfMaker :: raport generat [] []
[2024-07-13 23:01:34] production.INFO   : GenReport :: PdfMaker - done! [] {"stopwatch":"1s - 2 MB"}
[2024-07-13 23:01:34] production.DEBUG  : GenReport|Email :: trimit raport [] []
[2024-07-13 23:01:34] production.INFO   : GenReport|Email :: Pretending to mail message to: foo@example.com [] []
[2024-07-13 23:01:34] production.DEBUG  : GenReport|Email :: raport trimis [] []
[2024-07-13 23:01:34] production.INFO   : GenReport :: Email - done! [] {"stopwatch":"61ms - 4 MB"}
[2024-07-13 23:01:34] production.DEBUG  : GenReport :: generez răspuns  - start     [] []
[2024-07-13 23:01:34] production.DEBUG  : GenReport :: generez răspuns  - stop      [] {"stopwatch":"2ms - 4 MB"}
[2024-07-13 23:01:34] production.INFO   : GenReport - done! [] {"stopwatch":"2s - 4 MB"}

Formatoare

Am extins LineFormatter, acum aliniază level-urile dintr-un log pentru a le putea urmări mai ușor.