在 Symfony 中持久化更新的对象
Persisting Updated Objects in Symfony
我有一个 symfony 应用程序,我在其中尝试使用 setter 更新数据库中的实体。但是,当我更新实体并调用 $this->em->flush()
时,实体不会持久保存到数据库中。
这是我的服务:
<?php
namespace AppBundle\Service;
use AppBundle\Exceptions\UserNotFoundException;
use Doctrine\ORM\EntityManager;
use AppBundle\Entity\User;
/**
* Class MyService
* @package AppBundle\Service
*/
class MyService extends BaseService {
/**
* @var EntityManager
*/
protected $em;
/**
* @var User
*/
protected $user;
/**
* MyService constructor.
* @param EntityManager $em
*/
public function __construct(EntityManager $em){
$this->em = $em;
}
/**
* See if a user email exists
* @param string $email
* @return bool
*/
public function checkEmailExists($email){
$this->user = $this->em
->getRepository('AppBundle:User')
->findOneBy(['email' => $email]);
return !(is_null($this->user));
}
/**
* add credit to a users account
* @param User $user
* @param integer $credit
*/
public function addCredit(User $user, $credit){
$user->addCredit($credit);
$this->em->flush();
}
/**
* add a credit to a users account
* @param $email
* @param $credit
*/
public function addCreditByEmail($email, $credit){
if(!($this->checkEmailExists($email))){
throw new UserNotFoundException(sprintf('User with email %s not found.', $email));
}
$this->addCredit($this->user, $credit);
}
}
这是我的测试:
<?php
namespace AppBundle\Tests\Service;
use AppBundle\DataFixtures\ORM\PurchaseFixture;
use AppBundle\Entity\Vendor;
use AppBundle\Repository\OfferRepository;
use AppBundle\Tests\TestCase;
use AppBundle\Entity\Offer;
use AppBundle\DataFixtures\ORM\OfferFixture;
use AppBundle\DataFixtures\ORM\PaymentSystemFixture;
/**
* Class UserOfferServiceTest
* @package AppBundle\Tests\Service
*/
class MyServiceTest extends TestCase implements ServiceTestInterface
{
function __construct($name = null, array $data = [], $dataName = '')
{
$this->setFixtures([
'AppBundle\DataFixtures\ORM\CityFixture',
'AppBundle\DataFixtures\ORM\CountryFixture',
'AppBundle\DataFixtures\ORM\PaymentSystemFixture',
'AppBundle\DAtaFixtures\ORM\UserFixture',
]);
parent::__construct($name, $data, $dataName);
}
/**
* test the checkEmailExists() of app.vendor
*/
public function testCheckEmailExists(){
$myService = $this->getService();
$this->assertTrue($myService->checkEmailExists('user1@user1.com'));
$this->assertFalse($myService->checkEmailExists($this->fake()->safeEmail));
}
/**
* test the addCredit functionality
*/
public function testAddCredit(){
$myService = $this->getService();
$user = $this->getUser();
$this->assertEquals(0, $user->getCredit());
$toAdd = $this->fake()->numberBetween(1, 500);
$myService->addCredit($user, $toAdd);
$this->assertEquals($toAdd, $user->getCredit());
}
/**
* test the addCreditByEmail functionality
*/
public function testAddCreditByEmail(){
$myService = $this->getService();
$user = $this->getUser();
$email = $this->getUser()->getEmail();
$this->assertEquals(0, $user->getCredit());
$toAdd = $this->fake()->numberBetween(1, 500);
$myService->addCreditByEmail($email, $toAdd);
$updatedUser = $this->getEntityManager()
->getRepository('AppBundle:User')
->findOneBy(['email' => $email]);
$this->assertEquals($toAdd, $updatedUser->getCredit());
}
/**
* @return \AppBundle\Service\VendorService|object
*/
public function getService(){
$this->seedDatabase();
$this->client = $this->createClient();
return $this->client->getContainer()->get('app.admin_kiosk');
}
}
testAddCredit()
测试通过(因为我正在检查同一个对象),但 testAddCreditByEmail
失败并出现以下错误:1) AppBundle\Tests\Service\MyServiceTest::testAddCreditByEmail
Failed asserting that null matches expected 149.
我试过保留实体,刷新实体(如:$this->em->flush($user)
)都无济于事。请让我知道如何解决这个问题。
我发现了问题。
在测试用例中,我只需要通过执行 $this->getEntityManager()->refresh($user)
(在原始 $user 实体上)来刷新实体。谢谢!
我有一个 symfony 应用程序,我在其中尝试使用 setter 更新数据库中的实体。但是,当我更新实体并调用 $this->em->flush()
时,实体不会持久保存到数据库中。
这是我的服务:
<?php
namespace AppBundle\Service;
use AppBundle\Exceptions\UserNotFoundException;
use Doctrine\ORM\EntityManager;
use AppBundle\Entity\User;
/**
* Class MyService
* @package AppBundle\Service
*/
class MyService extends BaseService {
/**
* @var EntityManager
*/
protected $em;
/**
* @var User
*/
protected $user;
/**
* MyService constructor.
* @param EntityManager $em
*/
public function __construct(EntityManager $em){
$this->em = $em;
}
/**
* See if a user email exists
* @param string $email
* @return bool
*/
public function checkEmailExists($email){
$this->user = $this->em
->getRepository('AppBundle:User')
->findOneBy(['email' => $email]);
return !(is_null($this->user));
}
/**
* add credit to a users account
* @param User $user
* @param integer $credit
*/
public function addCredit(User $user, $credit){
$user->addCredit($credit);
$this->em->flush();
}
/**
* add a credit to a users account
* @param $email
* @param $credit
*/
public function addCreditByEmail($email, $credit){
if(!($this->checkEmailExists($email))){
throw new UserNotFoundException(sprintf('User with email %s not found.', $email));
}
$this->addCredit($this->user, $credit);
}
}
这是我的测试:
<?php
namespace AppBundle\Tests\Service;
use AppBundle\DataFixtures\ORM\PurchaseFixture;
use AppBundle\Entity\Vendor;
use AppBundle\Repository\OfferRepository;
use AppBundle\Tests\TestCase;
use AppBundle\Entity\Offer;
use AppBundle\DataFixtures\ORM\OfferFixture;
use AppBundle\DataFixtures\ORM\PaymentSystemFixture;
/**
* Class UserOfferServiceTest
* @package AppBundle\Tests\Service
*/
class MyServiceTest extends TestCase implements ServiceTestInterface
{
function __construct($name = null, array $data = [], $dataName = '')
{
$this->setFixtures([
'AppBundle\DataFixtures\ORM\CityFixture',
'AppBundle\DataFixtures\ORM\CountryFixture',
'AppBundle\DataFixtures\ORM\PaymentSystemFixture',
'AppBundle\DAtaFixtures\ORM\UserFixture',
]);
parent::__construct($name, $data, $dataName);
}
/**
* test the checkEmailExists() of app.vendor
*/
public function testCheckEmailExists(){
$myService = $this->getService();
$this->assertTrue($myService->checkEmailExists('user1@user1.com'));
$this->assertFalse($myService->checkEmailExists($this->fake()->safeEmail));
}
/**
* test the addCredit functionality
*/
public function testAddCredit(){
$myService = $this->getService();
$user = $this->getUser();
$this->assertEquals(0, $user->getCredit());
$toAdd = $this->fake()->numberBetween(1, 500);
$myService->addCredit($user, $toAdd);
$this->assertEquals($toAdd, $user->getCredit());
}
/**
* test the addCreditByEmail functionality
*/
public function testAddCreditByEmail(){
$myService = $this->getService();
$user = $this->getUser();
$email = $this->getUser()->getEmail();
$this->assertEquals(0, $user->getCredit());
$toAdd = $this->fake()->numberBetween(1, 500);
$myService->addCreditByEmail($email, $toAdd);
$updatedUser = $this->getEntityManager()
->getRepository('AppBundle:User')
->findOneBy(['email' => $email]);
$this->assertEquals($toAdd, $updatedUser->getCredit());
}
/**
* @return \AppBundle\Service\VendorService|object
*/
public function getService(){
$this->seedDatabase();
$this->client = $this->createClient();
return $this->client->getContainer()->get('app.admin_kiosk');
}
}
testAddCredit()
测试通过(因为我正在检查同一个对象),但 testAddCreditByEmail
失败并出现以下错误:1) AppBundle\Tests\Service\MyServiceTest::testAddCreditByEmail
Failed asserting that null matches expected 149.
我试过保留实体,刷新实体(如:$this->em->flush($user)
)都无济于事。请让我知道如何解决这个问题。
我发现了问题。
在测试用例中,我只需要通过执行 $this->getEntityManager()->refresh($user)
(在原始 $user 实体上)来刷新实体。谢谢!