简体   繁体   中英

Zend Framework 2: How to get DBAdapter in custom library

In project on ZF2 I'm creating my custom library vendor/TestVendor/TestLibrary/. In this library I want to create 2 classes: TestClass and TestClassTable. The TestClass should instantiate my custom object, the TestClassTable should deal with database and the tables. And I need to use DBAdapter in the class TestClass table to access database and tables.

The code looks like this:

In module index controller I create object from TestClass

class TestController extends AbstractActionController {

$TestObject = $this->getServiceLocator()->get('TestClass');

}

In my custom class vendor/TestVendor/TestLibrary/TestClass.php I create some methods:

namespace TestVendor\\TestLibrary;

class TestClass {

protected $Id;
protected $Name;

function __construct(){}

public function doMethodOne() {
    $TestClassTable = new TestClassTable();
$this->Id = 1;
$TestObjectRow = $TestClassTable->getTestObjectById($this->Id);
$this->Name = $TestObjectRow['Name'];
return $this;
}

}

And in TestClassTable class I want to access database

namespace TestVendor\\TestLibrary;

use Zend\\Db\\TableGateway\\AbstractTableGateway;

class TestClassTable extends AbstractTableGateway {

public function __construct() {

    $this->table = 'table_name';
    $this->adapter = $this->getServiceLocator()->get('Zend\Db\Adapter\Adapter');

}

public function getTestObjectById($Id) {

    $Id  = (int) $Id;
    $rowset = $this->select(array('id' => $Id));
    $row = $rowset->current();
    return $row;
}

}

Of course trying to access service locator or database adapter in my class TestClassTable brings error.

Looks like my approach is wrong.

Thanks in advance very much.

If you inject DBAdapter manually your code is highly coupled, using the service manager helps with this however you are still coupling yourself to the DBAdapter. There are various ways to de-couple your vendor code from this depending on what you are trying to achieve. Have a look at the Data mapper pattern & Adapter pattern - with the service manager as @Andrew suggested.

NB: A library in vendors in ZF2 should be a separate project & included via composer.

You should inject it into your class using the Service Manager.

Service Manager Config:

return array(
    'factories' => array(
         'MyClass' => function($sm) {
            $dbAdapter = $sm->get('Zend\Db\Adapter\Adapter');
            $myClass = new \MyNamespace\MyClass($dbAdapter);
            // I would have a setter, and inject like that but
            // using the constructor is fine too
            //$myclass->setDbAdapter($dbAdapter);

            return $myClass;
        },
    )
)

Now you can grab an instance inside your controller, with the DB adapter already injected for you:

SomeController.php

public function indexAction()
{
    $MyObject = $this->getServiceLocator()->get('MyClass');
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM