DirectoryTree / LdapRecord-Discussions

A place to ask questions, get help, or share what you've built with LdapRecord.
4 stars 1 forks source link

Unit tests without Laravel #14

Closed tadasvu closed 3 years ago

tadasvu commented 3 years ago

is there a way to write tests using DirectoryEmulator::setup('default'); without having laravel framework

Error : Call to undefined function LdapRecord\Laravel\Testing\app()
 C:\localwww\vendor\directorytree\ldaprecord-laravel\src\Testing\DirectoryEmulator.php:25
 C:\localwww\vendor\illuminate\support\helpers.php:433
 C:\localwww\vendor\directorytree\ldaprecord-laravel\src\Testing\DirectoryEmulator.php:26
 C:\localwww\tests\StatusPage\CreateAdGroup\Service\CreateAdGroupLdapServiceTest.php:27

trying to write some tests for: https://stackoverflow.com/questions/64597786/php-unit-for-ldaprecord

stevebauman commented 3 years ago

Hi @tadasvu,

Without using the Laravel framework, you'll have to do some mocking for sure. Before I help you with some implementation, have you used the Mockery framework before when writing tests?

tadasvu commented 3 years ago

thanks for reply, no haven't delt with Mockery before, currently reading docs.

not quite still sure how to do it, i was trying to Mock the Connection and except that some query methods where called on it:

class LdapServiceTest extends TestCase {

    public function findAllOrganizationalUnitsTest() {
        $connectionMock = Mockery::mock(Connection::class);
        $connectionMock->shouldHaveReceived('in');
        $connectionMock->shouldHaveReceived('listing');
        ...

        $test = new LdapService($connectionMock);
        $test->findAllOrganizationalUnits();
    }
}
stevebauman commented 3 years ago

From the code you've posted, it looks like you're using some kind of intermediate service class to handle retrieving objects from your LDAP server and attempting to mock the underlying LdapRecord\Connection that is being called.

However, if you're wanting to test real data being returned from a mock connection, you will instead have to mock the LdapRecord\Ldap class, which is the underlying source of all data returns. Keep in mind if you go down this route, you will have to mock real returned data, as an LDAP connection would return.

Here's an example test -- however this is almost pseudo-code, so you will have to modify things and probably fix something I may have missed below:

use LdapRecord\Ldap;
use LdapRecord\Container;
use LdapRecord\Connection;
use LdapRecord\Models\Entry;

$mockLdap = Mockery::mock(Ldap::class);

$connection = new Connection($config = [], $mockLdap);

// Replace the "default" connection with the connection
// containing a mock LDAP instance:
Container::addConnection($mock);

$mockLdapRecords = [
    [
        "distinguishedname" => "cn=John Doe,dc=local,dc=com",
        "cn" => ["John Doe"],
        "sn" => ["Doe"],
        "givenname" => ["John"],
        "memberof" => ["cn=Office,dc=local,dc=com"]
    ]
];

$mockLdap
    ->shouldReceive('setOptions')->once()
    ->shouldReceive('setOption')->once()
    ->shouldReceive('bind')->once()
    ->shouldReceive('search')->once()->andReturn($mockLdapRecords);

$objects = Entry::get();

Hope this helps!

stevebauman commented 3 years ago

Closing due to inactivity.