Przejdź do głównej zawartości

Zarządzanie sekretami — 1Password/doppler + scoped tokens + audyt co kwartał

Q22 · Operacje i higiena Jak zarządzasz kluczami API / sekretami w MCP i hookach?

Maksymalna odpowiedź: “Menedżer sekretów (1Password CLI, Doppler) + scoped tokens, audyt co kwartał.”

Dlaczego to ważne: Agenci, którzy mogą czytać Twój filesystem, mogą czytać Twoje sekrety. Zawęź to, co mogą znaleźć.

Model zagrożeń wokół sekretów fundamentalnie zmienił się w momencie, gdy agenci LLM dostali generyczny dostęp do shella, filesystemu i HTTP. W 2025 najgorszym scenariuszem dla przeciekniętego .env był nieuważny git push do publicznego repo. W 2026 najgorszym scenariuszem jest agent, który czyta Twój filesystem w każdym kroku, połyka każdy plaintext OPENAI_API_KEY=sk-…, jakiego się dogrzebie, a potem — co coraz częstsze — cytuje go z powrotem w stack trace, debug logu lub w odpowiedzi na prompt-injection ze skażonej strony albo zatrutego outputu narzędzia MCP. Raport GitGuardian “State of Secrets Sprawl” zalogował 28,6 mln nowych sekretów wyciekniętych do publicznych commitów GitHub w 2025, wzrost o 34% rok do roku, a autorzy raportu wprost przypisują to przyspieszenie workflowom agentycznym, które kopiują lokalny kontekst do transkryptów, issue na GitHubie i screenshotów na Discordzie bez redakcji. Badacze z API Stronghold odkryli równolegle ponad 21 tysięcy publicznie wystawionych runtime’ów agentycznych (OpenClaw, stacki w stylu AutoGPT, deploymenty langgraph), które wyciekały klucze API, tokeny OAuth i pełne historie rozmów do otwartego internetu przez trywialne błędy konfiguracyjne — agentowy odpowiednik publicznych S3 bucketów z 2017.

Mechanizm jest banalny i nieunikniony na każdym nowoczesnym stacku. Twój agent ma read na filesystem. Czyta .env. Cokolwiek jest w .env, jest teraz w jego working context, a stamtąd może wylądować w: transkrypcie, który podsyłasz koledze, breadcrumb w Sentry, debugowej sesji z console.log, kopipaste na Slacku, stack trace, który model dołącza do swojej self-analysis, odpowiedzi tool call wysłanej do zewnętrznego serwera MCP, któremu do końca nie ufasz, lub — to świeży hazard 2026 — payloadzie prompt-injection zaszytym w stronie WWW lub PDF, który prosi agenta, by wyeksfiltrował zmienne środowiskowe. Żadna z tych ścieżek nie wymaga złych intencji, żadna nie wymaga jailbreaka modelu i żadna nie jest blokowana przez Twojego providera. Jedyną trwałą obroną jest nigdy nie mieć plaintextowego sekretu na dysku w ogóle, a do tego upewnić się, że każdy token, który agent może sobie wyciągnąć, jest na tyle wąsko scopowany, że jego kompromitacja nie jest katastrofalna.

Właśnie dlatego Q22 siedzi w sekcji Operacje i higiena, i dlatego maksymalna odpowiedź wymaga trzech konkretów razem — menedżera sekretów, scoped tokenów i kwartalnego audytu. Każdy z osobna jest niepełny. Menedżer bez scoped tokenów wciąż daje agentowi master key, gdy ten startuje. Scoped tokeny bez menedżera wciąż leakują plaintextem przez .env. Oba bez audytu degradują się w ciągu dwóch kwartałów do “skonfigurowaliśmy to w Q1 i nigdy nie patrzyliśmy”, co funkcjonalnie jest tym samym, co brak setupu.

Setup max-score na Q22 to żaden produkcyjny sekret w plaintext nigdzie na Twojej maszynie poza zaszyfrowanym vaultem menedżera. Nie w ~/.zshrc, nie w .env, nie w .env.local, nie w .envrc, nie w scratchpadzie w Notes.app, nie w claude/settings.json. Menedżer sekretów (1Password CLI, Doppler lub odpowiednik typu HashiCorp Vault albo AWS Secrets Manager) jest jedynym źródłem prawdy, a każdy proces, który potrzebuje sekretu — Twój dev server, Twój serwer MCP, sesja Claude Code, background agent Codex CLI, runner GitHub Actions — pobiera go przez menedżera w momencie startu. Plaintext istnieje tylko w environment procesu na czas jego życia, nigdy na dysku.

