← NetlifyCONTENT HISTORY

Update to Netlify

Snapshot Oct 7, 2026 · 00:02 UTC · version 1.6.0

Collection source: downloaded plugin package.

WHAT CHANGED · RULE-BASED ANALYSIS

First saved snapshot

No earlier snapshot is available to establish a change.

Compare saved observations

Download comparison JSON
Full technical diff · 0 changed fields
Full snapshot data
{
  "description": "Picks the right Netlify site-protection layer and disambiguates the three unrelated \"auth\" concepts users conflate — app-user login (Netlify Identity), site-load gating (Password Protection / project visibility), and dashboard SAML SSO. Use it when asked to password-protect a site or Deploy Preview, make a project private/public, restrict a site to your team, require SSO to view a site, set up company-wide app SSO, or invite users to a private project. Also use it for SSO-session symptoms on protected sites: \"logged out mid-session\", 401s after about an hour, or token expiry/refresh questions. Not for wiring auth code — route app-login setup to netlify-identity.",
  "included_files": [
    {
      "relative_path": "references/two-layer-pattern.md",
      "size_in_bytes": 5424
    }
  ],
  "name": "netlify-access-control",
  "skill_md_contents": "---\nname: netlify-access-control\ndescription: 'Picks the right Netlify site-protection layer and disambiguates the three unrelated \"auth\" concepts users conflate — app-user login (Netlify Identity), site-load gating (Password Protection / project visibility), and dashboard SAML SSO. Use it when asked to password-protect a site or Deploy Preview, make a project private/public, restrict a site to your team, require SSO to view a site, set up company-wide app SSO, or invite users to a private project. Also use it for SSO-session symptoms on protected sites: \"logged out mid-session\", 401s after about an hour, or token expiry/refresh questions. Not for wiring auth code — route app-login setup to netlify-identity.'\n---\n\n# Netlify access control — pick the protection layer\n\nThis skill routes you to the correct protection layer. It does not teach each one. **These settings have no public API, CLI command, or MCP tool.** Never curl `api.netlify.com` or read local auth tokens to inspect or change them — give the user the dashboard path and checklist. On failure, report what you tried and stop.\n\n## First: disambiguate \"auth\" — three unrelated layers\n\nUsers constantly conflate these. Identify which one is meant before recommending anything.\n\n1. **Netlify Identity** — \"who is this user *inside my app*.\" Issues `nf_jwt`. → route to the **netlify-identity** skill; not covered here.\n2. **Password Protection / project visibility** — \"can this request load the site at all.\" Covered here.\n3. **Team/Org SAML SSO** — \"can you log in to the Netlify *dashboard*.\" Gates dashboard access; also underlies team-login site protection.\n\nSessions are separate. The same provider (e.g. Google) can appear twice unrelated — Identity OAuth for app users vs. SAML IdP for team members.\n\n**Double-login footgun:** a Password-Protection/team-login perimeter session and an Identity app session have **no bridge** — no shared cookie, no header forwarding, no JWT exchange. Don't try to wire them together. For the combined layered pattern and its tradeoffs, see `references/two-layer-pattern.md`.\n\n**Want company-wide app SSO with a single sign-in (no double login)?** Recommend the **Auth0 extension** federating to the corporate IdP *before* the two-layer stack.\n\n## Decision guide (this skill's job)\n\n- Restrict entire site to your team, invite by email → **Private project** (Credit-based) or **Team login protection** (Password Protection).\n- Share with anyone holding one shared password → **Basic password protection** (Pro) or **Password** visibility (Pro, Credit-based).\n- Keep production public, protect previews only → scope **Previews only** / **Non-production deploys only**.\n- Require SSO to *view a site* → Organization/Team SSO with **Only SSO allowed (strict)**, then Password Protection with **Team login protection**.\n- Protect specific pages/sections with multiple passwords → **Basic authentication with custom HTTP headers** (formerly Selective password protection): https://docs.netlify.com/manage/security/secure-access-to-sites/basic-authentication-with-custom-http-headers/\n- Authenticate your own end users → **Netlify Identity** / **OAuth provider tokens** / **Role-based access control with JWT** → route to netlify-identity.\n- Block malicious/automated traffic or AI crawlers → **Advanced Web Security** (WAF / Firewall Traffic Rules / rate limiting) or **User Agent Blocker** extension: https://docs.netlify.com/build/build-with-ai/block-ai-crawlers/\n\n## Key distinction: Private vs Password\n\n- **Private** already requires Netlify credentials — no shared password. Invite by email; recommended for team-only access.\n- **Password** = one universal shared password anyone can use (including managing team members, who must also enter it). No SSO.\n- **Team login protection** = same mechanism as Private: a visitor must log in as a member of your Netlify team, and **Reviewers** you invite can get in too (unlimited and not counted toward the member count on legacy plans; Pro or higher on Credit-based plans). **Git Contributors cannot log in** — invite them as Reviewers rather than upgrading them to Developer.\n\n## SSO-session symptom: 401s after ~1 hour\n\nIf a user reports being \"logged out mid-session\" or 401s on an SSO-protected site: **SSO auth tokens expire after 1 hour**, after which requests return `401`. Sites with SSO protection return the header **`Netlify-Site-Protection-Expires-In`** — seconds until the request's token expires. Refresh proactively:\n\n```js\n// Client-side. Checks the Netlify SSO protection header and reloads before expiry.\nconst res = await fetch(window.location.href, { method: \"HEAD\" });\nconst secondsLeft = Number(res.headers.get(\"Netlify-Site-Protection-Expires-In\"));\n// Tokens last 1 hour (3600s). Reload a bit early to avoid a 401.\nif (!Number.isNaN(secondsLeft) && secondsLeft < 60) {\n  window.location.reload();\n}\n```\n\n## UI paths (the only path — no API)\n\n**Credit-based plans (Free, Personal, Pro)** — project-level \"Password Protection\" is replaced by **Project visibility**:\n- Per project: Project configuration > General > Visitor access > **Project visibility** — `https://app.netlify.com/projects/{site_name}/configuration/general/#project-visibility`. Edit visibility → (Customize if a team default exists) → **Public** / **Password** (Pro only) / **Private** → set **Preview access** (Production and previews / Previews only) → Save.\n- Team default: Team settings > General > Visitor access > **Default project visibility** — `https://app.netlify.com/teams/{team_name}/settings/general#default-project-visibility`. Options: Private for new projects / Private for all projects / Public for new projects.\n- No per-team default *password* here; set a password per project.\n\n**Enterprise / Open Source / legacy (non-Credit-based)** — use **Password Protection** UI:\n- Per site: Project configuration > General > Visitor access > **Password Protection** — `https://app.netlify.com/projects/{site_name}/configuration/general#visitor-access`. Configure → Basic or Team login → scope (All deploys / Non-production deploys only) → Save.\n- Team default: Team settings > Access & security > Visitor access > **Default Password Protection settings** — `https://app.netlify.com/teams/{team_name}/settings/access#default-site-protection-settings`. Applies to all sites without their own settings.\n\n**Legacy → Credit-based mapping:** No protection→Public · Basic protection→Password · Team protection→Private · All deploys→Production and previews · Non-production deploys only→Previews only.\n\n## Constraints & footguns\n\n- **Site-specific Password Protection overrides team defaults.**\n- **Who can change these settings:** project visibility — Organization Owners (on certain Enterprise plans), Team Owners, and Developers with access to that project; **Internal Builders cannot publish to production, so they cannot make a project public**. Password Protection — a Developer changes it per site, a Team Owner sets the team default.\n- **Advanced Web Security runs before password/login prompts** — a blocked IP hits an error page before ever seeing the prompt. Internal order: Firewall Traffic Rules → WAF → Rate limiting.\n- **Third-party webhooks (Slack, Stripe, etc.) cannot reach a private project** — receiving webhooks requires the project to be **public**.\n- **Make public** requires at least one successful **production deploy**.\n- **Protecting only non-production deploys** with Password Protection is **Enterprise only**.\n- **Plan gating:** Basic password protection for the whole site → all Pro plans; all Password Protection options → Enterprise. Project visibility (public/private, private-by-default) → Credit-based Free/Personal/Pro only; password-protected visibility → Pro only. On Free/Personal a private project is visible only to the Team Owner (single-seat); Pro allows unlimited members.\n- **Team default changes by creation date:** teams created on/after **July 28, 2026** default to **Private for new projects**; earlier teams default to **Public**.\n- **Renamed:** \"site-wide password protection\" (old name of a Password Protection option); \"Selective password protection\" → Basic authentication with custom HTTP headers.\n\nReference: https://docs.netlify.com/manage/security/secure-access-to-sites/overview/ · https://docs.netlify.com/manage/security/secure-access-to-sites/password-protection/ · https://docs.netlify.com/manage/security/secure-access-to-sites/project-visibility/\n\n<!-- Advanced Web Security (WAF, Firewall Traffic Rules, rate limiting) specifics — limits, config keys, plan gating — not in source; referenced by URL only. -->\n<!-- Exact per-tier matrix of basic vs team-login options across plans is only partially stated in sources. -->\n\n<!-- system: agent-context/access-control/system.md — human-owned, merged by ctx-gen; edit system.md, not this section -->\n# Netlify house rules (access-control)\n\nThese are org conventions, not docs facts — merged into the rendered skill by\nctx-gen and never generated. Owned by the skills maintainer.\n\n1. This is a routing/disambiguation skill: keep it narrow — its job is\n   picking the right protection layer, not teaching each one.\n2. The combined Password-Protection + Identity pattern lives in this skill's\n   `references/two-layer-pattern.md`.\n3. \"Auth\" on Netlify is three unrelated layers users constantly conflate:\n   Netlify Identity (\"who is this user inside my app\" — issues `nf_jwt`),\n   Password Protection / project visibility (\"can this request load the site\n   at all\"), and Team/Org SAML SSO (\"can you log in to the Netlify\n   dashboard\"). Sessions are separate; the same provider (Google) can appear\n   in two unrelated places — Identity OAuth for app users, SAML IdP for team\n   members. Disambiguate before recommending anything.\n4. The double login is real: a Password-Protection/team-login perimeter\n   session and an Identity app session have no bridge — no shared cookie, no\n   header forwarding, no JWT exchange. Don't burn iterations wiring them\n   together; tradeoffs live in `references/two-layer-pattern.md`.\n5. These settings have no public API, CLI command, or MCP tool. Never curl\n   `api.netlify.com` or read local auth tokens to inspect or change them —\n   hand the user the dashboard path and checklist; on failure, report what\n   you tried and stop.\n6. Identity setup, auth code, and OAuth providers for app users belong to the\n   netlify-identity skill — route there; this skill only picks the layer.\n7. For company-wide app-level SSO with a single sign-in (no double login),\n   the Auth0 extension — federating to the corporate IdP — is the\n   recommendation before the two-layer stack.\n8. The description's triggers must include the SSO-session symptoms users\n   actually report — \"logged out mid-session\", 401s on an SSO-protected\n   site, token expiry/refresh — not only setup phrasing. The\n   `Netlify-Site-Protection-Expires-In` guidance is unreachable if the\n   skill never triggers on the symptom.\n9. Team login protection excludes Git Contributors, and the answer to that is\n   **Reviewers**, never a Developer seat. Reviewers can open team-login-\n   protected deploys: unlimited and not counted toward the member count on\n   legacy plans, Pro or higher on Credit-based plans. Every answer about Git\n   Contributor access must name the Reviewer path — recommending an upgrade to\n   Developer sells a paid seat per person to solve something the product\n   already solves for free. Stating the exclusion without the remedy is the\n   failure mode this rule exists to prevent; it has happened. Never frame the\n   permitted roles as a closed list (\"only X, Y and Z get in\") — even with the\n   Reviewer path added after it, a closed list reads as Reviewers being shut\n   out, and agents repeat it. Naming roles is optional; the question is\n   usually only about Git Contributors.\n10. Say who can change these settings, not only how to change them. Project\n   visibility: Organization Owners (on certain Enterprise plans), Team Owners,\n   and Developers with access to that project — and Internal Builders cannot\n   make a project public, because they cannot publish to production. Password\n   Protection: a Developer per site, a Team Owner for the team default. A\n   checklist handed to someone without the role is a dead end.\n"
}

SHA-256 of public snapshot: 0bd9bfe1c20ccc45bb563fe2a75f303350fe0dfc78dcae77e56f730b0d9d851a