17 Reaktionen zu “Random Record Extbase Repository – Türchen 4”

Kommentare abonnieren (RSS) oder TrackBack URL

Sehr fein

Alex Kellner am 04. Dezember 2011 um 14:49

sehr cool…
hab das derzeit rein über PHP gemacht, da ich keine besser Lösung wusst… aber das ist natürlich viel performater… 🙂

Thomas Allmer am 05. Dezember 2011 um 15:01

Danke für den Hinweis – ist zwar nicht ganz so wie ORDER BY RAND(), aber für viele Einsatzzwecke tut es das auch 🙂

Max am 12. Dezember 2011 um 14:04

also wenn man mehrere Random Einträge braucht ist ganze nicht mehr wirklich einsetzbar… da man hier pro Eintrag eine Abfrage starten müsste…

Thomas Allmer am 13. Dezember 2011 um 01:17

public function findRandom($limit = 1) {
$rows = $this->createQuery()->execute()->count();

$row_number = mt_rand(0, max(0, ($rows – 1)));

/* need to be shown more then one random value */
$temp_row_numer = $row_number – $limit;
if($temp_row_numer createQuery()->setOffset($temp_row_numer)->setLimit((int)$limit)->execute();
}

bown am 19. April 2012 um 11:08


/**
* Get a random object
* @return Tx_Extbase_Persistence_QueryResultInterface|array
*/
public function findRandom($limit = 1) {
$rows = $this->createQuery()->execute()->count();

$row_number = mt_rand(0, max(0, ($rows - 1)));

/* ne to be shown more then one random value */
$temp_row_numer = $row_number - $limit;
if($temp_row_numer createQuery()->setOffset($temp_row_numer)->setLimit((int)$limit)->execute();
}

bown am 19. April 2012 um 11:09

kann kein code posten.

if($temp_row_numer [kleiner] 0){
$temp_row_numer = 1;
}

bown am 19. April 2012 um 11:12

Es gibt durchaus eine Möglichkeit, ein Query zu manipulieren, um ein ORDER BY RAND() hineinzuschmuggeln:

// Query erstellen, kann auch ganz normal angereichert/geändert werden:
$query = $this->createQuery();
$query->setLimit(10);

// DB-Backend laden:
$backend = t3lib_div::makeInstance(‚Tx_Extbase_Persistence_Storage_Typo3DbBackend‘);
// Teile des Query extrahieren:
$parameters = array();
$statementParts = $backend->parseQuery($query, $parameters);
// Teile des Query ändern:
$statementParts[‚orderings‘][] = ‚RAND()‘;

// Wieder zusammensetzen:
$statement = $backend->buildQuery($statementParts, $parameters);
$query->statement($statement, $parameters);

// evtl. nur die „Rohdaten extrahieren:
//$query->getQuerySettings()->setReturnRawQueryResult(true);

$result = $query->execute();

Sollte funktionieren.

Max am 19. April 2012 um 12:14

Bin gerade zufällig drauf gestoßen, super Tipp!
Danke hierfür

Patrick am 10. Dezember 2012 um 17:33

Der Ansatz von Max funktioniert super, auch zur Manupulation anderer Query-Eigenschaften.
Ab 6.2 leider nicht mehr! Hat jemand schon dahingehend wietergearbeitet?

pvweb am 26. März 2014 um 14:28

Hallo Patrik,

das Vorgehen funktioniert auch unter TYPO3 6.2, wenn du Namespaces verwendest:

// Query erstellen, kann auch ganz normal angereichert/geändert werden:
$query = $this->createQuery();
$query->setLimit(2);

// DB-Backend laden:
$backend = TYPO3CMSCoreUtilityGeneralUtility::makeInstance(‚TYPO3CMSExtbasePersistenceGenericStorageTypo3DbBackend‘);

// Teile des Query extrahieren:
$parameters = array();
$statementParts = $backend->parseQuery($query, $parameters);

// Zufällige Sortierung verwenden – davor ggf. andere Sortierungen löschen!
unset($statementParts[‚orderings‘]);
$statementParts[‚orderings‘][] = ‚RAND()‘;

// Wieder zusammensetzen:
$statement = $backend->buildQuery($statementParts, $parameters);
$query->statement($statement, $parameters);

$result = $query->execute();

Man kann übrigens auch einen festen Wert innerhalb von RAND() angeben, um den Zufall quasi festzuschreiben. Ich habe das an verschiedenen Stellen verwendet, um Ergebnisse seitenweise darzustellen. Da will man ja auf Seite 2 keine Ergebnisse von Seite 1 sehen. Man kann eine Zufallszahl generieren und der Session speichern. Damit kann man Zufall erzeugen und dem Benutzer trotzdem immer wieder die selben zufälligen Ergebnisse präsentieren.

Max am 27. März 2014 um 11:35

Hallo Max, vielen Dank für Deine Antwort. Das neue Typo3DbBackend wurde komplett neu entwickelt. Die Methode buildQuery ist rausgefallen und die Methode parseQuery wurde in einen neuen QueryParser verschoben und als protected erklärt. Dieser Ansatz funktioniert daher leider nicht mehr. Oder liege ich da komplett falsch?

pvweb am 28. März 2014 um 09:19

Ich habe es mit 6.2 getestet und es hat geklappt – allerdings noch mit der Beta. Hat sich das im Release geändert?

Max am 28. März 2014 um 11:25

Ja. Das Typo3DbBackend wurde komplett erneuert. Ich benötige diese Funktionalität unbedingt und hoffe, hier (http://www.typo3forum.net/forum/extbase-extension-development/74336-migration-extbase-erweiterung-typo3-6-2-a.html) etwas präsentieren zu können….

pvweb am 28. März 2014 um 11:35

Stimmt, sehe ich gerade. Ja, das ist nicht wirklich praktisch. Ich denke, hier sollte man ein Ticket einrichten, weil die Funktion eigentlich echt praktisch ist. Ich finde eh, dass die starke Kapselung von Queries im Framework problematisch ist, weil es immer wieder Fälle geben wird, in den es einfach hilfreich ist, Queries zu ändern. Insofern ist 6.2 meines Erachtens in diesem Fall auf dem falschen Weg! Schade.

Max am 28. März 2014 um 13:57

Ich stand vor dem gleichen Problem in TYPO3 6.2 und bin zu folgender Lösung gekommen http://www.derhansen.de/2014/04/typo3-62-random-sorting-of-queryresults.html

Torben Hansen am 21. April 2014 um 15:03

Leider ist die von Hansen präsentierte Lösung suboptimal, sobald man tausende Einträge in der Datenbank hat.

Eine Lösung wäre, mit Standard-SQL eine Random-UID-Liste zu holen und diese dann per Extbase-Query zu holen. Das führt zwar die ORM-Philosophie ad absurdum, würde aber klappen.

Max am 12. Mai 2014 um 15:40

Kategorien

Archiv