4

I have a custom extension with model with structure like this in database:

+----------------------------------+
|entity_id | customer_id | balance |
+----------------------------------+
|     1    |      3      | 7100000 |
|     2    |      5      | 1250000 |
+----------------------------------+

I usually use my model in __construct function in controller like this:

public function __construct(
.... ,
/Namespace/Module/Model/CreditFactory $credit
... ,
){
  $this->credit = $credit;
}

and i can use to store and retrieve data from my model collection easily like this:

//retrieve Data
$credit = $this->credit->create()->load('1');
$anotherCredit = $this->credit->create()->getCollection()
    ->addFieldToFilter('customer_id','5')->getFirstItem();
$balance = $credit->getBalance();
$anotherBalance = $anotherCredit->getBalance();
//Store Data
$amount = 1000;
$endCreditBalance = $balance - $amount;
$credit->SetBalance(endCreditBalance);
$credit->save();
$endAnotherCreditBalance = $balance + $amount;
$anotherBalance->SetBalance(endAnotherCreditBalance);
$anotherBalance->save();

I tried to create unit test to compared the saved value with the value i want to store like this:

protected function setUp()
{
 $objectManager = new \Magento\Framework\TestFramework\Unit\Helper\ObjectManager($this);
 $this->customerCredit = $objectManager->getObject(\Namespace\Module\Model\CreditFactory::class);      
}

public function testSend()
{
 $credit = $this->credit->create()->load('1');
 $anotherCredit = $this->credit->create()->load('2');

 $balance = $credit->getBalance();
 $anotherBalance = $anotherCredit->getBalance(); 
 $amount = 250;
 $endCreditBalance = $balance - $amount;
 $credit->SetBalance(endCreditBalance);
 $credit->save();
 $endAnotherCreditBalance = $balance + $amount;
 $anotherBalance->SetBalance(endAnotherCreditBalance);
 $anotherBalance->save();
 $result = array(
          'credit_balance' => $credit->getBalance(),
          'another_credit_balance' => $anotherCredit->getBalance()
 );
 $expected = array(
          'credit_balance' => $endCreditBalance,
          'another_credit_balance' => $endAnotherCreditBalance
 );
 $this->assertEquals($expected, $result);
}

but i always got an error like this:

Error: Call to a member function load() on null

and i don't know if the rest of the code will work just fine or not

  • 1
    If you want to test database interaction you should take a look at creating an integration test instead. Also you are trying to load particular credits (ids 1 and 2) which you would need to add as a fixture first before being able to load them in a test. – Kristof at Fooman May 7 '18 at 10:59
  • @KristofatFooman can you give an example for that one? – mileven May 7 '18 at 11:00
  • 2
    I wouldn't be able to provide an example but this article gives a good overview of what is involved integer-net.com/integration-tests-with-magento-2 – Kristof at Fooman May 7 '18 at 11:05
  • You want to run Unit test or integration test? @mileven – Keyur Shah May 7 '18 at 13:23
0

What you are trying to do is actually an integration test and not an unit test. Magento makes an clear distinct in the types of test. With unit tests, all the dependencies of the class you are trying to test are replace with mocks, where all functions return null by default. It is also impossible to access the database as there is no active connection.

With integration tests however you get access to the actual objects and you can access the database.

In your code that is what you actually are trying to do: Testing if the integration between your database and your code is correct.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.