2016-06-28 80 views
3

我有一個簡單的實體類:Symfony的序列化主義實體

<?php 
namespace AppBundle\Entity; 

use Doctrine\ORM\Mapping as ORM; 
use Doctrine\Common\Collections\ArrayCollection; 


/** 
* @ORM\Entity(repositoryClass="CompanyUserRepository") 
* @ORM\Table(name="company_users") 
*/ 
class CompanyUser 
{ 
/** 
* @ORM\Column(type="integer") 
* @ORM\Id 
* @ORM\GeneratedValue(strategy="AUTO") 
*/ 
private $id; 

/** 
* @ORM\Column(type="string", length=100) 
*/ 
private $firstName; 

/** 
* @ORM\Column(type="string", length=100) 
*/ 
private $lastName ; 

/** 
* @ORM\OneToMany(targetEntity="Score", mappedBy="user") 
*/ 
private $scores; 
/** 
* Constructor 
*/ 
public function __construct() 
{ 
    $this->scores = new ArrayCollection(); 
} 

/** 
* Get id 
* 
* @return integer 
*/ 
public function getId() 
{ 
    return $this->id; 
} 

/** 
* Set firstName 
* 
* @param string $firstName 
* 
* @return CompanyUser 
*/ 
public function setFirstName($firstName) 
{ 
    $this->firstName = $firstName; 

    return $this; 
} 

/** 
* Get firstName 
* 
* @return string 
*/ 
public function getFirstName() 
{ 
    return $this->firstName; 
} 

/** 
* Set lastName 
* 
* @param string $lastName 
* 
* @return CompanyUser 
*/ 
public function setLastName($lastName) 
{ 
    $this->lastName = $lastName; 

    return $this; 
} 

/** 
* Get lastName 
* 
* @return string 
*/ 
public function getLastName() 
{ 
    return $this->lastName; 
} 

/** 
* Add score 
* 
* @param \AppBundle\Entity\Score $score 
* 
* @return CompanyUser 
*/ 
public function addScore(\AppBundle\Entity\Score $score) 
{ 
    $this->scores[] = $score; 

    return $this; 
} 

/** 
* Remove score 
* 
* @param \AppBundle\Entity\Score $score 
*/ 
public function removeScore(\AppBundle\Entity\Score $score) 
{ 
    $this->scores->removeElement($score); 
} 

/** 
* Get scores 
* 
* @return \Doctrine\Common\Collections\Collection 
*/ 
public function getScores() 
{ 
    return $this->scores; 
} 

}

問題是當我試圖讓所有的用戶和JSON序列化他們:

/** 
* @Route("/api/getUsers", name="getUsers") 
*/ 
public function getUsers(Request $request){ 
    $users = $this->getDoctrine() 
    ->getRepository('AppBundle:CompanyUser') 
    ->findAll(); 

    $serializer = $this->get('serializer'); 
    $data = $serializer->serialize($users, 'json'); 

    return new Response($users); 
} 

我得到已檢測到循環參考(配置的限制:1)。 當我刪除getScores getter時,一切正常。我只需要獲得id,firstName和lastName。有沒有辦法不序列化其他對象?

+1

對可能序列化的對象實現\ Serializable接口是一種很好的做法。考慮到這一點。 – Muriano

回答

4

那麼,在使用關係序列化實體時,處理circular references是很常見的事情。

解決方案沒有。 1:實現可序列化的接口並使關係屬性不是序列化/反序列化(大多數情況下,這是一個有效的解決方案)

解決方案編號2:此規範化器的setCircularReferenceLimit()方法設置在將其考慮爲循環引用之前將序列化相同對象的次數。它的默認值是1,因此,呼籲serialize()方法之前,這樣做:

public function getUsers(Request $request){ 
    $users = $this->getDoctrine() 
    ->getRepository('AppBundle:CompanyUser') 
    ->findAll(); 

    $serializer = $this->get('serializer'); 
    $serializer->setCircularReferenceLimit(2); // Change this with a proper value for your case 
    $data = $serializer->serialize($users, 'json'); 

    return new Response($data); 
} 

**** ****更新

正如@Derek說,在他的評論中,解決方案沒有。 2在某些Symfony版本中可能無效。然後,你可以嘗試這種方式設置一個處理循環引用:

$encoder = new JsonEncoder(); 
$normalizer = new ObjectNormalizer(); 

$normalizer->setCircularReferenceHandler(function ($object) { 
    return $object->getName(); // Change this to a valid method of your object 
}); 

$serializer = new Serializer(array($normalizer), array($encoder)); 
var_dump($serializer->serialize($org, 'json'));  

這應該回到你的實體值,而不是遍歷關係。

+0

您的解決方案沒有。 2不起作用。 setCircularReferenceLimit()方法不屬於Serializer類,而屬於AbstractNormalizer。你的代碼(至少在Symfony 2.8中)會引發一個致命的錯誤。由於getNormalizer()方法是私有的,因此我無法找到從序列化程序服務獲取此規範化程序的方法... – Derek

+0

getNormalizer()方法是私有的,因此無法使用它(並且它需要2個參數) 。看來標準器只能在將其注入到串行器之前進行定製... – Derek

+0

對於最後的評論@Derek,我很匆忙。我已經更新了我的回覆,並添加了處理此錯誤的新方法。 – Muriano