Clerk orgs
Skill ulpi-io/plugin-marketplace/plugins/clerk/skills/clerk-orgs
A curated collection of 7,800+ agent skills for Claude Desktop, sourced from skills.sh
npx -y skills add ulpi-io/plugin-marketplace --skill clerk-orgsAssembled from the repository path, not quoted from the project. Check it against their README if it does not work.
2 things to look at
- no licenseNo license file was found in the repository. Code published without one is not open source by default, so using it at work is a question for whoever answers licensing questions where you are.
- 1 stars1 stars. Stars are a popularity signal and not a quality one, but at this level it is likely that nobody has read this closely except its author, and you would be relying on your own review.
What its author says it does
Copied from the file, not written here
Clerk Organizations for B2B SaaS - create multi-tenant apps with org switching, role-based access, verified domains, and enterprise SSO. Use for team workspaces, RBAC, org-based routing, member management.
The file declares its own license as MIT. That is the author’s claim about this one file, and it is not the same thing as the license GitHub reports for the repository, which is listed with the other numbers below.
SKILL.md
6.6 KB, ~1.6k tokens by cl100k_base, as published. Nobody here has run it
Organizations (B2B SaaS)
Prerequisite: Enable Organizations in Clerk Dashboard first.
Version: Check
package.jsonfor the SDK version — seeclerkskill for the version table. Core 2 differences are noted inline with> **Core 2 ONLY (skip if current SDK):**callouts.
Quick Start
- Create an organization via dashboard or through Clerk API
- Use OrganizationSwitcher to let users switch between orgs
- Protect routes using orgSlug from URL and role checks
Documentation Reference
Key Patterns
1. Get Organization from Auth
Server-side access to organization:
import { auth } from '@clerk/nextjs/server'
const { orgId, orgSlug } = await auth()
console.log(`Current org: ${orgSlug}`)
2. Dynamic Routes with Org Slug
Create routes that accept org slug:
app/orgs/[slug]/page.tsx
app/orgs/[slug]/settings/page.tsx
Access the slug:
export default function DashboardPage({ params }: { params: { slug: string } }) {
return <div>Organization: {params.slug}</div>
}
3. Check Organization Membership
Verify user has access to specific org:
import { auth } from '@clerk/nextjs/server'
export default async function ProtectedPage() {
const { orgId, orgSlug } = await auth()
if (!orgId) {
return <div>Not in an organization</div>
}
return <div>Welcome to {orgSlug}</div>
}
4. Role-Based Access Control
Check if user has specific role:
const { has } = await auth()
if (!has({ role: 'org:admin' })) {
return <div>Admin access required</div>
}
5. OrganizationSwitcher Component
Let users switch between organizations:
import { OrganizationSwitcher } from '@clerk/nextjs'
export default function Nav() {
return (
<header>
<h1>Dashboard</h1>
<OrganizationSwitcher />
</header>
)
}
Default Roles
All new members get assigned a role:
| Role | Permissions |
|---|---|
org:admin | Full access, manage members, settings |
org:member | Limited access, read-only |
Custom roles can be created in the dashboard.
Default Permissions
| Permission | Role |
|---|---|
org:create | Can create new organizations |
org:manage_members | Can invite/remove members (default: admin) |
org:manage_roles | Can change member roles (default: admin) |
org:update_metadata | Can update org metadata (default: admin) |
Authorization Pattern
Complete example protecting a route:
import { auth } from '@clerk/nextjs/server'
import { redirect } from 'next/navigation'
export default async function AdminPage({ params }: { params: { slug: string } }) {
const { orgSlug, has } = await auth()
// Verify user is in the org
if (orgSlug !== params.slug) {
redirect('/dashboard')
}
// Check if admin
if (!has({ role: 'org:admin' })) {
redirect(`/orgs/${orgSlug}`)
}
return <div>Admin settings for {orgSlug}</div>
}
Conditional Rendering with <Show>
Use <Show> for role-based conditional rendering in client components:
import { Show } from '@clerk/nextjs'
<Show when={{ role: 'org:admin' }}>
<AdminPanel />
</Show>
<Show when={{ permission: 'org:billing:manage' }}>
<BillingSettings />
</Show>
Core 2 ONLY (skip if current SDK): Use
<Protect role="org:admin">and<Protect permission="org:billing:manage">instead of<Show>.
Billing Checks
The has() method supports billing plan and feature checks for gating access:
const { has } = await auth()
has({ plan: 'gold' }) // Check subscription plan
has({ feature: 'widgets' }) // Check feature entitlement
Core 2 ONLY (skip if current SDK):
has()only supportsroleandpermissionparameters. Billing checks are not available.
Session Tasks
When personal accounts are disabled, users must choose an organization after sign-in. This is handled by the choose-organization session task:
import { TaskChooseOrganization } from '@clerk/nextjs'
// Renders when user must select an org
<TaskChooseOrganization redirectUrlComplete="/dashboard" />
Core 2 ONLY (skip if current SDK): Session tasks are not available. Use
<OrganizationSwitcher>for org selection.
Enterprise SSO
Organizations can use Enterprise SSO (SAML/OIDC) for member authentication:
// Strategy name for Enterprise SSO
strategy: 'enterprise_sso'
// Access enterprise accounts on user object
user.enterpriseAccounts
Core 2 ONLY (skip if current SDK): Uses
strategy: 'saml'instead ofstrategy: 'enterprise_sso', anduser.samlAccountsinstead ofuser.enterpriseAccounts.
Common Pitfalls
| Symptom | Cause | Solution |
|---|---|---|
orgSlug is undefined | Not calling await auth() | Use const { orgSlug } = await auth() |
| Role check always fails | Not awaiting auth() | Add await before auth() |
| Users can access other orgs | Not checking orgSlug matches URL | Verify orgSlug === params.slug |
| Org not appearing in switcher | Organizations not enabled | Enable in Clerk Dashboard → Organizations |
| Invitations not working | Wrong role configuration | Ensure members have invite role permissions |
Workflow
- Setup - Enable Organizations in Clerk Dashboard
- Create org - Users create org or admin creates via API
- Add members - Send invitations or add directly
- Assign roles - Default member role, promote to admin as needed
- Build protected routes - Use auth() to check orgSlug and roles
- Use OrganizationSwitcher - Let users switch between orgs