turso-auth
v1.1.1
Published
API-key auth for React + Vite apps. Handles email/password login, `localStorage` persistence, auto-logout on 401/403, and protected route guarding.
Readme
turso-auth
API-key auth for React + Vite apps. Handles email/password login, localStorage persistence, auto-logout on 401/403, and protected route guarding.
Requirements
- React 18+
- react-router-dom 6+
- Tailwind CSS (for
LoginPagestyles)
Installation
npm install turso-authSetup
1. Wrap your app with AuthProvider
// App.tsx
import { BrowserRouter, Routes, Route, Navigate } from 'react-router-dom'
import { AuthProvider, ProtectedRoute, LoginPage } from 'turso-auth'
import Dashboard from './pages/Dashboard'
export default function App() {
return (
<BrowserRouter>
<AuthProvider apiUrl={import.meta.env.VITE_API_URL}>
<Routes>
<Route path="/login" element={<LoginPage />} />
<Route path="/" element={<Navigate to="/dashboard" replace />} />
<Route
path="/dashboard"
element={<ProtectedRoute><Dashboard /></ProtectedRoute>}
/>
</Routes>
</AuthProvider>
</BrowserRouter>
)
}2. Set your API URL
# .env
VITE_API_URL=https://your-backend.example.comPass it to AuthProvider via the apiUrl prop (resolved by your app's build, not the library):
<AuthProvider apiUrl={import.meta.env.VITE_API_URL}>The login request is sent to POST {apiUrl}/api/users/login and expects { api_key: string } in the response.
Usage
useAuth — access auth state and actions
import { useAuth } from 'turso-auth'
function Dashboard() {
const { apiKey, logout } = useAuth()
return (
<div>
<p>Authenticated: {apiKey}</p>
<button onClick={logout}>Sign out</button>
</div>
)
}| Value | Type | Description |
|---|---|---|
| apiKey | string \| null | The stored API key, or null when logged out |
| login(email, password) | Promise<void> | Authenticates and stores the key |
| logout() | void | Clears the key from state and localStorage |
ProtectedRoute — guard routes from unauthenticated users
import { ProtectedRoute } from 'turso-auth'
<Route path="/settings" element={<ProtectedRoute><Settings /></ProtectedRoute>} />Redirects to /login if no API key is present.
LoginPage — drop-in login form
import { LoginPage } from 'turso-auth'
<Route path="/login" element={<LoginPage />} />Navigates to /dashboard on success. Requires Tailwind CSS in the consuming app.
isAuthError / notifyUnauthorized — protect API calls
Use these in your own fetch services to trigger auto-logout on 401/403:
import { isAuthError, notifyUnauthorized } from 'turso-auth'
async function getProjects(apiKey: string) {
const res = await fetch(`${import.meta.env.VITE_API_URL}/api/projects`, {
headers: { 'X-API-Key': apiKey },
})
if (isAuthError(res.status)) {
notifyUnauthorized() // triggers logout across the app
throw new Error('Unauthorized')
}
if (!res.ok) throw new Error('Request failed')
return res.json()
}notifyUnauthorized() dispatches an auth:unauthorized custom event on window. AuthProvider listens for this and calls logout() automatically.
Customisation
The library is intentionally minimal. To change defaults, fork the source or wrap the exports:
| What to change | Where in source |
|---|---|
| Login endpoint path | src/context/AuthContext.tsx → login() fetch path (base URL is the apiUrl prop) |
| Response field name (api_key) | src/context/AuthContext.tsx → login() destructure |
| localStorage key name (apiKey) | src/context/AuthContext.tsx → STORAGE_KEY |
| Post-login redirect | src/pages/LoginPage.tsx → navigate(...) |
| App name / colours in login form | src/pages/LoginPage.tsx |
| Protected-route redirect target | src/components/ProtectedRoute.tsx |
Publishing
Releases are automated via GitHub Actions. Push a version tag to publish:
git tag v1.0.1
git push origin v1.0.1The workflow runs tests, builds, and publishes to npm. Requires an NPM_TOKEN secret stored in the prod GitHub environment.