Każdy token, do którego agent może sięgnąć, jest zawężony do minimum potrzebnych uprawnień i lifetime’u. Twój GitHub token to fine-grained PAT scopowany na jedno repo i jeden zestaw uprawnień (np. contents:write + pull-requests:write na developer-toolkit), nie klasyczny PAT z repo scope na całe Twoje konto. Twój Cloudflare token to scopowany API token na jedną strefę z jednym zestawem permissionów, nie globalny API key. Twój klucz OpenAI / Anthropic to project-scoped key z miesięcznym hard cap, nie workspace-admin key. Każdy agent lub serwer MCP dostaje swój własny token — nie współdzielony — żeby w razie wycieku transkryptu wiadomo było dokładnie, który token rotować, a blast radius był mały.

Robisz audyt co kwartał, który faktycznie jest w kalendarzu. Co trzy miesiące otwierasz menedżera, listujesz każdy aktywny sekret i odpowiadasz na dwa pytania per wpis: “czy to jeszcze w użyciu?” i “czy scope jest dalej właściwy?”. Rotujesz wszystko starsze niż 90 dni, co nie ma mocnego powodu, by przetrwać. Przeglądasz last-used dla każdego scoped tokena i odwołujesz wszystko nieaktywne >30 dni. Skanujesz repo i dotfiles w poszukiwaniu plaintextu, który prześliznął się między audytami (gitleaks detect, trufflehog filesystem . lub op inject --dry-run na każdym config file). Logujesz audyt gdzieś (secrets-audit-YYYY-Q*.md w osobistym repo, wydarzenie w kalendarzu z checklistą), żeby kolejny audyt miał historię do porównania.

Cokolwiek mniej — “mam vault w 1Password, ale moje serwery MCP wciąż czytają .env”, “rotuję klucze, gdy coś się dzieje niedobrego”, “zaudytuję, jak będę miał czas” — to odpowiedź na 1 lub 2 punkty.

1Password CLI (op run --env-file) — injection sekretów

Dział zatytułowany „1Password CLI (op run --env-file) — injection sekretów”

CLI 1Password (op) zyskało first-class secret references w 2023 i w 2026 są one najczęściej używanym wzorcem dla workflowów agent + MCP. Zamiast plaintextowego .env trzymasz .env z referencjami op:// i odpalasz komendę przez op run:

Okno terminala
# .env (komitowalny — bez sekretów w środku)
OPENAI_API_KEY=op://Personal/openai/credential
ANTHROPIC_API_KEY=op://Personal/anthropic/credential
GITHUB_TOKEN=op://Work/github-developertoolkit/token
CLOUDFLARE_API_TOKEN=op://Work/cloudflare-dt-prod/token
# Odpal cokolwiek — npm, MCP server, claude code — przez op run
op run --env-file=.env -- npm run dev
op run --env-file=.env -- claude
op run --env-file=.env -- npx @modelcontextprotocol/server-github

op run rezolwuje referencje w momencie startu procesu, wstrzykuje plaintext wyłącznie do environmentu child procesu i nigdy nie zapisuje ich na dysk. Child widzi normalne zmienne środowiskowe; model działający wewnątrz child widzi to samo; ale plik na dysku jest bezpieczny do komitowania, dzielenia na screenshocie albo wysłania koledze. Od 2026 istnieje też otwarty request — już zaimplementowany w buildach nightly — żeby Claude Code rezolwował referencje op:// bezpośrednio w bloku env w settings.json, eliminując całkowicie potrzebę wrapper skryptów. Dokumentacja deweloperska 1Password publikuje secret references guide, który obejmuje zagnieżdżone pola, sekcje i to, jak referować kody TOTP, klucze SSH i connect tokeny tą samą składnią.

Dla serwerów MCP konwencja to opakowanie komendy startującej w configu klienta MCP:

{
"mcpServers": {
"github": {
"command": "op",
"args": ["run", "--env-file=/Users/you/.config/mcp/github.env", "--",
"npx", "-y", "@modelcontextprotocol/server-github"]
}
}
}

Serwer MCP dostaje GITHUB_TOKEN w swoim environment przy starcie, model nigdy nie widzi wartości, a jedynym artefaktem na dysku są referencje op:// — które nic nie wyciekną, jeśli plik zostanie wystawiony.

