2012-02-21 15 views
9

voglio salvare uno dei miei un'entità oggetti nella sessione, ma come sto facendo così, sto ottenendo i seguenti due errori:Symfony2 entità serializzare oggetto alla sessione

Eccezione: Symfony \ Bundle \ FrameworkBundle \ DataCollector \ RequestDataCollector :: Serialize() deve restituire una stringa o NULL

e

ErrorException: Avviso: di serie ize(): "id" restituito come membro variabile da __sleep() ma non esiste in /var/www/clients/client71/web256/web/_dev_fd/kkupon/vendor/symfony/src/Symfony/Component/HttpKernel /DataCollector/DataCollector.php linea 29

il mio codice va in questo modo:

$offer = $this->getEntityManager()->getRepository('KkuponMainBundle:Offer')->find($offer_id); 
$request->getSession()->set('offer', $offer); 

Come potrei farlo bene?

Grazie.

UPDATE Con l'aiuto di Rowgm ho potuto risolvere questo problema impostando le proprietà protette invece che private. L'unico problema che ho è dopo che legge l'entità dalla sessione che EntityManager non conosce a tale proposito e se aggiungo l'oggetto (dalla sessione) a un altro oggetto (esiste una relazione OneToMany tra di loro), non lo farà lavoro.

<?php 
$offer = $this->get('session')->get('offer'); 
$coupon = new Coupon(); 
$coupon->setOffer($offer); 
$this->em->persist($coupon); 
$this->em->flush(); 

Questo genera un errore, perché coupon ha una proprietà oggetto che secondo l'EntityManager non è nel database (in realtà è nel DB, ho messo alla sessione dal DB).

<?php 
$offer = $this->get('session')->get('offer'); 
echo $this->em->getUnitOfWork()->isInIdentityMap($offer) ? "yes":"no"; //result: no 

Una soluzione può essere: $offer = $this->em->merge($offer);

Ma questo doesnt sembrano essere il migliore. Mi piacerebbe che il mio EntityManager percepisca gli oggetti entità memorizzati nella sessione senza dirlo ogni volta. Qualche idea?

risposta

14

è possibile serializzare qualsiasi entità impostando tutte le loro proprietà e le relazioni da privato a protetto.

Si potrebbe avere un problema comune con symfony2, anche se sono state impostate tutte le proprietà su protetto: è necessario rigenerare i proxy di quelle entità che sono state modificate. Per fare ciò, basta cancellare la cache.Per dev ambiente:

app/console cache:clear

Funziona anche se "contiene molti oggetti estranei e persino ArrayCollections di entità straniere", come lei ha detto.

+0

Grazie, ha aiutato molto. –

+0

Per favore, se puoi, rispondi alla parte di aggiornamento della mia domanda. –

+0

Pensaci: se si memorizza tutta quell'entità, si memorizzerà un oggetto Big nei dati della sessione. Per il tuo ambiente di sviluppo, non è un problema. Ma se hai molti utenti, è uno spreco di risorse. La soluzione è così semplice: memorizza l'id dell'oggetto e usa il metodo find() del repository per recuperare l'oggetto. Alla fine, è la stessa cosa. –

6

Le entità di serializzazione non sono consigliate, come si può vedere nello Doctrine-documentation. È necessario implementare lo Serializable-interface e serializzare/deserializzare manualmente i dati dell'entità.

+0

serializzazione mia entità sarebbe problematico, in quanto contiene molti oggetti estranei e persino ArrayCollections delle imprese estere. Qualche idea migliore rispetto alla sola memorizzazione dell'ID e al recupero dell'oggetto dal database ogni volta che ne ho bisogno? –

+0

Come puoi vedere dalla tua eccezione, quando lo metti in una sessione verrà serializzato, questo è ciò che sta causando l'errore. Ma come dici tu, a causa della complessità del tuo oggetto, dovresti probabilmente archiviare l'id e recuperare nuovamente l'oggetto dal database. Forse usare un qualche tipo di cache degli oggetti potrebbe funzionare, ma non ne sono sicuro. – dbrumann

+1

Grazie, sto solo memorizzando l'id. –

2

È possibile escludere i campi unnesseary da overridding __sleep metodo:

public function __sleep() { 

    // these are field names to be serialized, others will be excluded 
    // but note that you have to fill other field values by your own 
    return array('id', 'username', 'password', 'salt'); 
} 
Problemi correlati