2

リクエストに関する情報を取得しようとしていますが、結果を XML ファイルに入れる必要があります。次の要素を使用しています。

  • logEntry(ルート) (デフォルト)
    • タイムスタンプ (デフォルト) (文字列) タイムスタンプ
    • 優先度 (デフォルト) (文字列) 優先度
    • priorityName (デフォルト) (文字列) 優先度名
    • メッセージ (デフォルト) (文字列) メッセージ
    • uniqueId (新規) (文字列) 一意の ID
    • method (new) (string) Namespace\Class::MethodName()
    • args (新規) (文字列) base64 でエンコードされ、シリアル化された func_get_args();

次のようにする必要があります。

<logEntry><timestamp>2013-03-29T15:47:41+01:00</timestamp><priority>6</priority><priorityName>INFO</priorityName><message>Called</message><uniqueId>564fg56d4g5d4fg5f4g56fg465dfg</uniqueId><method>\Namespace\Controller::methodName</method><args>aa5abc8d6efeabcd7f67cb6a7df6bac5ba7a5fd7a5d6bac67a5bf6abcbb408f098=</args></logEntry>

私が読んだドキュメント: http://zf2.readthedocs.org/en/latest/modules/zend.log.formatters.html

動作しないコード:

$writer    = new \Zend\Log\Writer\Stream(getenv('LOG_FILE_LOCATION'));
$formatter = new \Zend\Log\Formatter\Xml('logEntry', array(
    'timestamp'    => 'timestamp',
    'priority'     => 'priority',
    'priorityName' => 'priorityName',
    'message'      => 'message',
    'uniqueId'     => 'uniqueId',
    'method'       => 'method',
    'args'         => 'args',
));
$writer->setFormatter($formatter);
$logger = new \Zend\Log\Logger();
$logger->addWriter($writer);

$logger->info('Started', array(
    'uniqueId' => $this->createGuid(),
    'method'   => __METHOD__,
    'args'     => serialize(array(get_class($e))), 
));

エラー: 注意: Undefined index: uniqueId in /var/www/library/Zend/Log/Formatter/Xml.php 行 168

Xml.php のコード https://github.com/zendframework/zf2/blob/master/library/Zend/Log/Formatter/Xml.php#L168

$event[$fieldKey] が問題です。$fieldKey は $event['extra'][$fieldKey] にのみ存在します。$this->elementMap はフラットです (extra 用の余分な配列は追加されません)。

Array
(
    [timestamp] => timestamp
    [priority] => priority
    [priorityName] => priorityName
    [message] => message
    [uniqueId] => uniqueId
    [method] => method
    [args] => args
)

私は何を間違っていますか?

これは ZF2 のバグだと思います... Github でコードを読むと、余分なフィールドとキーが見つからず、検出できません... どう思いますか?

4

1 に答える 1

4

問題は、Xml フォーマッターがextraロガーに渡されるデータを無視することです (ロガーはそれが配列であると想定し、フォーマッターは空の文字列、__toString() メソッドを持つオブジェクト、またはスカラーでないものを暗黙のうちに無視します。解決策は独自のプロセッサを作成して、余分なデータをロガーから渡される通常のイベント データとマージします。

これは非常に単純な例ですが、独自の関数の余分なデータの配列で渡される許可されたキー値をチェックしたいかもしれませんが、これはデモンストレーション目的で機能します。(おそらく、クラスのより良い名前も考えられるでしょう:D)

<?php
namespace Application\Log\Processor;

use Zend\Log\Processor\ProcessorInterface;

class Merger implements ProcessorInterface
{

    /**
     * Merge extra data into the event data
     * @param array $event event data
     * @return array event data
     */
    public function process(array $event)
    {
        if (!isset($event['extra'])) {
            $event['extra'] = array();
        }
        return array_merge($event, $event['extra']);
    }
}

実装するには、動作しないコードの最初の例で行ったように行いますが、使用するルート要素名を渡すだけです

$writer    = new \Zend\Log\Writer\Stream(getenv('LOG_FILE_LOCATION'));
$formatter = new \Zend\Log\Formatter\Xml('logEntry');
$writer->setFormatter($formatter);
$logger = new \Zend\Log\Logger();
$logger->addWriter($writer);

// add the processor into the mix
$processor = new \Application\Log\Processor\Merger;
$logger->addProcessor($processor);

$data = array(
    'uniqueId' => $this->createGuid(),
    'method'   => __METHOD__,
    'args'     => serialize(func_get_args()), 
);
$logger->info('Testing', $data);
于 2013-03-29T16:08:39.800 に答える