CLAUDE DESKTOP & COWORK. OAUTH2 + PKCE, SKILLS IN EVERY SESSION.
Connect Cowork to systemprompt.io over OAuth2 with PKCE. Your skills, brand rules, and workflows load into every Claude session. No API keys on the workstation.
OAuth2 + PKCE Handshake
Cowork opens with a blank slate. No memory of your last session, no record of the brand voice you shaped last week, no trace of the client-report template you wrote on Tuesday. You re-paste context, or accept that Claude sounds a little different every time.
The systemprompt.io connection uses OAuth2 with PKCE. Click connect, log in at systemprompt.io, approve. An authorisation code comes back, Cowork exchanges it at the token endpoint, and the session binds. No API key lands on disk. PKCE binds the code exchange to the one-time secret Cowork generated for the flow, so a captured code cannot be replayed from another machine. The authorize validator rejects missing or weak challenges outright; the file is named in the references.
Once the handshake completes, every skill on your account is available in Cowork. Your Anthropic login, Google credentials, and GitHub token do not travel through the connection. The plugin receives short-lived session JWTs that identify the user, not keys to upstream accounts. Staff engineers verifying this read the OIDC discovery document, authorize endpoint, and token exchange, all in one binary you run yourself.
- OAuth2 connection, no API keys on disk — Approve the connection in a browser tab. No API key, no config file to edit. A stolen laptop holds no static key to replay.
- PKCE blocks code replay — PKCE binds the authorisation code to the one-time secret the browser generated. A captured code is worthless on another machine. The validator rejects weak or missing challenges.
- Works with your Claude plan — Compatible with Claude Pro, Max, Team, and Enterprise. Runs on macOS and Windows. Connects as a standard Cowork plugin install, not a sideload.
- validation.rs (PKCE enforcement) Authorize-endpoint validator that requires a code_challenge and accepts only S256
- discovery.rs (OIDC discovery) The .well-known endpoints Cowork reads to resolve authorize, token, and introspection URLs
- wellknown.rs (route registration) OIDC discovery route registration
- token/ (authorization code exchange) Token exchange endpoint, trades the authorisation code for a short-lived session JWT
- register.rs (dynamic client registration) Dynamic client registration endpoint, so Cowork can attach without a manual app secret
- introspect.rs (token introspection) Token introspection endpoint used to validate active sessions
Skills You Own
A fresh chat every time is not just inconvenient. The tone, the process, and the correction you made at message forty die when the window closes. The next session starts with a Claude that does not know you.
A systemprompt.io skill is a Markdown document plus a small config block. It holds the instructions you want Claude to follow, tags for grouping, and an enabled flag so you can switch one off without deleting it. "My skills" means the Markdown files you wrote, not hidden features and not a shared prompt library. Read every one of them in the dashboard, edit in your browser, export as files. Cancel your account and you walk away with the Markdown.
Each skill scopes to your account through an owner reference, which is how the server decides whose skills to return when Cowork asks. The skill service loads them at session start, and a runtime injector merges the skill's instructions onto the base prompt before the tool call runs. A compliance officer finds the skill that shaped a response in the same audit row as the tool call. The loader file is named in the references.
- A skill is a file you own — Each skill is Markdown plus a config block with a name, description, and tags. You wrote it, you can read it, you can export it. If you leave systemprompt.io, the files come with you.
- Dashboard edits land in the next session — Edit a skill in the dashboard and the ingestion service upserts to the database. The next Cowork session sees the update without a restart, because the plugin reads skills at session start.
- Enable flag, fork, and history — Switch a skill off with the enabled flag, fork it, or tweak a paragraph. Version history preserves yesterday's copy, so a bad edit is never permanent.
- skill.rs (Skill model) Skill struct with ownership link, instructions, tags, and enabled flag
- skill.rs (loader service) Service that fetches a skill by id and emits a loaded event on every load
- ingestion.rs (dashboard sync) Ingestion service that reads directories and upserts skills on every edit
- skills.rs (config shapes) Skill config shapes used on disk and in memory
- skill_injector.rs (prompt merge) Runtime component that merges skill instructions onto the base prompt before a tool call
Dashboard-to-Session Sync
Skills are not a one-time import. They live on the dashboard and change as you do. When a client sends fresh brand guidelines on Friday, the old version is already wrong.
Edit a skill in the browser and the ingestion service reads the updated config, pulls the Markdown body, and writes the new version to the database. The next Cowork session asks for your skills at start and gets the fresh copy. The reverse works too. A skill you draft inside a Cowork conversation lands on the dashboard for later editing. The injector file that merges skill content onto the prompt is named in the references.
For a team workspace, the plugin manifest controls which organisation skills distribute to members. That channel is separate from personal skills. Personal skills stay in your account. Team skills publish through an admin and reach members. The two do not cross over unless an admin promotes a personal skill into the team library.
- Edit once, update everywhere — The ingestion service upserts changes to the database. The next Cowork session picks up the new version. No manual export, no paste-the-latest-version dance.
- Cowork-created skills round-trip — A skill you draft inside a Cowork conversation lands on the dashboard, so a rough idea becomes an editable file you refine later.
- Team skills stay separate — The plugin manifest distributes team skills through a different channel than personal ones. Personal skills do not appear in the team library unless you promote them.
- ingestion.rs (ingest_directory / ingest_skill) Ingestion service that turns dashboard edits into database rows
- skill_injector.rs (inject_for_tool, inject_with_metadata) The runtime merge that stitches skill instructions onto the base prompt and optionally returns metadata
- skills.rs (disk config) Disk skill config, config.yaml parsing and content file resolution
- plugin.rs (plugin manifest) Plugin manifest that declares which skills a team workspace distributes
- skill.rs (load service) Service that Cowork calls at session start to fetch the current skill set
- context_provider.rs (shared contexts) Shared conversation context provider used when a team workspace publishes shared state
Slash-Command Injection
A skill you cannot find when you need it is a skill you will not use. If the brand voice guide lives three tabs deep in a dashboard, you paste a rough approximation instead and the tone drifts.
Type a forward slash in Cowork and your skills appear as commands. Pick one and Claude receives the skill's instructions as part of the prompt for that turn. The slash command is a thin shell around the same injector the rest of the plugin uses, so a skill behaves the same whether you invoke it explicitly or an agent routes to it. The injector file is named below if you want to confirm that the merge happens before the model sees the message.
The loader supports an auto-discover mode that picks up every skill file in a directory, so adding a skill is a matter of dropping a Markdown file on the dashboard and reloading. Bind a skill to a specific agent or MCP server for scope, or leave it available everywhere. The loader iterates the directory, not a fixed list, so the count is unbounded.
- A skill, one keystroke away — Type / in Cowork and your skills appear as commands. Pick one and Claude receives your instructions for that turn, with no re-pasting.
- Same injector, slash or agent — Whether a slash command or an agent selects the skill, the same injector merges instructions into the prompt. One code path, so behaviour does not drift between modes.
- Add skills by dropping files — Auto-discover mode scans the skill directory. Add a skill by writing a Markdown file and a config block. The loader iterates the directory, so the count is unbounded.
- skills.rs (auto-discover) Skill config with auto-discover and per-skill overrides
- skill.rs (Skill model) Skill struct with file_path, instructions, and category
- skill_injector.rs (slash-command merge) Single merge path used whether a skill is triggered by slash command or agent
- plugin.rs (skills component) Plugin config with skills component reference and validation
- skill.rs (load with tracking) Skill load path that emits tracking events for later audit
Tenant-Isolated Skill Loader
If you use Cowork at work and at home, the two tenants should stay separate. Personal experiment skills should not land in your employer's dashboard. The employer's confidential process skills should not sit on a machine you control.
Every skill load passes an RBAC check before content returns. The server resolves the session token to a principal, looks up the skill's owner, and compares. A mismatch returns nothing, not even an error that would confirm the skill exists. The same middleware protects the rest of systemprompt.io, which is why personal skills stay invisible to a team workspace you belong to, and a team workspace's skills only return when you connect under that workspace. The permission middleware and load service are named below for a compliance officer tracing a request.
Lifecycle hooks let a team workspace attach policy at named points in the session. The set covers before and after every tool call with a failure variant, session start, session end, prompt submission, notifications, stops, and subagent start and stop. A team hook can inspect a tool call and block it, or log every prompt for audit, without code on your laptop. The HookEvent enum is in the hooks module and staff engineers confirming the surface has not grown silently can read it there.
- Account-scoped skill loading — The server checks the session token against each skill's owner before returning it. A team workspace's skills do not appear in your personal account, and personal skills do not appear in the team library, because the check refuses cross-account reads.
- Plugin manifests validated before distribution — Every plugin, including Cowork, is defined by a manifest with id rules, a version, and explicit component references. The manifest validates before any skill reaches a user, so a malformed plugin never ships a broken skill set.
- Lifecycle hooks for team policy — Named HookEvent points cover tool calls before, after, and on failure, session start and end, prompt submission, notifications, stops, and subagent start and stop. A workspace hook blocks a tool call before it runs or logs a prompt for audit, without touching individual laptops.
- rbac.rs (permission check) Middleware that checks the session token against the resource owner before any skill load
- plugin.rs (manifest validator) Plugin manifest with id rules, version, author, component references, and a validator run before distribution
- hooks.rs (HookEvent enum) HookEvent enum defining the ten lifecycle points a team workspace can attach policy to
- validator.rs (registry checks) Registry validator that checks ports, OAuth setup, and server types before skills are served
- session_manager.rs (session lifecycle) Session manager that tracks the lifetime of a connection and its permissions
- registry/ (server registry) Server registry that stores server configs and enforces access checks
Founder-led. Self-service first.
No sales team. No demo theatre. The template is free to evaluate — if it solves your problem, we talk.
Who we are
One founder, one binary, full IP ownership. Every line of Rust, every governance rule, every MCP integration — written in-house. Two years of building AI governance infrastructure from first principles. No venture capital dictating roadmap. No advisory board approving features.
How to engage
Evaluate
Clone the template from GitHub. Run it locally with Docker or compile from source. Full governance pipeline.
Talk
Once you have seen the governance pipeline running, book a meeting to discuss your specific requirements — technical implementation, enterprise licensing, or custom integrations.
Deploy
The binary and extension code run on your infrastructure. Perpetual licence, source-available under BSL-1.1, with support and update agreements tailored to your compliance requirements.
Ready to build?
Get started with systemprompt.io in minutes.