3

I am creating a framework on top on Symfony components. http://symfony.com/doc/2.7/create_framework/index.html

I want to access the container in my controller, but I am not sure how to do it the OOP way.

I am presently accessing it via global but I am sure there would be a better way to do the same. Please refer my code blocks:

#services.yml file
services:
  calendar.model.leapyear:
    class: Calendar\Model\LeapYear

Front Controller File

<?php

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

use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\Routing;
use Symfony\Component\HttpKernel;

$request = Request::createFromGlobals();
$routes = include __DIR__ . '/../src/routes.php';
$container = include __DIR__ . '/../src/app/Container.php';

$context = new Routing\RequestContext();
$matcher = new Routing\Matcher\UrlMatcher($routes, $context);

$controllerResolver = new HttpKernel\Controller\ControllerResolver();
$argumentResolver = new HttpKernel\Controller\ArgumentResolver();

$framework = new Framework($matcher, $controllerResolver, $argumentResolver);
$response = $framework->handle($request);

$response->send();

LeapYearController File

<?php


namespace Calendar\Controller;

use Controller;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;

class LeapYearController extends Controller
{

    protected $model;

    public function indexAction(Request $request, $year)
    {
        $this->model = $this->container->get('calendar.model.leapyear');
        if ($this->model->isLeapYear($year)) {
            return new Response('Yep, this is a leap year!');
        }

        return new Response('Nope, this is not a leap year.');
    }
}

Base controller

<?php

namespace Controller;

use Symfony\Component\DependencyInjection\ContainerAware;

class Controller extends ContainerAware
{
    protected $container;

    public function __construct()
    {
        global $container;
        $this->container = $container;
    }
}

1 Answers1

5

Your base class should look like this:

<?php

namespace Controller;

use Symfony\Component\DependencyInjection\ContainerAwareInterface;
use Symfony\Component\DependencyInjection\ContainerAwareTrait;

class Controller implements ContainerAwareInterface
{
    use ContainerAwareTrait;

    public function getContainer()
    {
        return $this->container;
    }
}

Then in your Controllers, you can call either $this->container as provided by ContainerAwareTrait or $this->getContainer() as provided by your base controller.

Rendy Eko Prastiyo
  • 1,068
  • 7
  • 16
  • Thank you for your answer. I also wanted to add Service and Dao for this controller. how would I be able to get the container in service and model to load dependencies. – Kumar Saurabh Sinha Feb 11 '17 at 23:43
  • 1
    You have to change the way your `Framework` serve the request-response. This tutorial will solve your problems: [The DependencyInjection Component](http://symfony.com/doc/2.7/create_framework/dependency_injection.html) – Rendy Eko Prastiyo Feb 12 '17 at 00:04