8

I have a problem running tests in my laravel app. My app is splitted into separated namespaces. Laravel App namespace is in app directory and it's App/ namespace. I have additional namespace in src directory.

My TestCase look like that:

<?php

namespace Tests\Unit;

use Illuminate\Foundation\Testing\DatabaseTransactions;
use PHPUnit\Framework\TestCase;
use SmoothCode\Sample\Domain\User\User;
use SmoothCode\Sample\Domain\User\UserRepository;
use SmoothCode\Sample\Domain\User\ValueObject\ConfirmationCode;
use SmoothCode\Sample\Shared\ValueObjects\Email;
use SmoothCode\Sample\Shared\ValueObjects\Id;
use SmoothCode\Sample\Shared\ValueObjects\Password;
use Tests\CreatesApplication;


class UserDomainTest extends TestCase
{
    use CreatesApplication;

    protected UserRepository $userRepository;

    public function testUserCreation() {
        $user = User::create(
            Id::generate(),
            'Jan',
            'Kowalski',
            new Email('test@test.com'),
            '123123123',
            new Password('Pass123!'),
            new \DateTimeImmutable(),
            ConfirmationCode::generate()
        );
//
//        $this->assertInstanceOf(User::class, $user);
    }

    protected function setUp(): void
    {
        parent::setUp();
    }


}

After running vendor/bin/phpunit I'm getting following error:

1) Tests\Unit\UserDomainTest::testUserCreation
RuntimeException: A facade root has not been set.

/home/jakub/Development/Projects/streetboss-server/vendor/laravel/framework/src/Illuminate/Support/Facades/Facade.php:258
/home/jakub/Development/Projects/streetboss-server/src/Sample/Shared/ValueObjects/Password.php:15
/home/jakub/Development/Projects/streetboss-server/tests/Unit/UserDomainTest.php:29

From that i know that the problem lies in src/Sample/Shared/ValueObjects/Password.php:15

which looks like:

<?php

namespace SmoothCode\Sample\Shared\ValueObjects;

use Illuminate\Support\Facades\Hash;
use Webmozart\Assert\Assert;

class Password {
    protected string $hash;

    public function __construct($plainPassword)
    {
        Assert::minLength($plainPassword, 6);

        $this->hash = Hash::make($plainPassword);
    }

    public function hashedPassword()
    {
        return $this->hash;
    }


}
I was trying to run:
php artisan config:cache
php artisan cache:clear
php artisan config:clear
composer dump-autoload

But I'm still getting this error.

Jakub Rusinowicz
  • 376
  • 1
  • 2
  • 12
  • use Illuminate\Support\Facades\DB; – Mehran Zamani Feb 02 '20 at 07:58
  • Where should I use this? In my Test Case? – Jakub Rusinowicz Feb 02 '20 at 12:15
  • Mehran Zamani, for clarity, class `SmoothCode\Sample\Domain\User\User` is not Model class and it is not operating on database – Jakub Rusinowicz Feb 02 '20 at 12:19
  • which line is UserDomainTest.php:29 ? You should explain more details about your code. take a look at [this](https://stackoverflow.com/questions/56456595/laravel-5-8-a-facade-root-has-not-been-set-after-homestead-restart). – Mehran Zamani Feb 05 '20 at 10:27
  • UserDomainTest.php:29 is this line: ``` ConfirmationCode::generate() ``` But what i've discoverd is that even when i replace whole code in `testUserCreation()` with : ``` Hash::make('test'); ``` or ``` bcrypt('test'); ``` I'm getting this error. So calling Facade in my tests is causing this error. – Jakub Rusinowicz Feb 05 '20 at 23:10
  • please provide ConfirmationCode in your question – Mehran Zamani Feb 06 '20 at 06:41

2 Answers2

9

Okay, I have found a solution for this error. For anyone who would have same problem:

My UserDomainTest was extending TestCase from namespace:

use PHPUnit\Framework\TestCase;

when I've changed to:

use Illuminate\Foundation\Testing\TestCase;

everything works like a charm.

Jakub Rusinowicz
  • 376
  • 1
  • 2
  • 12
  • 1
    How come the examples in the official docs extend `PHPUnit\Framework\TestCase` and not `Illuminate\Foundation\Testing\TestCase`? – Bogdan Ghervan Sep 29 '20 at 18:29
  • 3
    can not change into `use Illuminate\Foundation\Testing\TestCase;` because is not implement `createApplication` method – ha3an Nov 07 '21 at 08:49
  • Both of these are wrong; you need to extend `Tests\TestCase` as shown in [the documentation](https://laravel.com/docs/10.x/database-testing) for database testing. – miken32 Jul 19 '23 at 20:04
6

The Jakub's answer don't work for me, so I will explain what I do.

I have the file App/BusinessRules/Admin/Tests/EnvTest.php. Even using anyone of this 2 namespaces the fail occurs.

So in my EnvTest I extend the tests/TestCase.php file from the namespace:

use Tests\TestsCase
Caio Denadai
  • 61
  • 1
  • 1
  • 4
    If you define your own `protected function setUp(): void` then don't forget to call `parent::setUp();` too or you'll still get the same error about `A facade root has not been set`. – Morpork Dec 11 '20 at 06:34
  • 1
    Thank you! Adding `parent::setUp();` at the top of the protected function fixed the error for me. – kaeland Jun 09 '21 at 23:55