3

現在、複数のプロジェクトで再利用可能なライブラリとして機能するモジュールを構築中ですが、ライブラリであるため、コントローラーは必要ありません。たとえば、私がやろうとしているのは、Marketo soap API 用の zf2 モジュールを作成することです。ユーザーは、キーと wsdl の場所を /ROOT/config/autoload/local.php に追加します。構成には、「marketo」=>array() のようなものが含まれます。

今私が抱えている問題は、モジュールを使用している自分自身や他の人に、次のようなことができるようにしたいということです...

$marketo = new \Marketo\Client\Client();

\Marketo\Client\Client() クラス内で、コンストラクターに $config['marketo'] の配列キーを読み取らせます。

ただし、これらすべてを ini ファイルに入れることもできますが、zf2 の他のすべての構成と同じように維持することをお勧めします。

要約すると、マージされた zend 構成の配列キーを取得して、クラス内で使用したいと思います...

class Marketo{
    private $key;
    private $pass;
    public function __construct(){
        $c = \Zend\Config\Config('marketo);
        $this->key = $c['key'];
        $this->pass = $c['pass'];
    }
}

============ 以下の回答による ZF 2.1.1 の時点で完全に機能するソリューション =============

モジュール構造は次のようになります (新しい例を使用して、最初からやり直すことができます) + ディレクトリ名を示します - ファイル名を示します

modules
  - Application /* Standard setup with an IndexController */
  - Cybersource /* The new module to be added */
      + config
         - module.config.php
      + src
         + Cybersource
            + Client
               - Client.php
            + ServiceFactory
               - ClientServiceFactory.php
      - Module.php
      - autoload_classmap.php

module.config.php

return array(
    'service_manager' => array(
        'factories' => array(
            'Cybersource\Client\Client' => 'Cybersource\ServiceFactory\ClientServiceFactory',
        )
    ),
    'cybersource' => array(
        'Endpoint' => 'https://ics2wstest.ic3.com/commerce/1.x/transactionProcessor', // test environment
        'WSDL' => 'https://ics2wstest.ic3.com/commerce/1.x/transactionProcessor/CyberSourceTransaction_1.80.wsdl',
        'TXKey' => '',
        'MerchID' => '',
    ),
);

クライアント.php

namespace Cybersource\Client;

class Client {

    private $config;

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

    public function getConfig() {
        return $this->config;
    }

}

ClientServiceFactory.php

namespace Cybersource\ServiceFactory;

use Cybersource\Client\Client;
use Zend\ServiceManager\FactoryInterface;
use Zend\ServiceManager\ServiceLocatorInterface;

class ClientServiceFactory implements FactoryInterface {

    public function createService(ServiceLocatorInterface $serviceLocator) {
        $config = $serviceLocator->get('Config');

        return new Client($config['cybersource']);
    }

}

Module.php

namespace Cybersource;
use Zend\ModuleManager\Feature\ConfigProviderInterface;

class Module implements ConfigProviderInterface {

    public function getAutoloaderConfig() {
        return array(
            'Zend\Loader\ClassMapAutoloader' => array(
                __DIR__ . '/autoload_classmap.php',
            )
        );
    }

    public function getConfig() {
        return include __DIR__ . '/config/module.config.php';
    }

}

autoload_classmap.php

<?php
// Generated by ZF2's ./bin/classmap_generator.php
return array(
    'Cybersource\Module'                              => __DIR__ . '/Module.php',
    'Cybersource\Client\Client'                       => __DIR__ . '/src/Cybersource/Client/Client.php',
    'Cybersource\ServiceFactory\ClientServiceFactory' => __DIR__ . '/src/ServiceFactory/ClientServiceFactory.php',
);

モジュールが application.config.php でアクティブ化されたら、次を使用して、アプリケーション モジュールの IndexController で使用できます。

<?php


namespace Application\Controller;

use Zend\Mvc\Controller\AbstractActionController;
use Zend\View\Model\ViewModel;
class IndexController extends AbstractActionController {

