I want you to know how to write a service and let the container handle it for you.
This post comes from a very cool evening with Jacopo Romei and David Funaro, two friends of mine, developers too.
A container?
Yes, a container: Symfony2 implements a dependency injection container able to load any service you need ( a service can be the DB connection, a Twitter WS, a mailer ) in the way you prefer.
Ever thought the factories.yml of symfony 1.4 was evil? The DIC basically does
the same thing. But, the right way.
Why does a container is that great?
Because it lets you decide the behaviour of the framework.
Ever thought the sfActions were crap and wanted to build your own C of the MVC
with symfony 1.4 in a simple way? A pain in the mess :)
With the DIC you are able to configure Symfony’s architecture.
Building your own service
I’ll show a really simple example.
To let the container manage your extension you simply need:
- a bundle
- an extension, able to load the cascading configuration of your service
- your service class(es)
If you are familiar with the Sf2 sandbox you know it comes bundled with a simple
application bundle, HelloBundle, which exposes the route:
1
| |
and renders a template saying hello to the name:

We will add the mood of our application to that page ;–)
First of all we need to tell Sf2 that we want to enable our service:
1
| |
Then we have to build an extension able to load the configuration for our service.
Inside src/Application/HelloBundle we create a directory DependencyInjection
and create the HelloExtension class:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 | |
If you take a closer look to the serviceLoad method
1 2 3 4 5 6 7 8 9 | |
you’ll notice that it accepts, as parameters, the configuration ( yes, the YML
configuration, the one we left untouched with the ~ symbol ) and the container.
Why does our extension calls the serviceLoad method? That comes from the YAML
configuration done before:
1
| |
Remember? If we wrote hello.obama, we should have defined a obamaLoad method
in our extension.
Then it creates an XMLFileLoader and loads the configuration of our services,
which lies in the Resources/config folder, an XML file called hello.xml.
Then, it sets a parameter, for the service: it sets hello.service.mood; true
if we have defined it in the configuration, false otherwise ( our situation ).
Ok, things will become clear watching at the hello.xml, located in
src/Application/HelloBundle/Resources/config/hello.xml:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | |
As you see, it defines a service ( hello_service ), which istantiates the class
%hello.service.class%, a parameter defined some lines above, with the argument
%hello.service.mood%.
Yes, that parameter comes from the HelloExtension!
Remember?
1 2 3 | |
So, here we are passing to the XML the parameter %hello.service.mood% with
false value.
Ok, we are close to the end, what’s missing there? Oh, our service!
In the XML we stated that the class of the hello_service service should be
Application\HelloBundle\Service\Hello, so we only need to create it under
src/Application/HelloBundle/Service/Hello.php:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | |
as you see, the mood is passed by the DIC in the constructor*, and we have
defined a __toString returning 2 different strings based on the value of the mood.
Ok, we’re done.
Open the dummy front controller bundled with the sandbox and pass a second argument to the template:
1 2 3 4 5 6 7 8 | |
then edit the twig template:
File /src/source/downloads/code/[src/Application/HelloBundle/Resource/views/Hello/index.twig] could not be found
So, let’s see it in action:

Now we can edit the service configuration:
1 2 | |
and see what happens:

“Oh shit”… A bit lost? Here’s a recap!
Ok, let’s try to explain things again!
In the configuration of you application ( app/config/config_dev.yml ) you add
to your application a new service ( hello.service ), with no parameters.
Then, when in the application you call the service hello_service, the DIC
looks for an extension able to load the service, which is HelloExtension.
It runs the method serviceLoad, which looks to an XML describing the service
passing it the parameters you defined in the YAML configuration ( none ).
Then the DIC instantiate the service class with the parameters mapped in the XML
( $mood = false ).
The second time, we have defined $mood as true, so the container instantiates
the class with a really simple:
1 2 3 | |
the result is that you get an instance of your service configured as you want.