ENCSPožádat o přístup ke kódu

Notebook / Esej

Oprávnění před modelem

Říjen 2026

Firemní znalostní báze má dokumenty pro všechny a dokumenty jen pro pár lidí: interní poznámky, čísla, smlouvy. Odpovědi píše jazykový model. Kam patří řízení přístupu?

Lákavá odpověď zní „do promptu“. Je špatná.

Tři místa, kde může být

  1. V promptu. Vyhledat široce, modelu říct, kdo se ptá a co smí vidět, a požádat ho, ať zbytek neprozradí.
  2. Až po vyhledání. Vzít nejlepší výsledky a pak vyřadit ty, které uživatel vidět nesmí.
  3. V dotazu. Každý databázový dotaz, který čte kusy dokumentů, připojí dokument a uplatní přístupovou podmínku uživatele.

Proč ne v promptu

Pokyn není kontrola. Dokument, který obsahuje vlastní pokyny, otázka položená oklikou nebo další verze modelu — každá z těch věcí může z „prosím, neprozrazuj“ udělat únik. Zdrženlivost modelu se nedá otestovat do jistoty.

Selhává to i opačným směrem, a to mě překvapilo víc. Když systémový prompt mluvil o důvěrnosti, model začal odmítat i lidi, kteří nárok měli — včetně majitele firmy — a nedělal to konzistentně. Štítky v dokumentech typu „interní“ bral jako příkazy. Model, kterého požádáte, ať hlídá přístup, ho bude hlídat nepředvídatelně.

Proč ne až po vyhledání

Filtrování nejlepších výsledků je potichu zmenší. Když je šest z osmi nejlepších kusů zakázaných, uživatel dostane dva slabé kusy a horší odpověď, aniž by věděl proč. Řazení přitom proběhlo nad dokumenty, které vidět nesmí.

V dotazu

Přístup je tedy podmínka v SQL: každý vidí dokumenty sdílené s celou firmou, své vlastní dokumenty a dokumenty přidělené jemu nebo jeho roli. Výjimka neexistuje, ani pro majitele firmy — osobní položka někoho zůstane jeho jen tehdy, když nikdo není vyjmutý. Tu podmínku sestavuje jediná funkce, je otestovaná nad skutečným Postgresem skutečnými dotazy a prochází jí každý dotaz, který čte kusy dokumentů — vektorové vyhledávání, fulltextové vyhledávání a jedno místo, na které se snadno zapomene.

Místo, na které se snadno zapomene

Hybridní vyhledávání rozhoduje, která slova z otázky jsou „vzácná“, podle toho, v kolika kusech se vyskytují. Kdyby se ten počet bral z celého korpusu, výsledky uživatele by se měnily podle dokumentů, které nesmí vidět. Položíte otázku, všimnete si, že nějaké slovo je bráno jako běžné, a víte, že se objevuje v mnoha dokumentech, ke kterým nemáte přístup. Malý únik, ale skutečný. Proto se i počty omezují stejnou podmínkou.

Totéž platí pro opravu překlepů. Když je slovo v otázce napsané špatně, opraví se na nejbližší slovo, které se v dokumentech vyskytuje. Kdyby se ten slovník skládal z celého korpusu, klidně by vaši otázku „opravil“ na jméno člověka z dokumentu, který číst nesmíte. Proto se slovník skládá jen z toho, co vidět smíte.

Důsledek pro prompt

Protože kontext už odpovídá oprávněním, může prompt říkat opak první možnosti: všechno, co jsi dostal, tento člověk vidět smí — odpověz úplně a štítky typu „interní“ ber jako popis, ne jako příkaz. Tím zmizel jak únik, tak nevyzpytatelná odmítnutí.

Obě rozhodnutí spolu souvisejí. Prompt „odpověz úplně“ je bezpečný jen proto, že filtr je před ním; přesunout filtr dál a nezměnit prompt by byla chyba. Ta vazba je zapsaná přímo u kódu, protože kdo za půl roku změní jedno, musí vědět o druhém.

Co to stojí

  • Jedno spojení tabulek navíc v každém vyhledávacím dotazu. S indexem je to v tomhle měřítku levné; zadarmo to není.
  • Každý nový způsob čtení kusů musí použít společnou přístupovou podmínku. To je kázeň, a proto ji hlídají testy, ne paměť.

Pravidlo, které jsem si z toho vzal: model nikdy nesmí být součástí, která rozhoduje, kdo co smí vědět. Ve chvíli, kdy se text dostane k modelu, už musí být rozhodnuto.