Laravel 5.8 .env.testing file is not working

Viewed 19154

I created a .env.testing file with my credentials, everything the same as .env besides a different table name for the database.

I tried php artisan config:clear which deletes the cached config file in bootstrap/cache/config.php and it broke the database connection. If I re-cache the file by running php artisan config:cache the cached file is back, but without the credentials in the .env.testing file. When I rerun PHPUnit, it connects to the wrong DB, the DB name that is stored in .env not .env.testing.

Is this for real? Did the latest Laravel release break test environments?

Here is what the docs read: (found here: https://laravel.com/docs/5.8/testing)

"You are free to define other testing environment configuration values as necessary. The testing environment variables can be configured in the phpunit.xml file, but make sure to clear your configuration cache using the config:clear Artisan command before running your tests!

Also, you may create a .env.testing file in the root of your project. This file will override the .env file when running PHPUnit tests or executing Artisan commands with the --env=testing option."

UPDATE

I finally was able to override the database that is stated in the .env by adding the database override in the phpunit.xml file; the .env.testing is still not working. The docs are misleading at the least.

9 Answers

I was having this same problem with Laravel v5.6. I set up a .env.testing file with a different username, password, and database but my tests were always running in the main .env database.

It looks like you need to specify the test environment when running the config cache command. After running this command, it worked as described in the docs:

php artisan config:cache --env=testing

This is what worked for me:

In phpunit.xml I had to define <env name="APP_ENV" value="testing"/> inside the <php> block to make PhpUnit load .env.testing instead of .env


It seems like the Laravel docs are wrong and .env.testing is not hard-coded anywhere in Laravel or PhpUnit, it reads the environment file for whatever APP_ENV is specified in phpunit.xml. You could even rename this to .env.phpunit or anything else if you define it in phpunit.xml in this format: <env name="APP_ENV" value="phpunit"/>

I was having the same issue with Laravel v7. Had my hands in my hair for quite some time, but I found a workaround.

The .env.testing was a lost cause for me. I never got it to load, so I just put all the variables within phpunit.xml. To make the testing environment (php artisan test) actually load those variables, I had to do this:

First I had to set APP_ENV in phpunit.xml to force="true":

<php>
    <server name="APP_ENV" value="testing" force="true"/>
    <server name="BCRYPT_ROUNDS" value="4"/>
    <server name="CACHE_DRIVER" value="array"/>
    <server name="DB_CONNECTION" value="sqlite"/>
    <server name="DB_DATABASE" value=":memory:"/>
    <server name="MAIL_MAILER" value="array"/>
    <server name="QUEUE_CONNECTION" value="sync"/>
    <server name="SESSION_DRIVER" value="array"/>
    <server name="TELESCOPE_ENABLED" value="false"/>
</php>

Then I had to run php artisan config:clear, NOT :cache. When I ran php artisan config:cache it actually would not work. Probably because it caches the env once and never loads the new settings based on the different environment.

You need to set APP_CONFIG_CACHE variable in phpunit.xml to avoid testing and local configurations overwrites each other.

<server name="APP_ENV" value="testing"/>
<server name="APP_CONFIG_CACHE" value="cache/config-testing.php" force="true"/>

It seems that the variables defined in phpunit.xml is overriding the variables defined in .env.testing file, not the other way around as we all expect.

I recommend keeping only APP_ENV in phpunit.xml and then cloning .env.testing from current .env. And it will work as expected.

phpunit.xml

<php>
  <server name="APP_ENV" value="testing"/>
  <!-- Remove all others and define them in .env.testing -->
</php>

In order to run .env.testing in test runs only and to run .env in default behavior. You will need to execute:

./vendor/bin/phpunit.bat // For windows
./vendor/bin/phpunit // For Linux

Good luck

What does your .env.testing look like?

is your environment set to APP_ENV=testing?

When I do tests and I do not have that and only have my database details in the file it does not work but when I make a carbon copy of the original .env file and edit the env to testing mine works.

If you are likely using phpstorm,then,

go to settings of your phpstorm or press Ctrl + Alt + S.

then selectt Languages & Frameworks ->PHP ->Test Frameworks Under Test Runner tab, click Default configuration file and select (by clicking the folder icon) the path of your project's PHPUnit.xml file.

it will make all your changes in the xml file take effect.Then create the .env.testing file, create your preferred DB config variables for test and running your tests again!

When you use a local docker container, make sure you don't set the "env_file" key in docker-compose.yml to point to your .env file (or have it overwritten with an environment key). These container-level environment variables take precedence over the values loaded by Laravel (i.e. from .env.testing).

So don't do the following in your docker-compose.yml:

phpfpm:
  env_file: .env

or

phpfpm 
  environment:
    APP_ENV: "testing"

or otherwise unset them before running tests: unset DB_CONNECTION OR_OTHERS && php artisan config:cache --env=testing && php artisan test

Related