Skip to content
  • About
    • What is Symfony?
    • Community
    • News
    • Contributing
    • Support
  • Documentation
    • Symfony Docs
    • Symfony Book
    • Screencasts
    • Symfony Bundles
    • Symfony Cloud
    • Training
  • Services
    • SensioLabs Professional services to help you with Symfony
    • Platform.sh for Symfony Best platform to deploy Symfony apps
    • SymfonyInsight Automatic quality checks for your apps
    • Symfony Certification Prove your knowledge and boost your career
    • Blackfire Profile and monitor performance of your apps
  • Other
  • Blog
  • Download
sponsored by SensioLabs
  1. Home
  2. Documentation
  3. Configuration
  4. How to Master and Create new Environments
  • Documentation
  • Book
  • Reference
  • Bundles
  • Cloud

Table of Contents

  • Different Environments, different Configuration Files
  • Executing an Application in different Environments
    • Selecting the Environment for Console Commands
  • Creating a new Environment
  • Environments and the Cache Directory
  • Going further

How to Master and Create new Environments

Edit this page

Warning: You are browsing the documentation for Symfony 4.0, which is no longer maintained.

Read the updated version of this page for Symfony 6.2 (the current stable version).

How to Master and Create new Environments

Every application is the combination of code and a set of configuration that dictates how that code should function. The configuration may define the database being used, if something should be cached or how verbose logging should be.

In Symfony, the idea of "environments" is the idea that the same codebase can be run using multiple different configurations. For example, the dev environment should use configuration that makes development easy and friendly, while the prod environment should use a set of configuration optimized for speed.

Different Environments, different Configuration Files

A typical Symfony application begins with three environments: dev, prod and test. As mentioned, each environment represents a way to execute the same codebase with different configuration. It should be no surprise then that each environment loads its own individual configuration files. These different files are organized by environment:

  • for the dev environment: config/packages/dev/
  • for the prod environment: config/packages/prod/
  • for the test environment: config/packages/test/

In reality, each environment differs only somewhat from others. This means that all environments share a large base of common configurations. This configuration is put in files directly in the config/packages/ directory.

The location of these files is defined by the application's kernel:

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
// src/Kernel.php

// ...
class Kernel extends BaseKernel
{
    // ...

    protected function configureContainer(ContainerBuilder $container, LoaderInterface $loader)
    {
        // ...
        $confDir = $this->getProjectDir().'/config';

        // always load all files in /config/packages/
        $loader->load($confDir.'/packages/*'.self::CONFIG_EXTS, 'glob');

        // then, if available, load the files in the specific environment directory
        if (is_dir($confDir.'/packages/'.$this->environment)) {
            $loader->load($confDir.'/packages/'.$this->environment.'/**/*'.self::CONFIG_EXTS, 'glob');
        }

        // load a special services.(yaml/xml/php) and, if available, services_ENVIRONMENT.(yaml/xml/php) file
        $loader->load($confDir.'/services'.self::CONFIG_EXTS, 'glob');
        $loader->load($confDir.'/services_'.$this->environment.self::CONFIG_EXTS, 'glob');
    }
}

Take the framework package, installed by default, as an example:

  • Loaded in all environments, config/packages/framework.yaml configures the framework with some secret setting;
  • In the prod environment, nothing extra will be set as there is no config/packages/prod/ directory;
  • The same applies to dev, as there is no config/packages/dev/framework.yaml. There are however other packages (e.g. routing.yaml) with special dev settings;
  • At last, during the test environment, the framework's test features are enabled in config/packages/test/framework.yaml.

Executing an Application in different Environments

To execute the application in each environment, change the APP_ENV environment variable. During development, this is done in .env:

1
2
3
4
5
# .env
APP_ENV=dev

# or for test:
#APP_ENV=test

Visit the http://localhost:8000/index.php page in your web browser to see your application in the configured environment.

Tip

In production, it is recommended to configure the environment variables in your web server configuration.

Note

The given URLs assume that your web server is configured to use the public/ directory of the application as its root. Read more in Installing Symfony.

If you open the file you just visited (public/index.php), you'll see that the environment variable is passed to the kernel:

1
2
3
4
5
6
// public/index.php

// ...
$kernel = new Kernel($_SERVER['APP_ENV'] ?? 'dev', $_SERVER['APP_DEBUG'] ?? false);

// ...

