Repo of the Day
anomalyco/openauth
Published: Jan 14, 2025
Open repository ↗▦ Universal, standards-based auth provider.
Summary
OpenAuth is a self-hosted, OAuth 2.0-based authentication server written in TypeScript that can run as a standalone service or be embedded into an existing application. It targets web apps, mobile apps, single-page apps, internal tools, and third-party clients, and is currently labeled as beta in the README. The library is built on the Hono web framework and ships with provider integrations, a themeable UI, and a small client SDK.
What it is useful for
OpenAuth is useful when you want a single, centralized auth server running on your own infrastructure instead of using a SaaS product or wiring auth into each application separately. It implements the OAuth 2.0 specification, so any OAuth-compatible client can use it, including third-party applications that need a "log in with myapp" flow.
It supports multiple identity sources: third-party providers such as GitHub, built-in flows such as email/password and pin code, or custom providers you implement yourself. The runtime is portable across Node.js, Bun, AWS Lambda, and Cloudflare Workers, and a minimal KV-style storage layer (with adapters for Cloudflare KV, DynamoDB, and an in-memory store for tests) holds refresh tokens and password hashes.
The project explicitly does not handle user management. Once a user is identified, OpenAuth invokes a callback where you look up or create the user record, so you can keep your existing database and ORM. A documented limitation is that OpenAuth is still in beta, and the README recommends the examples/ folder and SST components for fuller deployments.
How engineers can use it
The README documents the following quick-start path:
-
Import
issuerfrom@openauthjs/openauthand configure providers, subjects, storage, and asuccesscallback. For example:import { issuer } from "@openauthjs/openauth" import { GithubProvider } from "@openauthjs/openauth/provider/github" import { PasswordProvider, PasswordUI } from "@openauthjs/openauth/provider/password" const app = issuer({ providers: { github: GithubProvider({ clientID: process.env.GITHUB_CLIENT_ID!, clientSecret: process.env.GITHUB_CLIENT_SECRET!, scopes: ["user:email"], }), password: PasswordProvider(PasswordUI({ sendCode: async (email, code) => { console.log(email, code) }, })), }, subjects, storage: MemoryStorage(), async success(ctx, value) { // look up or create user, then return ctx.subject("user", { userID }) }, }) -
Define
subjectswithvalibot(or any Standard Schema-compatible library) so the JWT payload is typed. -
Export the Hono app for the chosen runtime:
export default appfor Bun or Cloudflare Workers, wrap withhono/aws-lambda'shandlefor Lambda, or@hono/node-server'sservefor Node.js. -
On the client, use
createClientfrom@openauthjs/openauth/client. For server-rendered apps, run the code flow viaclient.authorize(redirectUri, "code")and exchange the code withclient.exchange. For SPAs and mobile apps, enable PKCE with{ pkce: true }, store the verifier, then send the access token asAuthorization: Bearer ...to your API. Verify withclient.verify(subjects, accessToken, { refresh }), which auto-refreshes expired tokens.
For full production setup details, the README points to openauth.js.org.