Ho il seguente schema di database:
table 'products' id category_id
e ovviamente una tabella delle categorie, solo con un ID.
I dati sembrano qualcosa del genere:
Products -------------------- | id | category_id | -------------------- | 0 | 1 | | 1 | 1 | | 2 | 1 | | 3 | 2 | | 4 | 2 | | 5 | 1 | --------------------
Vorrei select una categoria (ad esempio la Categoria 1), quindi seleziono tutte le righe da quella categoria nella mia class di repository di prodotti:
return $this ->createQueryBuilder('u') ->andWhere('u.category = :category') ->setMaxResults(1) ->setParameter('category', $category->getId()) ->getQuery() ->getSingleResult() ;
Come posso select ora un prodotto random? Inoltre: è ansible risolvere questo tramite relazioni?
Ho una relazione OneTraMany tra le entity framework; "Category" e "Product", quindi potrei anche get tutti i prodotti tramite category-> getProducts () …
Qualsiasi aiuto sarebbe davvero utile, grazie
Per prima cosa devi contare il numero totale di prodotti, quindi generare un offset random per select un prodotto random.
Questo dovrebbe farti cominciare:
$count = $this->createQueryBuilder('u') ->select('COUNT(u)') ->getQuery() ->getSingleScalarResult();
E poi puoi generare un numero random tra il tuo 1 e il numero totale di righe.
return $this->createQueryBuilder('u') ->where('u.category = :category') ->setFirstResult(rand(0, $count - 1)) ->setMaxResults(1) ->setParameter('category', $category->getId()) ->getQuery() ->getSingleResult() ;
Che si traduce in:
SELECT * FROM products WHERE category_id = ? LIMIT 1, {random offset}
Usa questa function di aiuto:
<?php use Doctrine\ORM\EntityManager; /** * Retrieve one random item of given class from ORM repository. * * @param EntityManager $em The Entity Manager instance to use * @param string $class The class name to retrieve items from * @return object */ function getRandomDoctrineItem(EntityManager $em, $class) { static $counters = []; if (!isset($counters[$class])) { $this->counters[$class] = (int) $this->manager->createQuery( 'SELECT COUNT(c) FROM '. $class .' c' )->getSingleScalarResult(); } return $em ->createQuery('SELECT c FROM ' . $class .' c ORDER BY c.id ASC') ->setMaxResults(1) ->setFirstResult(mt_rand(0, $counters[$class] - 1)) ->getSingleResult() ; }
Esempio di utilizzo:
$randomItem = getRandomDoctrineItem($em, 'Application\Entity\Post');