Doppler to najmocniejsza scentralizowana alternatywa dla zespołów, które chcą wyciągnąć sekrety z osobistych vaultów do dzielonego, audytowanego control plane. CLI Dopplera trzyma ten sam wzorzec “opakuj komendę”, ale ciągnie z hostowanego, role-based-access projektu:

Okno terminala
doppler run --project developer-toolkit --config dev -- npm run dev
doppler run --project ai-tools --config dev -- npx @modelcontextprotocol/server-github
doppler run --project developer-toolkit --config dev -- claude

Argument sprzedażowy Dopplera vs 1Password to centralizacja: sekrety żyją w jednym projekcie per aplikacja, ze środowiskami (dev, staging, prod), role-based access dla zespołu i pełnym audit logiem kto co i kiedy pobierał. Blog Dopplera opublikował writeup o LLM security w 2026, który wprost adresuje wycieki sekretów między agentami i promptami — warto przeczytać, zanim podpiszesz się pod wzorcem, bo broni tezy, że model nigdy nie powinien widzieć wartości sekretu, tylko referencję. Doppler ma też first-class integrację z Cloudflare Workers: doppler secrets download --no-file --format env | wrangler secret put … to kanoniczny sposób trzymania sekretów wrangler w synchronizacji ze źródłem prawdy w Dopplerze, zamiast wrangler secret put z pamięci.

Trade-off to operacyjny overhead: Doppler jest hostowaną zależnością, kosztuje powyżej free tier, a Twój dev workflow ma teraz dodatkowy failure mode (Doppler padnie → agent nie wystartuje). Dla solo developera z subskrypcją 1Password w portfelu, op run jest zwykle właściwym wyborem. Dla zespołu 3+ osób, gdzie dyscyplina rotacji liczy się bardziej niż osobista wygoda, wygrywa Doppler.

Cloud-native (Vault, AWS Secrets Manager, Cloudflare Secrets Store)

Dział zatytułowany „Cloud-native (Vault, AWS Secrets Manager, Cloudflare Secrets Store)”

Dla server-side sekretów — czyli wszystkiego, co serwer MCP lub background agent pobiera w produkcji — kanoniczny wzorzec 2026 to trzymać sekrety w cloud manager natywnym dla Twojej platformy i nigdy nie synchronizować plaintextu na lokalny dysk. Na Cloudflare Workers (runtime tego repo) ścieżka to wrangler secret put POLAR_ACCESS_TOKEN, a potem czytanie env.POLAR_ACCESS_TOKEN w kodzie; plaintext istnieje tylko w zaszyfrowanym store Cloudflare i runtime workera — Twoja lokalna maszyna nigdy go nie trzyma. Na AWS odpowiednikiem jest Secrets Manager plus IAM scopowane na konkretny ARN sekretu. Na HashiCorp Vault dynamiczne credentials do baz danych z TTL-ami pozwalają wydać agentowi 30-minutowy token DB, który sam się odwołuje — to złoty standard dla każdego agenta, który potrzebuje read/write do bazy.

Writeup z fast.io “AI Agent Secrets Management: Best Practices for 2026” broni tezy, że prawdziwą obroną dla workloadów agentycznych są dynamiczne, krótko żyjące credentials (à la Vault), a nie tylko lepsza higiena statycznych sekretów. Rozumowanie: agent, który dostaje świeży 15-minutowy token z Vault na początku każdego zadania, może leakować ten token swobodnie do transkryptów — zanim ktokolwiek przeczyta transkrypt, token jest martwy. To mocniejsza gwarancja niż “token w Twoim vaulcie jest zaszyfrowany”, bo eliminuje attack window całkowicie.

Scoped tokens (GitHub fine-grained PAT, Cloudflare scoped API tokens)

Dział zatytułowany „Scoped tokens (GitHub fine-grained PAT, Cloudflare scoped API tokens)”

