Skip to content

Instantly share code, notes, and snippets.

@Ocramius
Created November 12, 2011 13:42
Show Gist options
  • Save Ocramius/1360533 to your computer and use it in GitHub Desktop.
Save Ocramius/1360533 to your computer and use it in GitHub Desktop.
Zend\Db adapter instantiation through Zend Framework 2 Di
<?php
return array(
'di' => array(
'definition' => array(
//teaching DI to use the factory
'class' => array(
'Zend\Db\Db' => array(
'methods' => array(
'factory' => array(
'adapter' => array(
'type' => false,
'required' => true,
),
'config' => array(
'type' => false,
'required' => false,
),
),
),
),
'Zend\Db\Adapter\AbstractAdapter' => array(
'instantiator' => array(
'Zend\Db\Db',
'factory',
),
),
),
),
'instance' => array(
'alias' => array(
//we just know it's an abstract adapter
'my-db-adapter' => 'Zend\Db\Adapter\AbstractAdapter',
),
//documentmanager
'my-db-adapter' => array(
'parameters' => array(
'adapter' => array(
// same db factory parameters you used in 1.x (I suppose)
),
),
),
),
),
);
@cmple
Copy link

cmple commented Feb 9, 2012

Hi there,
I'm not sure how can I use the my-db-adapter ? I assume it's going to be converted into 'myDbAdapter' var somewhere ?
For example I have the following file:
../module/MyModule/src/MyModule/Model/Account.php
How can I use the default dbAdapter throughout all of my Model classes ?
Thanks!

@Ocramius
Copy link
Author

Hey,

in your case, I suppose your MyModule\Model\Account is a Zend\Db\Table, right?
From my point of view, the default DB adapter is no more an existing concept.
What you have to do is to define a dependency:

            'MyModule\Model\Account' => array(
                'parameters' => array(
                    'adapter' => 'my-db-adapter',
                ),
            ),

That will do the trick.
To get your fully configured table object, you now do $myModel = $di->get('MyModule\Model\Account');

If you are not sure about what Zend\Di is, please look at http://packages.zendframework.com/docs/latest/manual/en/zend.di.html

@cmple
Copy link

cmple commented Feb 10, 2012

Hey,
Is there a good reason for using a db table instead of a db adapter ?
I've heard that tables are much heavier than a db adapter query, did it change with zf2 ?
Also, can something like this be accomplished with a db table:

        ->from(array('l'=> 'listings'),array(
            'l.id',
            'l. ...',
        ))
        ->joinLeft(array('i' => 'items'),"i.id = l.itemId AND i.userId = '{$this->userInfo->id}'", array(
            'i.title',
            'i. ...'
        ))
        ->joinLeft(array('u' => 'uploads'),"u.id = l.picture AND u.userId = '{$this->userInfo->id}'", array(
            'thumbnail' => 'u.fileNameThumb',
        ))
        ->where('...');

@Ocramius
Copy link
Author

@cmple Either way you see it, the db adapter is always needed... Table objects add some overhead, yes, but also fit completely different tasks. Either way you see it, both require an adapter to get the work done. In my code, I just generate the adapter and in my comment I show you how to use it with a table.
If you want to use the adapter alone, then it's just like
php$adapter = $di->get('my-db-adapter');

@cmple
Copy link

cmple commented Feb 10, 2012

Where is $di coming from ?
I've tried:
use Zend\Di\Di as Di;
..... {
$di = new Di();
$db = $di->get('my-db-adapter');

That didn't work

also is there a way to turn on php errors like in zf1:
[development : production]
phpSettings.display_startup_errors = 1
phpSettings.display_errors = 1

It's kinda hard to code with no error reporting :)

@Ocramius
Copy link
Author

Did you clone the application skeleton? There's a nice tutorial at http://packages.zendframework.com/docs/latest/manual/en/zend.mvc.html

@andrew13
Copy link

 'MyModule\Model\Account' => array(
                'parameters' => array(
                    'adapter' => 'my-db-adapter',
                ),
            ),

Does this need to be defined for every model that is used? IE

 'Album\Controller\AlbumController' => array(
                'parameters' => array(
                    'albumTable' => 'Album\Model\AlbumTable',
                    'bandTable' => 'Album\Model\BandTable',
                ),
            ),
'Album\Controller\BandController' => array(
                'parameters' => array(
                    'bandTable' => 'Album\Model\BandTable',
                ),
            ),

In other words does every controller need to have the Model specified?

@Ocramius
Copy link
Author

If you have multiple defined, yes. Otherwise, if you typehint your methods correctly, like following:

    public function __construct(My\Stuff $stuff) {
        $this->stuff = $stuff;
    }

Then, if you defined an alias 'my-stuff' for an instance of type My\Stuff, you could just use Zend\Di\Configuration option 'preference', like following, you should not be worried about defining injections manually every time:

return array(
    'instance' => array(
        'alias' => array(
            'my-stuff' => 'My\Stuff',
        ),
        'preference' => array(
            'My\Stuff' => 'my-stuff', //this will tell Zend\Di to use alias 'my-stuff' when no alias is requested, but an instance of My\Stuff is needed
        ),
    ),
);

That is just an example config. You can find more examples about Zend\Di at https://github.com/ralphschindler/Zend_DI-Examples

@andrew13
Copy link

Awesome thanks for the help!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment