add auth to backend and frontend
This commit is contained in:
+14
-12
@@ -4,7 +4,7 @@ import LatestTemperature from "@/components/latest-temperature"
|
||||
import TemperatureHistory from "@/components/temperature-history"
|
||||
import TemperaturePlot from "@/components/temperature-plot"
|
||||
import RegisterForm from './components/register-form'
|
||||
// import { Button } from "@/components/ui/button"
|
||||
import { AuthProvider } from './contexts/auth-context'
|
||||
|
||||
|
||||
|
||||
@@ -12,18 +12,20 @@ import RegisterForm from './components/register-form'
|
||||
function App() {
|
||||
return (
|
||||
<ThemeProvider defaultTheme="dark" storageKey="vite-ui-theme">
|
||||
<main className="min-h-screen bg-background p-6 w-full">
|
||||
<div>
|
||||
<RegisterForm />
|
||||
</div>
|
||||
<div className="w-full mx-auto space-y-2">
|
||||
<TemperaturePlot />
|
||||
<div className="grid grid-cols-4 gap-6">
|
||||
<LatestTemperature />
|
||||
<TemperatureHistory />
|
||||
<AuthProvider>
|
||||
<main className="min-h-screen bg-background p-6 w-full">
|
||||
<div>
|
||||
<RegisterForm />
|
||||
</div>
|
||||
</div>
|
||||
</main>
|
||||
<div className="w-full mx-auto space-y-2">
|
||||
<TemperaturePlot />
|
||||
<div className="grid grid-cols-4 gap-6">
|
||||
<LatestTemperature />
|
||||
<TemperatureHistory />
|
||||
</div>
|
||||
</div>
|
||||
</main>
|
||||
</AuthProvider>
|
||||
</ThemeProvider>
|
||||
)
|
||||
}
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
import {
|
||||
createContext,
|
||||
useState,
|
||||
useEffect,
|
||||
} from "react"
|
||||
|
||||
import type { ReactNode } from "react"
|
||||
|
||||
type User = {
|
||||
id: number
|
||||
email: string
|
||||
create_at: string
|
||||
}
|
||||
|
||||
type AuthContextType = {
|
||||
user: User | null
|
||||
isAuthenticated: boolean
|
||||
login: (email: string, passwor: string) => Promise<void>
|
||||
logout: () => void
|
||||
isLoading: boolean
|
||||
}
|
||||
|
||||
export const AuthContext = createContext<AuthContextType | null>(null)
|
||||
|
||||
export function AuthProvider({ children }: { children: ReactNode }) {
|
||||
const [user, setUser] = useState<User | null>(null)
|
||||
const [isLoading, setIsLoading] = useState(true)
|
||||
|
||||
useEffect(() => {
|
||||
checkAuth()
|
||||
}, [])
|
||||
|
||||
async function checkAuth() {
|
||||
try {
|
||||
const res = await fetch("/api/me", {
|
||||
credentials: "include",
|
||||
})
|
||||
if (res.ok) {
|
||||
const data = await res.json()
|
||||
setUser(data.user)
|
||||
}
|
||||
}
|
||||
catch {
|
||||
setUser(null)
|
||||
}
|
||||
finally {
|
||||
setIsLoading(false)
|
||||
}
|
||||
}
|
||||
|
||||
async function login(email: string, password: string) {
|
||||
const res = await fetch("/api/login", {
|
||||
method: "POST",
|
||||
credentials: "include",
|
||||
headers: { "Content-Type": "application/json" },
|
||||
body: JSON.stringify({ email, password })
|
||||
})
|
||||
|
||||
if (!res.ok) {
|
||||
const msg = await res.text()
|
||||
throw new Error(msg || "Invalid credentials")
|
||||
}
|
||||
|
||||
const data = await res.json()
|
||||
setUser(data.user)
|
||||
}
|
||||
|
||||
async function logout() {
|
||||
await fetch("api/logout", {
|
||||
method: "POST",
|
||||
credentials: "include",
|
||||
})
|
||||
setUser(null)
|
||||
}
|
||||
|
||||
return (
|
||||
<AuthContext.Provider value={{ user, isAuthenticated: !!user, login, logout, isLoading }}>
|
||||
{children}
|
||||
</AuthContext.Provider>
|
||||
)
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
import { AuthContext } from "@/contexts/auth-context"
|
||||
import { useContext } from "react"
|
||||
|
||||
export function useAuth() {
|
||||
const ctx = useContext(AuthContext)
|
||||
if (!ctx) throw new Error("useAuth must be used within AuthProvider")
|
||||
return ctx
|
||||
}
|
||||
Reference in New Issue
Block a user