You can also replace $_SERVER['APP_ENV'] ?? 'dev' by just 'dev' to always run the application in the dev environment, independent of the APP_ENV variable.

Note

The test environment is used when writing functional tests and is usually not accessed in the browser directly via a front controller.

Debug Mode

Important, but unrelated to the topic of environments is the second argument to the Kernel constructor. This specifies if the application should run in "debug mode". Regardless of the environment, a Symfony application can be run with debug mode set to true or false (respectively 1 or 0 for the APP_DEBUG variable defined in .env). This affects many things in the application, such as displaying stacktraces on error pages or if cache files are dynamically rebuilt on each request. Though not a requirement, debug mode is generally set to true for the dev and test environments and false for the prod environment.

Internally, the value of the debug mode becomes the kernel.debug parameter used inside the service container. If you look inside the application configuration file, you'll see the parameter used, for example, to turn Twig's debug mode on:

  • YAML
  • XML
  • PHP
1
2
3
# config/packages/twig.yaml
twig:
    debug: '%kernel.debug%'
1
2
3
4
5
6
7
8
9
10
11
12
<?xml version="1.0" encoding="UTF-8" ?>
<container xmlns="http://symfony.com/schema/dic/services"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:doctrine="http://symfony.com/schema/dic/doctrine"
    xsi:schemaLocation="http://symfony.com/schema/dic/services
        http://symfony.com/schema/dic/services/services-1.0.xsd
        http://symfony.com/schema/dic/twig
        http://symfony.com/schema/dic/twig/twig-1.0.xsd">

    <twig:config debug="%kernel.debug%" />

</container>
1
2
3
4
$container->loadFromExtension('twig', array(
    'debug' => '%kernel.debug%',
    // ...
));

Selecting the Environment for Console Commands

By default, Symfony commands are executed in whatever environment is defined by the APP_ENV environment variable (usually configured in your .env file).

Use the --env and --no-debug options to modify this behavior:

1
2
3
4
5
6
7
8
# 'dev' environment and debug enabled
$ php bin/console command_name

# 'prod' environment (debug is always disabled for 'prod')
$ php bin/console command_name --env=prod

# 'test' environment and debug disabled
$ php bin/console command_name --env=test --no-debug

Creating a new Environment

Since an environment is nothing more than a string that corresponds to a set of configuration, creating a new environment is quite easy.

Suppose, for example, that before deployment, you need to benchmark your application. One way to benchmark the application is to use near-production settings, but with Symfony's web_profiler enabled. This allows Symfony to record information about your application while benchmarking.

The best way to accomplish this is via a new environment called, for example, benchmark. Start by creating a new configuration directory and a configuration file:

  • YAML
  • XML
  • PHP
1
2
3
# config/packages/benchmark/web_profiler.yaml
framework:
    profiler: { only_exceptions: false }
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
<!-- config/packages/benchmark/web_profiler.xml -->
<?xml version="1.0" encoding="UTF-8" ?>
<container xmlns="http://symfony.com/schema/dic/services"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:framework="http://symfony.com/schema/dic/symfony"
    xsi:schemaLocation="http://symfony.com/schema/dic/services
        http://symfony.com/schema/dic/services/services-1.0.xsd
        http://symfony.com/schema/dic/symfony
        http://symfony.com/schema/dic/symfony/symfony-1.0.xsd">

    <framework:config>
        <framework:profiler only-exceptions="false" />
    </framework:config>

</container>
1
2
3
4
// config/packages/benchmark/web_profiler.php
$container->loadFromExtension('framework', array(
    'profiler' => array('only_exceptions' => false),
));

And... you're finished! The application now supports a new environment called benchmark.

Change the APP_ENV variable to benchmark to be able to access the new environment through your browser:

1
2
# .env
APP_ENV=benchmark

Importing configuration

Besides loading files in the Kernel, you can also import files in the configuration directly. For instance, to make sure the benchmark environment is identical to the prod environment, you might want to load all its configuration as well.

You can achieve this by using a special imports key:

