Fix inconsistent line endings across all project files for cross-environment consistency. Add complete unit test suite covering core utilities, API routes, and server services. Add Playwright E2E test setup with smoke, auth, and agent API tests. Update all project configuration files to match standardized formatting. Fix MCP API error handling to properly propagate HTTP status codes and use correct JSON-RPC error codes. Add VSCode workspace configuration, extensions, and example MCP config files. Update .gitignore to exclude new test and build artifacts.
68 lines
2.1 KiB
TypeScript
68 lines
2.1 KiB
TypeScript
"use client";
|
|
|
|
import { createContext, useContext, useEffect, useState, type ReactNode } from "react";
|
|
import type { RecordAuthResponse, RecordModel } from "pocketbase";
|
|
import getPocketBase from "@/lib/pocketbase";
|
|
|
|
interface AuthContextType {
|
|
user: RecordModel | null;
|
|
loading: boolean;
|
|
login: (email: string, password: string) => Promise<void>;
|
|
register: (email: string, password: string, passwordConfirm: string, name: string) => Promise<void>;
|
|
logout: () => void;
|
|
requestPasswordReset: (email: string) => Promise<void>;
|
|
}
|
|
|
|
const AuthContext = createContext<AuthContextType | undefined>(undefined);
|
|
|
|
export function AuthProvider({ children }: { children: ReactNode }) {
|
|
const [user, setUser] = useState<RecordModel | null>(null);
|
|
const [loading, setLoading] = useState(true);
|
|
|
|
useEffect(() => {
|
|
const pb = getPocketBase();
|
|
if (pb.authStore.isValid) {
|
|
setUser(pb.authStore.record);
|
|
}
|
|
setLoading(false);
|
|
|
|
pb.authStore.onChange(() => {
|
|
setUser(pb.authStore.record);
|
|
});
|
|
}, []);
|
|
|
|
const login = async (email: string, password: string) => {
|
|
const pb = getPocketBase();
|
|
const authData: RecordAuthResponse = await pb.collection("users").authWithPassword(email, password);
|
|
setUser(authData.record);
|
|
};
|
|
|
|
const register = async (email: string, password: string, passwordConfirm: string, name: string) => {
|
|
const pb = getPocketBase();
|
|
await pb.collection("users").create({ email, password, passwordConfirm, name });
|
|
await login(email, password);
|
|
};
|
|
|
|
const logout = () => {
|
|
const pb = getPocketBase();
|
|
pb.authStore.clear();
|
|
setUser(null);
|
|
};
|
|
|
|
const requestPasswordReset = async (email: string) => {
|
|
const pb = getPocketBase();
|
|
await pb.collection("users").requestPasswordReset(email);
|
|
};
|
|
|
|
return (
|
|
<AuthContext.Provider value={{ user, loading, login, register, logout, requestPasswordReset }}>
|
|
{children}
|
|
</AuthContext.Provider>
|
|
);
|
|
}
|
|
|
|
export function useAuth() {
|
|
const context = useContext(AuthContext);
|
|
if (!context) throw new Error("useAuth must be used within AuthProvider");
|
|
return context;
|
|
}
|