126

What is the best way to get the root app directory from inside the controller? Is it possible to get it outside of the controller?

Now I get it by passing it (from parameters) to the service as an argument, like this:

services:

    sr_processor:
        class: Pro\Processor
        arguments: [%kernel.root_dir%]

Is there a better, simpler way to get this information in Symfony2?

Imanali Mamadiev
  • 2,604
  • 2
  • 15
  • 23
Dawid Ohia
  • 16,129
  • 24
  • 81
  • 95

5 Answers5

221

UPDATE 2018-10-21:

As of this week, getRootDir() was deprecated. Please use getProjectDir() instead, as suggested in the comment section by Muzaraf Ali.

—-

Use this:

$this->get('kernel')->getRootDir();

And if you want the web root:

$this->get('kernel')->getRootDir() . '/../web' . $this->getRequest()->getBasePath();

this will work from controller action method...

EDIT: As for the services, I think the way you did it is as clean as possible, although I would pass complete kernel service as an argument... but this will also do the trick...

Jovan Perovic
  • 19,846
  • 5
  • 44
  • 85
  • 3
    +1 but not accurate for symfony2. Use instead: `$this->get('kernel')->getRootDir() . '/../..' . $this->getRequest()->getBasePath();` – Sebastian Aug 26 '13 at 06:12
  • Are you sure? I have successfully used this code in `2.0` -> `2.2`. Was directory structure changed in `2.3` or `master`? – Jovan Perovic Aug 26 '13 at 09:43
  • 36
    This solution is only right for controllers. Here the issue is about services. Anyway, why passing the *whole* container just to get a variable? It's far better to pass just %kernel.root_dir% – Massimiliano Arione Sep 10 '13 at 09:06
  • 2
    Massimiliano is right, and as an addition, i use `$this->container->getParameter('kernel.cache_dir')` in controllers instead of the solution you provided – lackovic10 Sep 11 '14 at 20:17
  • I agree, while this solution was acceptable in that time I feel like there are way more better solutions presently... – Jovan Perovic Feb 03 '15 at 08:20
  • @JovanPerovic ...such as... ? – xDaizu Apr 18 '16 at 09:51
  • 2
    This was more on topic of your service having `container` injected :) If you follow best practices, injecting the `container` should be avoided at all costs. As for the solution of getting `web` directory, I still use the one I provided above ;) – Jovan Perovic Apr 18 '16 at 10:19
  • why not just using `__DIR__` then – the_nuts Dec 02 '16 at 22:05
  • the `__DIR__ ` represents the current directory of class, so that would not work... – Jovan Perovic Dec 04 '16 at 13:20
  • 4
    As of Symfony 3.3 and onwards use `%kernel.project_dir%/web/` instead of `%kernel.root_dir%/../web/` – Muzafar Ali Aug 21 '17 at 02:53
16

In Symfony 3.3 you can use

$projectRoot = $this->get('kernel')->getProjectDir();

to get the web/project root.

Chris
  • 799
  • 6
  • 15
8

If you are using this path to access parts of the projects which are not code (for example an upload directory, or a SQLite database) then it might be better to turn the path into a parameter, like this:

parameters:
    database_path: '%kernel.root_dir%/../var/sqlite3.db'

This parameter can be injected everywhere you need it, so you don't have to mess around with paths in your code any more. Also, the parameter can be overridden at deployment time. Finally, every maintaining programmer will have a better idea what you are using it for.

Update: Fixed kernel.root_dir constant usage.

Artur Stępień
  • 466
  • 3
  • 18
MauganRa
  • 494
  • 6
  • 8
7

You can also use regular expression in addition to this:

    $directoryPath = $this->container->getParameter('kernel.root_dir') . '/../web/bundles/yourbundle/';
    $directoryPath = preg_replace("/app..../i", "", $directoryPath);
    echo $directoryPath;
Tragaknight
  • 413
  • 4
  • 10
3

Since Symfony 3.3 you can use binding, like

services:
_defaults:
    autowire: true      
    autoconfigure: true
    bind:
        $kernelProjectDir: '%kernel.project_dir%'

After that you can use parameter $kernelProjectDir in any controller OR service. Just like

class SomeControllerOrService
{
    public function someAction(...., $kernelProjectDir)
    {
          .....
Andrew Zhilin
  • 1,654
  • 16
  • 11