Druga połowa odpowiedzi to to, że sam sekret powinien być mały. Wyciekniony fine-grained GitHub PAT scopowany na contents:write w jednym repo to umiarkowanie złe; wyciekniony klasyczny PAT z pełnym repo scope na całym koncie to katastrofa. Domyślny stan 2026 dla każdego tokena w rękach agenta powinien być: jeden konkretny zasób, jedno konkretne uprawnienie, jedna konkretna data wygaśnięcia.

  • GitHub: fine-grained PATs (Settings → Developer settings → Personal access tokens → Fine-grained tokens). Scopuj na dokładnie te repo, których agent lub serwer MCP dotyka, wybierz minimalne uprawnienia (contents, pull-requests, issues w razie potrzeby) i ustaw wygaśnięcie 30 lub 90 dni, nie “no expiration”. GitHub App tokens są jeszcze lepsze dla setupów zespołowych, bo są auto-rotowane.
  • Cloudflare: scoped API tokens, nie globalny API key. Każdy token dostaje konkretne account/zone permissions (Workers Scripts: Edit, Account Settings: Read, etc.) i jest ograniczony do zasobów, których naprawdę potrzebuje. Globalny API key nie powinien w 2026 istnieć na żadnej maszynie developerskiej — to relikt API z 2018.
  • OpenAI / Anthropic: project-scoped API keys z miesięcznymi limitami użycia. Każdy projekt (np. developer-toolkit-prod, cli-tools-personal) dostaje swój klucz, więc spend jest przypisywalny per agent setup, a rotacja lokalna.
  • Stripe / Polar / Resend / PostHog / Sentry: restricted keys wszędzie tam, gdzie provider to wspiera. Restricted keys w Stripe pozwalają scopować na read-only customers lub write-only payment_intents. Resend oferuje per-domain API keys. PostHog ma personal API tokens, które można scopować na konkretne projekty.

Wzorzec jest ten sam we wszystkich: załóż, że token wycieknie. Potem zaprojektuj setup tak, by w momencie wycieku szkoda była ograniczona do jednego repo, jednej strefy, jednego projektu lub jednej ograniczonej akcji.

