I use Zend Expressive framework via default ZE skeleton app with Zend ServiceManager as DIC and Plates as template engine.
Let's say I've got index.phtml
template. I want to get some service, which dumps me assets, smth like:
<?= $this->getContainer()->get('my service class')->dumpAssets() ?>
Service is registered via factory and accesible in the app:
<? $container->get('my service class') ?>
How to pass external service instance or its result into template?
It's pretty much bad practice to inject the entire service container into a template (or any other class except a factory). A better approach would be to write an extension to dump the assets.
Extension class:
<?php
namespace App\Container;
use League\Plates\Engine;
use League\Plates\Extension\ExtensionInterface;
use App\Service\AssetsService;
class DumpAssetsExtension implements ExtensionInterface
{
public $assetsService;
/**
* AssetsExtension constructor.
* @param $container
*/
public function __construct(AssetsService $assetsService)
{
$this->assetsService = $assetsService;
}
public function register(Engine $engine)
{
$engine->registerFunction('dumpAssets', [$this, 'dumpAssets']);
}
public function dumpAssets()
{
return $this->assetsService->dumpAssets();
}
}
Factory:
<?php
namespace App\Container;
use Interop\Container\ContainerInterface;
class DumpAssetsFactory
{
public function __invoke(ContainerInterface $container)
{
$assetsService = $container->get(App\Service\AssetsService::class);
return new PlatesExtension($assetsService);
}
}
Configuration:
<?php
return [
// ...
'factories' => [
App\Container\DumpAssetsExtension::class => App\Container\DumpAssetsFactory::class,
]
];
In your template:
<?php
$service = $this->dumpAssets();
?>
I figured out how to access container from template engine via extensions . It's not clear MVC-ly, but...
At first, add plates config into config/autoload/templates.global
:
return [
// some othe settings
'plates' => [
'extensions' => [
App\Container\PlatesExtension::class,
],
],
],
At second, create App\\Container\\PlatesExtension.php
with code:
<?php
namespace App\Container;
use League\Plates\Engine;
use League\Plates\Extension\ExtensionInterface;
class PlatesExtension implements ExtensionInterface
{
public $container;
/**
* AssetsExtension constructor.
* @param $container
*/
public function __construct($container)
{
$this->container = $container;
}
public function register(Engine $engine)
{
$engine->registerFunction('container', [$this, 'getContainer']);
}
public function getContainer()
{
return $this->container;
}
}
At third, create factory App\\Container\\PlatesExtensionFactory.php
to inject container into plates extension:
<?php
namespace App\Container;
use Interop\Container\ContainerInterface;
class PlatesExtensionFactory
{
public function __invoke(ContainerInterface $container)
{
return new PlatesExtension($container);
}
}
Next, register plates extension in ServiceManager ( config/dependencies.global.php
):
return [
// some other settings
'factories' => [
App\Container\PlatesExtension::class => App\Container\PlatesExtensionFactory::class,
]
];
At last, get container and needed service from Plates template:
<?
$service = $this->container()->get('my service class');
?>
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.