Twig - parse variables from imported template - php

I trying to add new function to Twig Extension file which includes template and parses variables from included template. And I have no clue how to get variable from imported template.
My Templates
Config.html
{% set myVariable= "MyVariable" %}
template.html
{{layout("config") }}
My Config Variable: {{ myVariable }}
This is my Twig Extension Class.
class TwigExtensions extends \Twig_Extension {
public function getFunctions()
{
return array(
new \Twig_SimpleFunction(
'layout', array($this, 'twig_layout', ), [ 'needs_environment' => true, 'needs_context' => true, 'is_safe' => ['all'] ]
)
);
}
function twig_layout(\Twig_Environment &$env, &$context, $template, $variables = [], $withContext = true, $ignoreMissing = false, $sandboxed = false)
{
$file_name = (string)$template . ".html";
if ($withContext) {
$variables = array_merge($context, $variables);
}
$result = '';
try {
$result = $env->resolveTemplate($file_name)->render($variables);
// how to get variables from $file_name tempalte
} catch (Throwable $e) {
return "NULL"
}
return $result;
}
}

Related

Slim PHP Link to an anchor on another page

I am working on a website using the Slim framework. I am trying to make a link that takes the user to a specific place on the home page.
This is the normal link:
Home
First I tried to write an absolute link like:
Anchor
But this doesn't work and results in https://example.com/#anchor
This doesn't work either:
Home
How can I get the link to work and take me to the specified anchor?
The path_for twig extension can't handle anchors:
Home
UPD:
class DecoratedTwigExtension
{
private TwigExtension $twigExtension;
public function __construct(TwigExtension $twigExtension)
{
$this->twigExtension = $twigExtension;
}
public function __call($name, $arguments)
{
if (is_callable([$this->twigExtension, $name])) {
return $this->twigExtension->$name(...$arguments);
}
$message = sprintf('There is no callable method %s::%s', get_class($this->twigExtension), $name);
throw new \BadMethodCallException($message);
}
public function pathFor($name, $data = [], $queryParams = [], $appName = 'default', $anchor = '')
{
$path = $this->twigExtension->pathFor($name, $data, $queryParams);
// some manipulations with $path
if ($anchor !== '') {
}
return $path;
}
}
// Register Twig View helper
$container['view'] = function ($c) {
$view = new \Slim\Views\Twig('path/to/templates', [
'cache' => 'path/to/cache'
]);
// Instantiate and add Slim specific extension
$router = $c->get('router');
$uri = \Slim\Http\Uri::createFromEnvironment(new \Slim\Http\Environment($_SERVER));
// ======= the main lines =======
$twigExtension = new \Slim\Views\TwigExtension($router, $uri);
$view->addExtension(new \App\Namespace\DecoratedTwigExtension($twigExtension));
return $view;
};

Render Sonata admin list in block

I try to create a block for the main page based on list action sonata admin is possible?
example
dashboard:
blocks:
- { type: mea.task.block, position: center, roles: [ ROLE_WORKER ] }
Here is block render
class TaskListAdminBlock extends AbstractAdminBlockService
{
/**
* {#inheritdoc}
*/
public function execute(BlockContextInterface $blockContext, Response $response = null)
{
$controller = 'Mea\TaskBundle\Sonata\Controller\TaskCrudController::listAction';
$path = [
'_controller' => $controller,
];
$subRequest = $this->requestStack->getMasterRequest()->duplicate($query, null, $path);
return $this->kernel->handle($subRequest, HttpKernelInterface::SUB_REQUEST);
}
}
TaskCrudController is sonata admin controller for task
this throw error
There is no `_sonata_admin` defined for the controller `Mea\TaskBundle\Sonata\Controller\TaskCrudController` and the current route ``
Is possible to fix this code or archive this in another way?
Ok I found beautifully solution
This renders in ajax made admin list
public function execute(BlockContextInterface $blockContext, Response $response = null)
{
$controller = 'Mea\TaskBundle\Sonata\Controller\TaskCrudController::listAction';
$path = array(
'_controller' => $controller
);
$query = [
'filter'=>[
'_per_page'=>4,
],
];
$subRequest = $this->requestStack->getMasterRequest()->duplicate($query, null, $path);
$subRequest->headers->set('X-Requested-With','XMLHttpRequest');
$subRequest->request->set('_sonata_admin','mea.task.task.admin');
$response = $this->kernel->handle($subRequest, HttpKernelInterface::SUB_REQUEST);
return $response;
}
Not fully work fine - ajax mode switch actions to select.

Call to a member function addMessage() on null,

I am trying to add slim flash message to be accessed with my controller
using Slim framework 3 & Twig, But I get the following error :
Call to a member function addMessage() on null,
Buzz\Controllers\MailController::$flash in
C:\xampp\htdocs\myapp\app\Controllers\MailController.php on line 63
// bootfile.php
<?php
$container['MailController'] = function($container){ return new \Buzz\Controllers\MailController($container); };
$container['flash'] = function($container){ return new \Slim\Flash\Messages; };
$container['view'] = function($container){
$twig = new \Slim\Views\Twig(__DIR__ . '/../pages/views', [ 'cache' => false, ]);
$twig->addExtension(new \Slim\Views\TwigExtension( $container->router, $container->request->getUri()));
$view->getEnvironment()->addGlobal('flash', $container->flash);
return $twig;
};
// MailController.php
public function sendmail($request, $response){
$sent = mail->send();
if ($sent) {
$this->flash->addMessage('mailsuccess', 'Thank you for contacting');
}
}

how to render twig template and return function zend framework