    public function indexAction() {
        $c = $this->getServiceLocator()->get('Cybersource\Client\Client');
        $conf = $c->getConfig();
        var_dump($conf);
        return new ViewModel();
    }

}

上記のコントローラー出力は、表示/テスト目的で getConfig() という関数を Client クラスに追加したため、構成の出力をダンプします。

すべての助けをありがとう。

4

2 に答える 2

2

ServiceFactoryを作成するには、 を定義する必要がありますClient。ServiceFactory は、マージされたモジュール構成を取得して、クライアントに設定できます。これで完全に分離され、Zend\Config がまったくなくてもクラスを再利用できます。多くの構成オプションがある場合は、拡張する別の構成クラスを作成し、\Zend\StdLib\AbstractOptionsこれをクライアントに渡すことができます。

namespace Marketo\Service;

class ClientServiceFactory implements FactoryInterface
{
    public function createService(ServiceLocatorInterface $serviceLocator)
    {
        //Get the merged config of all modules
        $configuration = $serviceLocator->get('Config');
        $configuration = $configuration['marketo'];

        $client = new \Marketo\Client\Client($configuration['key'], $configuration['pass']);
    }
}

クライアント ファクトリをサービス ロケータに登録します。module.config.phpまたはでこれを行います。Module.php

public function getServiceConfig()
{
    return array('factories' => array(
        'marketo_client' => 'Marketo\Service\ClientServiceFactory'
    );
}

ユーザーは ServiceManager からクライアントを取得できるようになりました。すべての構成がきちんとセットアップされています。

$sm->get('marketo_client');
于 2013-02-20T20:15:02.767 に答える
2

おそらく次のようにモジュールを定義します。

<?php

namespace Marketo;

use Zend\ModuleManager\Feature\ConfigProviderInterface;

class Module implements ConfigProviderInterface
{
    public function getConfig()
    {
        return array(
            'service_manager' => array(
                'factories' => array(
                    'Marketo\Client\Client' => 'Marketo\ServiceFactory\ClientServiceFactory',
                ),
            ),
            'marketo' => array(
                'key'  => 'DEFAULT',
                'pass' => 'DEFAULT',
            ),
        );
    }
}

注: overはより柔軟 (オーバーライド可能) であり、アプリケーションをセットアップするときにメソッド呼び出しがキャッシュされるため、getConfigoverを使用することを好みました。getServiceConfig

次にMarketo\ServiceFactory\ClientServiceFactory

<?php

namespace Marketo\ServiceFactory;

use Marketo\Client\Client;
use Zend\ServiceManager\FactoryInterface;
use Zend\ServiceManager\ServiceLocatorInterface;

class ClientServiceFactory implements FactoryInterface
{
    public function createService(ServiceLocatorInterface $serviceLocator)
    {
        $config = $serviceLocator->get('Config');

        return new Client($config['marketo']['key'], $value['marketo']['pass']);
    }
}

その後、次のように呼び出してサービス ロケーターから Marketo クライアントをプルできるようになります (コントローラーなどで)。

$marketoClient = $this->getServiceLocator()->get('Marketo\Client\Client');

この時点で、Marketo\Client\Clientとにかく で構築されkeypass両方とも に設定されていDEFAULTます。

続けて、ファイルを作成してこれをオーバーライドしましょうconfig/autoload/marketo.local.php(モジュールではなく、アプリケーションのルートに!):

<?php

return array(
    'marketo' => array(
        'key'  => 'MarketoAdmin',
        'pass' => 'Pa$$w0rd',
    ),
);

keyandを再配布してはならないため、これは非常に重要です。このファイルをorpassに入れます。.gitignoresvn:ignore

したがって、基本的にここで行ったことは次のとおりです。

  1. サービス ファクトリを使用して Marketo クライアントをインスタンス化するようにサービス マネージャの設定をセットアップする
  2. 'config'マージされた構成 (サービス名: ) を使用して Marketo クライアントをインスタンス化するようにサービス ファクトリをセットアップします。
  3. 実際のアプリケーション インスタンスのローカル構成を追加する
  4. サービス ロケータを介して Marketo サービスを取得します。
于 2013-02-20T20:28:15.840 に答える