Slim-4 How to get twig in controllers with PHP-DI

Hello, I dont know where I was wrong in my project, when I try to use Twig in my controller that doesn’t work.
I use the following url “http://localhost:8080/bob

Thank you in advance to any one who may be able to help me :slight_smile:

This is the error :

index.php

<?php

use DI\Container;
use DI\Bridge\Slim\Bridge as SlimAppFactory;

require __DIR__ . '/../vendor/autoload.php';

$container = new Container;

$settings = require __DIR__ . '/../app/settings.php';
$settings($container);

$app = SlimAppFactory::create($container);

$views = require __DIR__ . '/../app/views.php';
$views($app);

$middleware = require __DIR__ . '/../app/middleware.php';
$middleware($app);

$routes = require __DIR__ . '/../app/routes.php';
$routes($app);

$app->run();

settings.php

<?php

use \Psr\Container\ContainerInterface;

return function (ContainerInterface $container){
    $container->set('settings', function (){
        return [
            'displayErrorDetails' => true,
            'LogErrorDetails' => true,
            'logErrors' => true,
            'views' => [
                'path' => 'ressources/views',
                'settings' => ['cache'=> false],
            ]
        ];
    });
};

middleware.php

<?php

use Slim\App;

return function (App $app){
    $setting = $app->getContainer()->get('settings');
    $app->addErrorMiddleware(
        $setting['displayErrorDetails'],
        $setting['LogErrorDetails'],
        $setting['logErrors']
    );
};

routes.php

<?php

use Slim\App;
use Psr\Http\Message\ResponseInterface as Response;
use Psr\Http\Message\ServerRequestInterface as Request;
use App\Controllers\WelcomeController;

return function (App $app){
    $app->get('/', [WelcomeController::class, 'index']);
    $app->get('/{name}', [WelcomeController::class, 'show']);
};

views.php

<?php

use Slim\App;
use Slim\Views\Twig;
use Slim\Views\TwigMiddleware;
use Twig\Loader\FilesystemLoader;

return function (App $app) {
    
    $container = $app->getContainer();

    $container->set('view', function() use ($container) {
        $settings = $container->get('settings')['views'];
        $loader = new FilesystemLoader($settings['path']);
        return new Twig($loader, $settings['settings']);
    });

    $container->set('viewMiddleware', function() use ($app, $container) {
        return new TwigMiddleware($container->get('view'), $app->getRouteCollector()->getRouteParser()); 
    });
};

WelcomeController.php

<?php

namespace App\Controllers;

use Slim\Views\Twig as View;
use Psr\Http\Message\ResponseInterface as Response;
use Psr\Http\Message\ServerRequestInterface as Request;

class WelcomeController
{
    protected $views;

    public function __construct(Views $views)
    {
        return $this->view = $views;
    }

    public function index(Request $request, Response $response){
        $response->getBody()->write("Hello world!");
        return $response;
    }
    
    public function show(Request $request, Response $response, $name){
        return $view->render($response, 'auth\home.twig', ['User' => $name]);
    }
}

public function __construct(Views $views)

There is a typo. It should be View, like the alias use Slim\Views\Twig as View;

1 Like

Ho yeah totaly, miss this one, after multiple tests but I have the folllowing error after this correction.

Entry “App\Controllers\WelcomeController” cannot be resolved: Entry “Slim\Views\Twig” cannot be resolved: Entry “Twig\Loader\LoaderInterface” cannot be resolved: the class is not instantiable Full definition: Object ( class = #NOT INSTANTIABLE# Twig\Loader\LoaderInterface lazy = false ) Full definition: Object ( class = Slim\Views\Twig lazy = false __construct( $loader = get(Twig\Loader\LoaderInterface) $settings = (default value) array ( ) ) ) Full definition: Object ( class = App\Controllers\WelcomeController lazy = false __construct( $views = get(Slim\Views\Twig) ) )

Then you have to add a container definiton for Twig::class, e.g.

use Slim\Views\Twig;
use Psr\Container\ContainerInterface;
// ...

return [
    // ...
    Twig::class => function (ContainerInterface $container) {
        $settings = $container->get('settings')['twig'];
        $twig = Twig::create($settings['paths'], $settings['options']);

        return $twig;
    },

    // ...   
];