I'm migrating from zend framework 1 to 3 , and I have a function that returns twig template but I don't know what should I use to render view twig template on zf3
How to:
use class of viewer
set my template path
set array to render it in template
return template
code:
protected function convertItemList($aItemList)
{
$aSet = [];
//$config['template_paths'] = [APPLICATION_PATH . '/../library/Core/Backend/SRO/Views/'];
//$oView = new Core_Twig_View($config);
if (!$aItemList) {
return [];
}
foreach ($aItemList as $iKey => $aCurItem) {
$aSpecialInfo = [];
$aInfo = $aCurItem;
$aInfo['info'] = $this->getItemInfo($aCurItem);
$aInfo['blues'] = $this->getBluesStats($aCurItem, $aSpecialInfo);
$aInfo['whitestats'] = $this->getWhiteStats($aCurItem, $aSpecialInfo);
//$oView->assign('aItem', $aInfo);
$i = isset($aCurItem['Slot']) ? $aCurItem['Slot'] : $aCurItem['ID64'];
if ($aCurItem['MaxStack'] > 1) {
$aSet[$i]['amount'] = $aCurItem['Data'];
}
$aSet[$i]['TypeID2'] = $aInfo['TypeID2'];
$aSet[$i]['OptLevel'] = $aInfo['OptLevel'];
$aSet[$i]['RefItemID'] = !isset($aCurItem['RefItemID']) ? 0 : $aCurItem['RefItemID'];
$aSet[$i]['special'] = isset($aInfo['info']['sox']) && $aInfo['info']['sox'] ? true : false;
$aSet[$i]['ItemID'] = $aCurItem['ID64'];
$aSet[$i]['ItemName'] = $aInfo['info']['WebName'];
$aSet[$i]['imgpath'] = $this->getItemIcon($aCurItem['AssocFileIcon128']);
//$aSet[$i]['data'] = $oView->render('itemData.twig');
}
return $aSet;
}
I use this module https://github.com/OxCom/zf3-twig.
You can install it by github instructions and add this parameter to zf3 configuration array:
'service_manager' => array(
'factories' => array(
...
'TwigStrategy' => \ZendTwig\Service\TwigStrategyFactory::class,
...
),
)
1) After this you can use Twig in some action of some controller by this code:
function someAction(){
...
$viewModel = new ZendTwig\View\TwigModel(['foo'=>'bar']);
return $viewModel;
}
2) To set other template:
function someAction(){
$viewModel = new ZendTwig\View\TwigModel(['foo'=>'bar']);
$viewModel->setTemplate('application/controller/name'); //set path here
return $viewModel;
}
3) You can to set array variables by TwigModel "__construct" parameter:
function someAction(){
$viewModel = new ZendTwig\View\TwigModel($someVariablesArray);
$viewModel->setTemplate('application/controller/name'); //set path here
return $viewModel;
}
4) If you need to return html code, you need to do something:
Add in services config one more param:
'service_manager' => array(
'factories' => array(
...
'TwigStrategy' => \ZendTwig\Service\TwigStrategyFactory::class,
'TwigRenderer' => \ZendTwig\Service\TwigRendererFactory::class,
...
),
)
Add TwigRenderer service in your controller factory:
class YourControllerFactory implements FactoryInterface
{
public function __invoke(ContainerInterface $container, $requestedName, array $options = null)
{
return new YourController($twigRenderer);
}
}
and get twigRenderer in your Controller:
private $twigRenderer;
public function __construct($twigRenderer)
{
$this->twigRenderer = $twigRenderer;
}
After this get html:
function someAction(){
$viewModel = new ZendTwig\View\TwigModel(['foo'=>'bar']);
$viewModel->setTemplate('mails/order/order_in_process');
$html = $this->twigRenderer->render($viewModel);
return $html;
}
Sorry for my english!

Twig sandboxing not working for me

Playing around with twig templates (not a part of Symfony, in CodeIgniter) and it doesn't look like I can get a global sandbox to work correctly. I'm pretty sure I'm just doing something stupid, but I really can't see it.
Functions to make twig work:
public function twig_setup($configs = NULL)
{
Twig_Autoloader::register();
$env = array(
'cache' => config_item('cache_dir'),
'strict_variables' => TRUE,
'auto_reload' => TRUE,
'extension' => 'php',
'filesystem' => NULL
);
if (!is_null($configs))
{
$env = array_merge($env, $configs);
}
$this->set_extension($env['extension']);
if (is_null($env['filesystem']))
{
$env['filesystem'] = VIEWPATH;
}
else
{
$env['filesystem'] = VIEWPATH .'/'. ltrim($env['filesystem'],'/');
}
$this->set_filesystem($env['filesystem']);
// These two things should not get set to the environment
unset($env['extension']);
unset($env['filesystem']);
$this->set_environment($env);
}
public function set_sandbox($tags, $filters, $methods, $properties, $functions, $is_global = TRUE)
{
$user_policy = new Twig_Sandbox_SecurityPolicy($tags, $filters, $methods, $properties, $functions);
$user_sandbox = new Twig_Extension_Sandbox($user_policy, $is_global);
$this->twig->addExtension($user_sandbox);
}
public function disable_logic()
{
$tags = array('for', 'block', 'include');
$filters = array();
$methods = array();
$properties = array();
$functions = array('parent', 'block');
$this->set_sandbox($tags, $filters, $methods, $properties, $functions);
}
Usage:
$twig = new TwigThing();
$twig->twig_setup();
$twig->disable_logic();
Now, once I render a template, I should not be able to use something like raw or url_encode
{{ my_var|url_encode }}
That should kick out an error, or something, but it just encodes the var...wtf am I doing wrong here?

Categories