0025_public_bucket_allows_listing silently returns zero findings when splinter.public_buckets is unset — undocumented transaction-local contract

オープン
#181 コメント 1 件 リアクション 0 件 担当者 0 名 GitHub で見る

メンテナーはふだん 1 日以内に返信

@sidgaikwad がすでに取り組んでいます。

2026年9月15日 から。

  • #190 @sidgaikwad による — オープン

評価

難易度
4/5
見積もり時間
3〜5日
初心者へのやさしさ
45/100
issue の種類
バグ
明瞭さ
おおむね明確
活発さ
静か
技術スタック
postgresql, sql

調査の方向性

コンパイル済みの splinter.sql にある 0025_public_bucket_allows_listing query とそのプリアンブルから始め、splinter.json の分離された query フィールドと setup フィールドを比較します。README と CI psql --single-transaction の呼び出しを確認し、トランザクションローカルな GUC の契約を文書化します。設定が存在しない場合に、何も知らせずに正常な結果を生成できないこと、また setup がスキップされた場合と正当な空のバケットリストの両方を扱う動作になっていることを完了条件とします。

索引モデルが issue の本文から書いたものです。

説明

Summary

Since #170 ("chore: 0025 query_to_xml workaround", merged 2026-07-02), 0025_public_bucket_allows_listing no longer reads storage.buckets itself. The view now reads a GUC:

coalesce(
    nullif(pg_catalog.current_setting('splinter.public_buckets', true), '')::pg_catalog.jsonb,
    '[]'::pg_catalog.jsonb
)

and the storage.buckets read moved into a preamble DO block that exists only in the compiled splinter.sql, which populates the GUC transaction-locally:

perform pg_catalog.set_config('splinter.public_buckets', buckets, true);

Consequence: any consumer that executes the lint query without running that preamble in the same transaction gets zero findings — indistinguishable from a genuinely clean result. The lint fails open. #170 itself had to switch this repo's CI runner to psql --single-transaction to keep the GUC visible, which illustrates the hazard: the contract is real, but it lives only in the compiled artifact and CI invocation, and the README documents the pgrst.db_schemas dependency while splinter.public_buckets is undocumented.

Real-world impact (hosted advisor path)

On our hosted project, 0025 reported two findings (user-avatars, workspace-branding) through 2026-06-10. Sometime after #170, the findings disappeared from the hosted security-advisor results while both flagged conditions still hold — we re-verified by executing the lint's own predicate manually with the bucket list supplied: both broad PERMISSIVE SELECT policies still exist and both findings reproduce exactly. We can't inspect the hosted advisor runner, but the observable symptom is precisely what a runner that doesn't execute the preamble in-transaction would produce, and no other 0025-touching change exists in the window.

For an advisor whose job is to flag data exposure, "input not supplied" being indistinguishable from "no exposure found" seems worth closing: consumers (including us) read the absence of findings as a clean bill.

The same hazard is now formalized in the manifest

The versioned splinter.json manifest publishes per-lint query fields with a separate setup field. A consumer that runs a lint's query without executing setup in the same transaction reproduces the same silent zero for 0025.

Prior art

This is the same failure class as the unset-pgrst.db_schemas case (supabase/cli#5868, fixed by #168 coalescing to 'public'). The difference: 0025 has no sane inline default available — an empty bucket list doesn't degrade the lint, it disables it silently.

Suggestions
  1. Document the splinter.public_buckets contract in the README alongside pgrst.db_schemas, including the transaction-local requirement.
  2. Prefer fail-loud over fail-open: when the setting is absent (as opposed to a legitimately empty []), either raise, or emit a sentinel "not evaluated" row, so runners that skip the preamble become visible instead of silently green.
  3. Alternatively, restore a self-contained fallback: read storage.buckets directly when the GUC is absent and the storage schema exists (the pre-#170 behavior), using whatever construction avoids the original query_to_xml problem that motivated #170.

Happy to provide the manual reproduction steps or test against a fix.

主要言語
PLpgSQL
スター
284
フォーク
110
PR マージ指標
30日以内にマージされた PR はありません

環境構築

はじめの一歩

  1. issue を最後まで読み、次にプロジェクトのコントリビューションガイドを読みます。
  2. 着手することを issue にコメントします — 二人が同じ作業をするのを防げます。
  3. リポジトリをフォークし、ブランチを切って変更します。
  4. issue 番号を参照したプルリクエストを送ります。

supabase/splinter のほかの issue

supabase/splinter の issue をすべて見る

似ている issue

Databases の issue をもっと見る

新しい issue をメールで受け取る

初心者向けの GitHub issue を短くまとめたダイジェスト。