sql >> Database >  >> RDS >> PostgreSQL

ActiveRecord:hoe vind je ouders van wie ALLE kinderen aan een aandoening voldoen?

Gebruik arel kan je behoorlijk ver brengen. Het lastige is hoe je niet je hele zoekopdracht schrijft met arel 's eigen query-syntaxis?

Hier is een truc:bij het maken van uw zoekopdracht met where , als je arel . gebruikt voorwaarden, krijg je een aantal extra methoden gratis. U kunt bijvoorbeeld de subquery die u daar heeft volgen met .exists.not , waarmee u een (NOT ( EXISTS (subquery))) Gooi dat in where van de ouders -clausule en je bent klaar.

De vraag is, hoe verwijs je naar de betrokken tabellen? Daar heb je Arel voor nodig. Je zou gebruik Arel's where met zijn lelijke voorwaarden zoals a.eq b . Maar waarom? Omdat het een gelijkheidsvoorwaarde is, kunt u in plaats daarvan de voorwaarden van Rails gebruiken! U kunt verwijzen naar de tabel die u opvraagt ​​met een hash-sleutel, maar voor de andere tabel (in de buitenste query) kunt u de arel_table gebruiken . Bekijk dit:

parents = Parent.arel_table
Parent.where(
  Child.where(other_parent_id: nil, parent_id: parents[:id]).exists.not
)

Je kunt het Arel-gebruik zelfs verminderen door een beetje gebruik te maken van strings en te vertrouwen op het feit dat je subquery's als parameters kunt invoeren in Rails' where . Het heeft niet veel nut, maar het dwingt je niet om te veel in Arel's methoden te graven, dus je kunt die truc of andere SQL-operators gebruiken die een subquery nemen (zijn er zelfs andere?):

parents = Parent.arel_table
Parent.where('NOT EXISTS (?)',
  Child.where(parent_id: parents[:id], other_parent_id: nil)
)

De twee belangrijkste punten hier zijn:

  • U kunt subquery's maken op dezelfde manier als u gewend bent om gewone query's te maken, verwijzend naar de tabel van de buitenste query met Arel. Het is misschien niet eens een echte tafel, het kan een alias zijn! Gekke dingen.
  • U kunt subquery's gebruiken als parameters voor where . van Rails methode prima.


  1. Oracle SQL-groep op if

  2. Hoe verbinding maken met een MySQL-database via ODBC vanuit de Qt-toepassing?

  3. De PostgreSQL gem pq voor Heroku . installeren

  4. lastInsertId werkt niet in Postgresql