2

Symfony 2.1プロジェクトの場合、配列を返すときにJsonResponseオブジェクトを自動的に作成するリスナーを登録する新しいアノテーション@Json()を作成しようとしています。私はそれを機能させましたが、何らかの理由で、@ Jsonアノテーションがないメソッドでも、リスナーは常に呼び出されます。Sensioエクストラバンドルは@Templateアノテーションを使用してこれを行うため、私のアプローチは機能すると思います。

これが私の注釈コードです。

<?php

namespace Company\Bundle\Annotations;

/**
 * @Annotation
 */
class Json extends \Sensio\Bundle\FrameworkExtraBundle\Configuration\ConfigurationAnnotation
{
    public function getAliasName()
    {
        return 'json';
    }
}

これが私のリスナーコードです。

<?php

namespace Company\Bundle\Listener\Response\Json;

class JsonListener
{
    //..

    public function onKernelView(GetResponseForControllerResultEvent $event)
    {
        $request = $event->getRequest();
        $data = $event->getControllerResult();

        if(is_array($data) || is_object($data)) {
            if ($request->attributes->get('_json')) {
                $event->setResponse(new JsonResponse($data));
            }
        }
    }
}

これはリスナーのyaml定義です。

json.listener:
            class:      Company\Bundle\Listener\Response\Json
            arguments:  [@service_container]
            tags:
                - { name: kernel.event_listener, event: kernel.view, method: onKernelView }

kernel.viewリスナーとして登録されているため、明らかにここに何かが欠けています。これを変更して、コントローラーアクションに@Json()アノテーションが存在する場合にのみ呼び出されるようにするにはどうすればよいですか?

4

1 に答える 1

1

決定的な答えのふりをしないでください。

なぜ拡張しているのかわかりませんConfigurationAnnotation。コンストラクターはを受け入れarrayますが、アノテーションの構成は必要ありません。代わりに、実装ConfigurationInterface

namespace Company\Bundle\Annotations;

use Sensio\Bundle\FrameworkExtraBundle\Configuration\ConfigurationInterface;

/**
 * @Annotation
 */
class Json implements ConfigurationInterface
{
    public function getAliasName()
    {
        return 'json';
    }

    public function allowArray()
    {
        return false;
    }
}

SensionFrameworkExtraBundleのSensioControllerListenerは、アノテーション(クラスとメソッドアノテーションのマージ)を読み取り、次のチェックを実行します。

if ($configuration instanceof ConfigurationInterface) {
    if ($configuration->allowArray()) {
        $configurations['_'.$configuration->getAliasName()][] = $configuration;
    } else {
        $configurations['_'.$configuration->getAliasName()] = $configuration;
    }
}

接頭辞が。のリクエスト属性を設定し_ます。を正しくチェックして_jsonいるので、機能するはずです。$request->attributesビューイベントリスナーにダンプしてみてください。json.listenerサービスも正しくロードされていることを確認してください(でダンプしてくださいphp app/console container:debug >> container.txt)。

それが機能しない場合は、ここにデバッグステートメントと印刷ステートメントを追加してみてくださいControllerListener.phpベンダーフォルダーにあります)。

var_dump(array_keys($configurations)); // Should contain _json

編集する前にコピーを作成することを忘れないでください。そうしないと、Composerは依存関係を更新するときにスローしてエラーになります。

于 2013-02-21T11:47:38.937 に答える