Audyt jest tym, co trzyma system przed rdzewieniem. Bez niego scoped tokeny się akumulują, dormant zostają włączone, a “tymczasowe” tokeny z podwyższonymi uprawnieniami stają się trwałe. Standard 2026 to wstawić cykliczne wydarzenie kalendarzowe na 90 dni zatytułowane “Secrets audit — Q*” i odpalić sztywną checklistę:

  1. Wylistuj wszystko. op item list --vault Personal i op item list --vault Work (lub doppler secrets --project … --config …). Porównaj z listą z poprzedniego kwartału. Zbadaj każdy nowy wpis, który nie ma oczywistego właściciela.
  2. Sprawdź last-used. Dla każdego tokena API sprawdź w dashboardzie providera last-used timestamp (GitHub, Cloudflare, OpenAI, Anthropic, Stripe — wszyscy to wystawiają). Cokolwiek nieaktywne >30 dni: odwołaj. Zawsze możesz odtworzyć.
  3. Rotuj długowieczne. Cokolwiek starsze niż 90 dni bez dobrego powodu: rotuj. Zaktualizuj wpis w menedżerze, zrestartuj zależne procesy i odwołaj stary token u providera.
  4. Sprawdź scope ponownie. Dla każdego ocalałego tokena zweryfikuj, czy scope pasuje do aktualnego użycia. Jeśli token wciąż ma repo scope, ale agent dotyka tylko jednego repo, zejdź na fine-grained.
  5. Skanuj na drift plaintextu. Odpal gitleaks detect --source . --no-banner na każdym repo na maszynie i trufflehog filesystem ~/ --no-update --only-verified (lub odpowiednik), żeby złapać plaintext, który się prześliznął. Napraw, co się znalazło, a potem zacommituj .gitleaks.toml z allowlistą dla znanych bezpiecznych referencji (op://… strings, przykładowe wartości w docs).
  6. Zaloguj audyt. Dopisz jeden akapit podsumowania do ~/personal/secrets-audit-YYYY-Q*.md: co się zmieniło, co zostało zrotowane, co odwołane, co zaskoczyło. Audyt z kolejnego kwartału czyta ten plik jako pierwszy.

Pierwszy audyt zajmie 2–3 godziny. Każdy kolejny spada poniżej 30 minut, bo gros pracy to rotacja + revocation, a nie setup.

  1. Wybierz menedżera i zobowiąż się do niego na 90 dni. Jeśli masz już 1Password i jesteś solo lub w duecie: op run to ścieżka najmniejszego oporu. Jeśli jesteś w zespole 3+ albo chcesz centralizowanego audit logu out-of-the-box: Doppler. Nie odpalaj obu — problem dwóch źródeł prawdy Cię ugryzie. Zainstaluj CLI (brew install 1password-cli lub brew install dopplerhq/cli/doppler) i zweryfikuj auth przed dotknięciem jakiegokolwiek istniejącego .env.

  2. Zinwentaryzuj każdy plaintext sekret na maszynie. Odpal gitleaks detect --source ~ --no-banner --no-git (lub trufflehog filesystem ~/ --no-update), żeby wystawić każdy plaintext key w katalogu domowym. Spodziewaj się 30–100 trafień za pierwszym razem. Otwórz raport, zignoruj false positives i wsadź każdy realny klucz do menedżera — konwencja nazewnicza: <service>/<environment>/<purpose> (np. openai/personal/cli, github/work/developertoolkit-pat).

  3. Zastąp pliki .env plikami z referencjami. Dla każdego projektu, w .env zamień plaintextowe wartości na referencje op:// (1Password) albo usuń je w całości i przerzuć się na doppler run (Doppler). Nowy .env jest komitowalny — zweryfikuj uruchamiając cat .env i potwierdzając, że spokojnie wkleiłbyś go w screenshocie. Zaktualizuj .gitignore, żeby trzymać starą formę .env.local zaignorowaną jako bezpiecznik, ale nowy plik oparty na ref może być spokojnie trackowany.

  4. Owiń każdy długo działający proces w menedżerze. Twój dev server: op run --env-file=.env -- npm run dev. Sesja Claude Code: op run --env-file=.env -- claude (lub ekwiwalent w Dopplerze). Każdy serwer MCP w configu klienta: wstaw na początek komendę menedżera. Zasada: jedno miejsce wstrzykuje sekrety; reszta czyta je z environmentu, nie wiedząc, skąd przyszły.

  5. Zdegraduj każdy token do scopowanego. Otwórz dashboard każdego providera. GitHub: konwertuj klasyczne PAT-y na fine-grained PAT scopowane na konkretne repo. Cloudflare: zastąp globalny API key per-purpose scopowanymi tokenami. OpenAI / Anthropic: rozbij pojedynczy workspace key na project-scoped klucze z miesięcznymi capami. Tworząc każdy nowy scoped token, zapisz go w menedżerze, odwołaj stary natychmiast i zaktualizuj wszędzie, gdzie był referowany.

  6. Daj każdemu serwerowi MCP i agentowi własny token. Nie współdziel GITHUB_TOKEN między Claude Code, Codex CLI i serwerem @modelcontextprotocol/server-github. Stwórz trzy fine-grained PAT-y z tym samym scope, ale różnymi nazwami — jeśli jeden transkrypt wycieknie, rotujesz jeden token i wiesz dokładnie, który agent go wystawił.

  7. Dodaj gitleaks do pre-commit hooka. brew install gitleaks i dorzuć gitleaks detect --staged --no-banner do pre-commit hooka repo (lub .husky/pre-commit). To Twój siatka bezpieczeństwa na nieuchronny dzień, gdy zapomnisz i wkleisz realny klucz do config file przez przypadek. CI powinno odpalać ten sam check na push.

  8. Wsadź audyt co kwartał do kalendarza. Cykliczne wydarzenie co 90 dni, 60 minut, zatytułowane “Secrets audit — Q*”. Pierwszy odpal to ten, którego będziesz unikać; odpal go mimo to. Przejdź sześciopunktową checklistę powyżej. Po pierwszym razie nawyki same się skorygują, bo nie będziesz chciał spędzać godziny w kolejnym kwartale rotując rzeczy, które mogłeś zrotować szybko.

  • .env zacommitowany do repo. Wciąż #1 wektor wycieku w 2026 według GitGuardian. Odpal git log -p -- '.env' na każdym repo, jakiego kiedykolwiek dotknąłeś, i zrotuj wszystko, co znajdziesz — historia Gita jest wieczna, więc “usunąłem później” nie pomaga. Fix jest strukturalny: przerzuć się na pliki .env oparte na referencjach i wsadź hook gitleaks na pre-commit, żeby przyszły drift był łapany u źródła.
  • Hardkodowane klucze w plikach źródłowych. Dosłowne const apiKey = "sk-…" w src/lib/openai.ts jest znacznie gorsze niż .env, bo propaguje się przez każdy clone, każdy artefakt CI i każdy search index, do którego agent kiedykolwiek sięgnie. Jeśli Twój agent wystawi go raz w transkrypcie, załóż, że jest skompromitowany. Zrotuj, potem przerzuć się na dostęp tylko przez env.
  • Tokeny o szerokim scope. Klasyczny GitHub PAT z pełnym repo scope to master key na każde prywatne repo, jakie widzisz — w tym te, których nie jesteś właścicielem. Globalny API key Cloudflare to to samo. OpenAI workspace keys bez spend cap pozwalają niekontrolowanemu agentowi spalić cały budżet karty w popołudnie. Zdegraduj każdy z nich do scoped odpowiednika. Model tokenowy z 2018 nie nadaje się do agentycznych workloadów 2026.
  • Jeden token współdzielony między agentami. Gdy ten sam GITHUB_TOKEN jest używany przez Claude Code, Codex CLI, runner GitHub Actions, serwer MCP i bota na Slacku, wyciek zmusza Cię do rotacji wszędzie naraz i nie wiesz, który agent wycieknął. Jeden token per agent per środowisko jest non-negotiable dla setupu max-score.
  • Menedżer sekretów jako narzędzie copy-paste. Wsadzanie sekretów do 1Password, ale dalej kopiowanie ich do .env, niweczy cały sens. Plaintext jest z powrotem na dysku, agent dalej go przeczyta. Menedżer musi być źródłem runtime, nie schowkiem.
  • Brak wygaśnięcia. “No expiration” na PAT to nawyk z 2018 i powinien być nielegalny w Twoim workflowie. Default 90 dni, nawet dla kluczy, o których myślisz, że zawsze ich będziesz potrzebował. Rotacja wymusza audyt.
  • Pomijanie audytu, bo “nic się nie zmieniło”. Nic widocznego się nie zmieniło; pod powierzchnią sześć tokenów jest teraz starszych niż 180 dni, dwa dormant, jeden provider dodał nowe permission scopes, których nie odebrałeś. Wartość audytu się składa, gdy go odpalasz. Pominięcie go jednego kwartału nie podwaja pracy w kolejnym — potraja.
  • Ślepe ufanie outputowi serwera MCP. Zewnętrzny serwer MCP, którego nie audytujesz w pełni, może wywołać process.env i wyeksfiltrować wszystko z Twojego environmentu. Traktuj serwery MCP jak rozszerzenia przeglądarki: minimalna liczba, minimalne uprawnienia, preferuj first-party lub dobrze recenzowane, daj każdemu swój scoped token i nigdy nie odpalaj ich z wstrzykniętym master .env.
  • Potrafisz bez wahania wymienić menedżera sekretów, którego używasz (1Password CLI, Doppler, Vault, AWS Secrets Manager). Jest zainstalowany, jesteś zalogowany i działa od >30 dni.
  • Odpalenie grep -r "sk-" ~ 2>/dev/null (lub jakiegokolwiek ekwiwalentnego prefiksu providera) zwraca zero plaintextowych kluczy — tylko referencje op:// lub puste .env.
  • Każdy .env w Twoich repo jest bezpieczny do zacommitowania. Realne sekrety żyją w menedżerze.
  • Każdy serwer MCP w configu klienta startuje przez op run lub doppler run — żadnych plaintextowych kluczy w żadnym JSON-ie configu MCP.
  • Twoje GitHub PAT-y są wszystkie fine-grained, każdy scopowany na konkretne repo z jawnymi datami wygaśnięcia ≤90 dni. Żaden klasyczny PAT z repo scope nie istnieje na Twoim koncie.
  • Twoje konto Cloudflare nie ma żadnego tokena z etykietą “Global API Key” wpiętego w jakikolwiek aktywny workflow.
  • Klucze OpenAI i Anthropic są project-scoped z miesięcznymi cap-ami na spend. Wiesz, ile kosztuje każdy projekt miesięcznie z dokładnością ±20%.
  • Każdy agent / serwer MCP / job CI używa swojego własnego tokena, nie współdzielonego.
  • gitleaks chodzi na każdym pre-commit i każdym run CI, z allowlistą dla znanych bezpiecznych referencji op://.
  • Masz cykliczne wydarzenie co 90 dni “Secrets audit” w kalendarzu, odpaliłeś je w zeszłym kwartale i masz secrets-audit-YYYY-Q*.md, by to udowodnić.
  • Czytając transkrypty agenta z ostatniego tygodnia, nie znajdujesz ani jednego plaintextowego credentiala zacytowanego gdziekolwiek.