1
2
3
4
5
6
7
8
# config/packages/benchmark/other.yaml
imports:
    - { resource: '../prod/' }

    # other resources are possible as well, like importing other
    # files or using globs:
    #- { resource: '/etc/myapp/some_special_config.xml' }
    #- { resource: '/etc/myapp/*.yaml' }
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
<!-- config/packages/benchmark/other.xml -->
<?xml version="1.0" encoding="UTF-8" ?>
<container xmlns="http://symfony.com/schema/dic/services"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:framework="http://symfony.com/schema/dic/symfony"
    xsi:schemaLocation="http://symfony.com/schema/dic/services
        http://symfony.com/schema/dic/services/services-1.0.xsd
        http://symfony.com/schema/dic/symfony
        http://symfony.com/schema/dic/symfony/symfony-1.0.xsd">

    <imports>
        <import resource="../prod/"/>

        <!-- other resources are possible as well, like importing other
             files or using globs:
        <import resource="/etc/myapp/some_special_config.yaml"/>
        <import resource="/etc/myapp/*.xml"/>
        -->
    </imports>

</container>
1
2
3
4
5
6
7
// config/packages/benchmark/other.php
$loader->import('../prod/');

// other resources are possible as well, like importing other
// files or using globs:
//$loader->import('/etc/myapp/some_special_config.yaml');
//$loader->import('/etc/myapp/*.php');

Environments and the Cache Directory

Symfony takes advantage of caching in many ways: the application configuration, routing configuration, Twig templates and more are cached to PHP objects stored in files on the filesystem.

By default, these cached files are largely stored in the var/cache/ directory. However, each environment caches its own set of files:

1
2
3
4
5
6
your-project/
├─ var/
│  ├─ cache/
│  │  ├─ dev/   # cache directory for the *dev* environment
│  │  └─ prod/  # cache directory for the *prod* environment
│  ├─ ...

Sometimes, when debugging, it may be helpful to inspect a cached file to understand how something is working. When doing so, remember to look in the directory of the environment you're using (most commonly dev/ while developing and debugging). While it can vary, the var/cache/dev/ directory includes the following:

appDevDebugProjectContainer.php
The cached "service container" that represents the cached application configuration.
appDevUrlGenerator.php
The PHP class generated from the routing configuration and used when generating URLs.
appDevUrlMatcher.php
The PHP class used for route matching - look here to see the compiled regular expression logic used to match incoming URLs to different routes.
twig/
This directory contains all the cached Twig templates.

Note

You can easily change the directory location and name. For more information read the article How to Override Symfony's default Directory Structure.

Going further

Read the article on How to Set external Parameters in the Service Container.

This work, including the code samples, is licensed under a Creative Commons BY-SA 3.0 license.
TOC
    Version
    We stand with Ukraine.
    Version:
    Measure & Improve Symfony Code Performance

    Measure & Improve Symfony Code Performance

    Check Code Performance in Dev, Test, Staging & Production

    Check Code Performance in Dev, Test, Staging & Production

    Symfony footer

    ↓ Our footer now uses the colors of the Ukrainian flag because Symfony stands with the people of Ukraine.

    Avatar of Stefan Oderbolz, a Symfony contributor

    Thanks Stefan Oderbolz for being a Symfony contributor

    1 commit • 3 lines changed

    View all contributors that help us make Symfony

    Become a Symfony contributor

    Be an active part of the community and contribute ideas, code and bug fixes. Both experts and newcomers are welcome.

    Learn how to contribute

    Symfony™ is a trademark of Symfony SAS. All rights reserved.

    • What is Symfony?

      • Symfony at a Glance
      • Symfony Components
      • Case Studies
      • Symfony Releases
      • Security Policy
      • Logo & Screenshots
      • Trademark & Licenses
      • symfony1 Legacy
    • Learn Symfony

      • Symfony Docs
      • Symfony Book
      • Reference
      • Bundles
      • Best Practices
      • Training
      • eLearning Platform
      • Certification
    • Screencasts

      • Learn Symfony
      • Learn PHP
      • Learn JavaScript
      • Learn Drupal
      • Learn RESTful APIs
    • Community

      • SymfonyConnect
      • Support
      • How to be Involved
      • Code of Conduct
      • Events & Meetups
      • Projects using Symfony
      • Downloads Stats
      • Contributors
      • Backers
    • Blog

      • Events & Meetups
      • A week of symfony
      • Case studies
      • Cloud
      • Community
      • Conferences
      • Diversity
      • Documentation
      • Living on the edge
      • Releases
      • Security Advisories
      • SymfonyInsight
      • Twig
      • SensioLabs
    • Services

      • SensioLabs services
      • Train developers
      • Manage your project quality
      • Improve your project performance
      • Host Symfony projects

      Deployed on

    Follow Symfony

    Search by Algolia