Ich habe Probleme mit der Abfrageplanung für PostgreSQL 9.6. Meine Anfrage sieht folgendermaßen aus:
SET role plain_user;
SELECT properties.*
FROM properties
JOIN entries_properties
ON properties.id = entries_properties.property_id
JOIN structures
ON structures.id = entries_properties.entry_id
WHERE structures."STRUKTURBERICHT" != ''
AND properties."COMPOSITION" LIKE 'Mo%'
AND (
properties."NAME" LIKE '%VASP-ase-preopt%'
OR properties."CALCULATOR_ID" IN (7,22,25)
)
AND properties."TYPE_ID" IN (6)
Ich habe die Sicherheit auf Zeilenebene für die oben verwendeten Tabellen aktiviert.
Mit
set enable_nestloop = True
führt der Abfrageplaner Nested Loop Joining mit einer Gesamtlaufzeit von ca. 37 Sekunden aus: https://explain.depesz.com/s/59BRMit
set enable_nestloop = False
wird die Hash-Join-Methode verwendet und die Abfragezeit beträgt ca. 0,3 Sekunden: https://explain.depesz.com/s/PG8E
Ich habe es getan, VACUUM ANALYZE
bevor ich die Abfragen ausgeführt habe, aber es hat nicht geholfen.
Ich weiß, dass es keine gute Praxis ist set enable_nestloop = False
, und andere ähnliche Optionen für den Planer. Aber wie könnte ich den Planer "überzeugen", Hash-Joins zu verwenden, ohne verschachtelte Schleifen zu deaktivieren?
Das Umschreiben der Abfrage ist eine Option.
Wenn ich dieselbe Abfrage unter einer Rolle ausführe, die RLS umgeht, wird sie sehr schnell ausgeführt. Die Sicherheitsrichtlinie auf Zeilenebene sieht folgendermaßen aus:
CREATE POLICY properties_select
ON properties
FOR SELECT
USING (
(
properties.ouid = get_current_user_id()
AND properties.ur
)
OR (
properties.ogid in (select get_current_groups_id())
AND properties.gr
)
OR properties.ar
);
Irgendwelche Ideen oder Vorschläge würden sehr geschätzt.
AND properties."TYPE_ID" IN (6);
und nicht= 6;
?