https://github.com/sansjack/svoauth
lightweight config-driven svelte OAuth wrapper
https://github.com/sansjack/svoauth
oauth2 oauth2-server svelte svelte5 sveltekit
Last synced: about 1 month ago
JSON representation
lightweight config-driven svelte OAuth wrapper
- Host: GitHub
- URL: https://github.com/sansjack/svoauth
- Owner: sansjack
- License: mit
- Created: 2025-04-07T21:43:26.000Z (about 1 year ago)
- Default Branch: main
- Last Pushed: 2025-05-15T14:24:52.000Z (about 1 year ago)
- Last Synced: 2025-09-24T19:29:49.908Z (9 months ago)
- Topics: oauth2, oauth2-server, svelte, svelte5, sveltekit
- Language: TypeScript
- Homepage:
- Size: 31.3 KB
- Stars: 7
- Watchers: 1
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
Awesome Lists containing this project
README
## π svoauth β Lightweight Config-Driven OAuth for SvelteKit
`svoauth` is a minimal and flexible OAuth 2.0 wrapper designed for SvelteKit projects. It uses a config-driven approach so you can easily plug in providers like GitHub, Google, and more.
---
### π¦ Features
- βοΈ Config-driven approach
- β‘οΈ Minimal SvelteKit integration
- ποΈββοΈ Lightweight and < 20kb
- π Supports token exchange, refresh, and revoke
- π» Server side rendering only (no client-side code)
- π PKCE support (e.g., for Google)
- π Easily configurable for multiple providers
### β Why Did I Make This?
I was working on a SaaS project of mine that needs a lot of integrations with different providers. I wanted to try abstract as much as possible out of my codebase for dealing with the OAuth side of things as i will be adding A LOT of different integrations in the future.
This was really made for my own use but I decided to make a public package so that others can use it as well. The main use of this is so I can get the users access tokens and refresh tokens so i can use them on their behalf to fetch data.
> [!WARNING]
> This package is not meant for the use of authentication but rather for the use of authorization and retrieving access tokens. This should also ONLY be used on the server-side.
## πΊοΈ Roadmap / TODO
My Plans for `svoauth`:
- [ ] Improve error handling and response structure
- [ ] Expand config options (custom headers, custom callbacks)
- [ ] Add some tests
- [ ] Create a proper documentation site with more in-depth examples and explanations
Have ideas? Feel free to open an issue or PR!
### βοΈ Configuration
Define your OAuth clients in a central `oauth.ts` config file:
```ts
// src/lib/server/oauth.ts
import { env } from '$env/dynamic/private';
import { OAuthHandler, type OAuthConfigs } from 'svoauth';
const clients: OAuthConfigs = {
github: {
clientId: env.GITHUB_CLIENT_ID,
clientSecret: env.GITHUB_CLIENT_SECRET,
authorizeUrl: 'https://github.com/login/oauth/authorize',
tokenUrl: 'https://github.com/login/oauth/access_token',
redirectUri: 'http://localhost:5173/integration/callback/github',
scopes: {
values: ['read:user', 'read:org', 'repo:status', 'read:project']
}
},
google: {
clientId: env.GOOGLE_CLIENT_ID,
clientSecret: env.GOOGLE_CLIENT_SECRET,
pkce: true,
authorizeUrl: 'https://accounts.google.com/o/oauth2/v2/auth',
tokenUrl: 'https://oauth2.googleapis.com/token',
refreshTokenUrl: 'https://oauth2.googleapis.com/token',
revokeTokenUrl: 'https://oauth2.googleapis.com/revoke',
redirectUri: 'http://localhost:5173/integration/callback/google',
params: [{ access_type: 'offline' }],
scopes: {
values: ['email', 'profile', 'https://www.googleapis.com/auth/calendar.readonly']
}
}
};
export const svoAuth = new OAuthHandler(clients);
```
---
### π Link Route
Create a route that redirects users to the provider's authorization page.
```ts
// src/routes/link/[client]/+server.ts
import { svoAuth } from '$lib/server/oauth';
import { redirect } from '@sveltejs/kit';
export const GET = async (event) => {
const clientName = event.params.client;
const authUrl = svoAuth.get(clientName).generateAuthorizeUrl(event);
throw redirect(303, authUrl);
};
```
---
### π― Callback Route
Create a callback route to handle the OAuth response and exchange the code for a token.
```ts
// src/routes/callback/[client]/+server.ts
import { json } from '@sveltejs/kit';
import { svoAuth } from '$lib/server/oauth';
export const GET = async (event) => {
const clientName = event.params.client;
const tokens = await svoAuth.get(clientName).exchangeCodeForToken(event);
const accessToken = tokens.accessToken();
return json({ token: accessToken });
};
```
---
### β»οΈ Refresh Token
Create a route to refresh the access token using a refresh token.
```ts
// src/routes/refresh/[client]/+server.ts
import { svoAuth } from '$lib/server/oauth';
import { json, error } from '@sveltejs/kit';
type RefreshReqest = {
token: string;
};
export const POST = async (event) => {
const { params, request } = event;
const clientName = params.client;
const result = (await request.json()) as RefreshReqest;
const { token } = result;
if (!token) {
throw error(422);
}
const newTokens = await svoAuth.get(clientName).refreshToken(token);
const access_token = newTokens.accessToken();
return json({ message: access_token });
};
```
---
### π« Revoke Token
Create a route to revoke a refresh token.
```ts
// src/routes/revoke/[client]/+server.ts
import { svoAuth } from '$lib/server/oauth';
import { json, error } from '@sveltejs/kit';
type RevokeRequest = {
refresh_token: string;
};
export const POST = async (event) => {
const { params, request } = event;
const clientName = params.client;
const result = (await request.json()) as RevokeRequest;
const { refresh_token } = result;
if (!refresh_token) {
throw error(422);
}
await svoAuth.get(clientName).revokeToken(refresh_token);
return json({ message: `${clientName} token has been revoked` });
};
```
---
### β
Example Flow
1. Navigate to `/link/github`
2. You get redirected to GitHub to authorize
3. After auth, GitHub redirects to `/callback/github`
4. The access token is extracted and returned as JSON