启用RLS(行级安全性)时,PostgreSQL查询未使用INDEX

启用RLS(行级安全性)时,PostgreSQL查询未使用INDEX,第1张

启用RLS(行级安全性)时,PostgreSQL查询未使用INDEX

我已经从发布之日起解决了这个问题…任何面临此问题的人,这就是我的做法:

我的解决方案是拥有一个包含“ propper”查询的 私有*

SECURITY DEFINER
“包装器”函数,以及另一个调用该 私有
函数和需要访问控制的表的 公共 函数。
*
INNER JOINS

因此,在上面的特定情况下,将是这样的:

CREATE FUNCTION private.filter_document() RETURNS SETOF public.document AS$$    SELECt * FROM public.document WHERe (        to_tsvector( 'english', content || ' ' || COALESCE(title, '')        ) @@ plainto_tsquery('english', fulltext_search_documents.search_text)    )$$LANGUAGE SQL STABLE SECURITY DEFINER;----CREATE FUNCTION public.filter_document() RETURNS SETOF public.document AS$$    SELECt filtered_d.* FROM private.filter_documents() AS filtered_d        INNER JOIN public.document AS d ON (d.id = filtered_d.id)$$LANGUAGE SQL STABLE;

由于我使用的是Postgraphile(
超级棒的 BTW!),因此我可以省去 私有
模式的自省,使“危险”功能无法访问!通过适当的安全性实现,最终用户将只能看到最终的GraphQL模式,从而将 Postgres 从外界中删除。

这工作得很漂亮! 直到最近 发布并修复 Postgres 10.3 时,才不再需要这种hack。

另一方面,我的RLS策略非常复杂,嵌套并且非常深入。它们再次运行的表也很大(总共要运行50,000多个条目才能针对RLS运行)。即使采用了超级复杂和嵌套的策略,我也设法将性能保持在合理的范围内。

使用RLS时,请记住以下几点:

  1. 建立适当的
    INDEXES
  2. 在任何地方都首选内联查询 !(即使这意味着重写N次相同的查询)
  3. 务必避免使用策略中的功能!如果您绝对必须在内部安装它们,请确保它们
    STABLE
    高且高
    COST
    (例如@mkurtz指出);或者是
    IMMUTABLE
  4. 从策略中提取查询,直接与查询一起运行,
    EXPLAIN ANALYZE
    并尝试尽可能对其进行优化

希望你们能像我一样找到有用的信息!



欢迎分享,转载请注明来源:内存溢出

原文地址:https://54852.com/zaji/5675385.html

(0)
打赏 微信扫一扫微信扫一扫 支付宝扫一扫支付宝扫一扫
上一篇 2022-12-17
下一篇2022-12-17

发表评论

登录后才能评论

评论列表(0条)

    保存