Chciałbym uzyskać wartość za pomocą następującego kodu SQL przy użyciu elokwentnego ORM.
- SQL
SELECT COUNT(*) FROM
(SELECT * FROM abc GROUP BY col1) AS a;
Następnie rozważałem następujące kwestie.
- Kod
$sql = Abc::from('abc AS a')->groupBy('col1')->toSql();
$num = Abc::from(\DB::raw($sql))->count();
print $num;
Szukam lepszego rozwiązania.
Proszę powiedz mi najprostsze rozwiązanie.
belongsToMany
podselekcja, musisz dodaćgetQuery()
dwukrotnie =>$sub->getQuery()->getQuery()
toSql
. Przeczytaj o PDO php.net/manual/en/book.pdo.php i zobacz wynik swojego$query->toSql()
$sub
zapytanie jest elokwentnym konstruktorem , nadal potrzebujesz->getQuery()
części, w przeciwnym razie pojawi się błąd, ponieważ ta metoda jest wskazana na typQuery\Builder
klasy.Dodano Laravel v5.6.12 (14.03.2018)
fromSub()
ifromRaw()
metody do konstruktora zapytań (# 23476) .Przyjęta odpowiedź jest poprawna, ale można ją uprościć do:
Powyższy fragment kodu generuje następujący kod SQL:
źródło
Rozwiązanie @JarekTkaczyk jest dokładnie tym, czego szukałem. Jedyne, czego mi brakuje, to jak to zrobić, gdy używasz
DB::table()
zapytań. W tym przypadku tak to robię:Specjalna uwaga jak wykonać
mergeBindings
bez użyciagetQuery()
metodyźródło
DB::raw()
wykonało pracę za mnieOd laravel 5.5 istnieje dedykowana metoda dla podzapytań i możesz jej używać w następujący sposób:
lub
źródło
Call to undefined method subSelect()
wygląda na to,subSelect
że nie istnieje.selectSub
. Zaktualizowałem teraz moją odpowiedź.Lubię robić coś takiego:
Nie jest zbyt elegancki, ale jest prosty.
źródło
Nie mogłem zrobić twojego kodu, aby wykonać żądane zapytanie, AS jest aliasem tylko dla tabeli
abc
, a nie dla tabeli pochodnej. Laravel Query Builder nie obsługuje niejawnie pochodnych aliasów tabel, najprawdopodobniej do tego potrzebny jest DB :: raw.Najprostsze rozwiązanie, jakie mogłem wymyślić, jest prawie identyczne z twoim, jednak generuje zapytanie, o które prosiłeś:
Utworzone zapytanie to
źródło
Poprawny sposób opisany w tej odpowiedzi: https://stackoverflow.com/a/52772444/2519714 Najpopularniejsza obecnie odpowiedź nie jest do końca poprawna.
W ten sposób https://stackoverflow.com/a/24838367/2519714 nie jest poprawny w niektórych przypadkach, takich jak: sub select ma gdzie powiązania, następnie dołącza tabelę do sub select, a następnie inne gdzie są dodawane do wszystkich zapytań. Na przykład zapytanie:
select * from (select * from t1 where col1 = ?) join t2 on col1 = col2 and col3 = ? where t2.col4 = ?
Aby wykonać to zapytanie, napiszesz kod taki jak:Podczas wykonywania tego zapytania jego metoda
$query->getBindings()
zwróci powiązania w nieprawidłowej kolejności, jak['val3', 'val1', 'val4']
w tym przypadku, zamiast poprawnej['val1', 'val3', 'val4']
dla surowego sql opisanego powyżej.Jeszcze raz poprawny sposób, aby to zrobić:
Również powiązania zostaną automatycznie i poprawnie połączone z nowym zapytaniem.
źródło