Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Added ability to forward logs to an ArrayAccess #233

Merged
merged 1 commit into from
Sep 26, 2023

Conversation

rtripault
Copy link
Contributor

What does it do

It adds the ability to use a class implementing ArrayAccess interface to "forward" logs to.

Why is it needed

It provides the ability to "proxy" logs to a PSR/Monolog logger, ie.

use Monolog\Logger;
use Psr\Log\LoggerInterface;

final class Proxy implements \ArrayAccess
{
    private LoggerInterface $logger;

    public function __construct(LoggerInterface $logger)
    {
        $this->logger = $logger;
    }

    /**
     * @param mixed $offset
     * @param mixed $value
     */
    public function offsetSet($offset, $value): void
    {
        $this->logger->log(...self::modxLogEntryToMonolog($value));
    }

    /**
     * @param mixed $offset
     */
    public function offsetExists($offset): bool
    {
        return false;
    }

    /**
     * @param mixed $offset
     */
    public function offsetGet($offset): void
    {
        return;
    }

    /**
     * @param mixed $offset
     */
    public function offsetUnset($offset): void
    {
        return;
    }

    /**
     * Converts a modx produced log entry (using ARRAY_EXTENDED target) to monolog usable arguments
     *
     * @param array{
     *     'content': string,
     *     'level': string,
     *     'msg': string,
     *     'def': string,
     *     'file': string,
     *     'line': string
     * } $payload
     *
     * @see \xPDO::_log()
     *
     * @return array{int, string, array<mixed>}
     * @see LoggerInterface::log()
     */
    private static function modxLogEntryToMonolog(array $payload): array
    {
        \preg_match('/^\[([^\]]+)\].*/', $payload['content'], $matches);
        $datetime = $matches[1];

        $context = [
            'extra' => [
                'datetime' => $datetime,
                'level_name' => $payload['level'],
            ],
        ];

        // remove invalid characters from filename and linenumber (added by modx::log())
        $file = trim(str_replace('@ ', '', $payload['file']));
        $line = trim(str_replace(':', '', $payload['line']));

        // prepend MODX base path to index.php errors
        if ($file === '/index.php') {
            $file = MODX_BASE_PATH . $file;
        }

        // make sure the file exists
        if (file_exists($file)) {
            $context['extra']['fileName'] = $file;
            $context['extra']['lineNumber'] = $line;
        }

        return [self::getMonologLevel($payload['level']), $payload['msg'], $context];
    }

    /**
     * @param string $level
     *
     * @return int
     *
     * @see \xPDO::_getLogLevel()
     */
    private static function getMonologLevel(string $level): int
    {
        switch ($level) {
            case 'DEBUG':
                return Logger::DEBUG;
            case 'INFO':
                return Logger::INFO;
            case 'WARN':
                return Logger::WARNING;
            case 'ERROR':
                return Logger::ERROR;
            case 'FATAL':
            default:
                return Logger::EMERGENCY;
        }
    }
}

then once modX/XPDO is constructed (pseudo code)

/** @var \Psr\Log\LoggerInterface $logger */
$proxy = new Proxy($logger)
$modx->setLogTarget([
            'target' => 'ARRAY_EXTENDED',
            'options' => [
                'var' => & $proxy,
            ],
        ]);

Somehow related/alternative to #213

Hoping that makes sense and you feel it could be a valuable addition to the code.

@cla-bot
Copy link

cla-bot bot commented Sep 28, 2022

Thank you for your pull request and welcome to our community. We could not parse the GitHub identity of the following contributors: Romain Tripault.
This is most likely caused by a git client misconfiguration; please make sure to:

  1. check if your git client is configured with an email to sign commits git config --list | grep email
  2. If not, set it up using git config --global user.email [email protected]
  3. Make sure that the git commit email is configured in your GitHub account settings, see https://github.com/settings/emails

@Mark-H
Copy link
Collaborator

Mark-H commented Sep 28, 2022

LGTM, but would be nice to work on PSR-3 in xPDO 3.2 or so too :D

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants