Database data within the BasePresenter

Se7en
Member | 13
+
0
-

Hi all.

I am trying to load a database table within my BasePresenter so that the data can be used via all the child presenters.

Here's the BasePresenter:

<?php
namespace App\Presenters;

use App\Data;
use Nette;

abstract class BasePresenter extends Nette\Application\UI\Presenter
{
    private $globalSettings;

    public function __construct(Data\GlobalTable $globalSettings)
    {
		parent::__construct();
		$this->globalSettings = $globalSettings;
    }

  	protected function startup()
	{
	    parent::startup();
		// Here we'll add some global settings from the database to make them available via other presenters
	}

}
?>

And here is an extended presenter example:

<?php
namespace App\Presenters;

use App\Data;
use Nette;

final class TestPresenter extends BasePresenter
{
	private $anotherTable;

	public function __construct(Data\AnotherTable $anotherTable)
	{
		parent::__construct();
		$this->anotherTable = $anotherTable;
	}
}
?>

But I get the following error:

ArgumentCountError

Too few arguments to function App\Presenters\BasePresenter::__construct(), 0 passed in /home/test/app/presenters/TestPresenter.php.........

Can anybody explain where I'm going wrong?

nightfish
Member | 529
+
+2
-

Se7en wrote:

Too few arguments to function App\Presenters\BasePresenter::__construct(), 0 passed in /home/test/app/presenters/TestPresenter.php.........

Can anybody explain where I'm going wrong?

When extending a class, you must pass all required parameters to parent's constructor.

There are two main ways of doing it:

  1. Add GlobalTable dependency to TestPresenter.php and pass it to parent, while leaving BasePresenter.php unchanged:
public function __construct(Data\GlobalTable $globalSettings, Data\AnotherTable $anotherTable)
{
 		parent::__construct($globalSettings);
 		$this->anotherTable = $anotherTable;
}
  1. In abstract presenters you can use dependency injection via @inject annotation. In BasePresenter.php change private to public, add @inject annotation:
abstract class BasePresenter extends Nette\Application\UI\Presenter
{
    /** @var Data\GlobalTable @inject */
    public $globalSettings;

    // the rest of your code (constructor needs not be here, unless you do stuff other than assigning dependencies in it)
}

This way you can add dependencies to your BasePresenter without the need to explicitly pass them from child presenters.

See docs for more information.

Last edited by nightfish (19. 4. 2019 10:00)

Se7en
Member | 13
+
0
-

Thanks for the clear reply. That makes a lot of sense.

I still find it hard to find exactly what I'm looking for via the docs at times.

CZechBoY
Member | 3608
+
0
-

So start with some php tutorial and you learn that.