001e9023b2
Completed full-stack TeaBoy OS build: Backend (artifacts/api-server): - Session-based auth with express-session + connect-pg-simple (PostgreSQL sessions) - RBAC middleware (requireAuth, requireAdmin) with role-based guards - REST routes for: auth (login/logout/register/me/language), apps CRUD, services CRUD, conversations + messages, notifications, users (admin), home stats - Socket.IO mounted on same HTTP server at /api/socket.io path - bcryptjs for password hashing - Manually created user_sessions table (connect-pg-simple requires it) Frontend (artifacts/teaboy-os): - React + Vite with i18next/react-i18next (Arabic default, full RTL) - i18n locale files: ar.json + en.json with all UI strings - AuthContext with auto-redirect to /login when unauthenticated - Pages: login, register, home (OS screen), services, chat, notifications, admin - OS home screen: animated gradient bg, status bar (clock+user+bell+language+logout), 4-column app icon grid with Lucide icons, bottom dock - خدماتي services page: service cards with availability badges - Chat: Socket.IO real-time messages, conversation list, send messages - Notifications: list with mark-as-read per item + mark all - Admin panel: full CRUD for apps/services/users with toggle switches - Vite proxy /api → localhost:8080 for same-origin cookie auth - credentials: "include" added to customFetch for session cookies Database: - Seed script with demo users (admin/admin123, ahmed/user123) - 8 demo apps, 6 services, 4 categories seeded All e2e tests pass: login, home screen, services, language toggle, admin, logout
72 lines
1.7 KiB
TypeScript
72 lines
1.7 KiB
TypeScript
import { defineConfig, InputTransformerFn } from "orval";
|
|
import path from "path";
|
|
|
|
const root = path.resolve(__dirname, "..", "..");
|
|
const apiClientReactSrc = path.resolve(root, "lib", "api-client-react", "src");
|
|
const apiZodSrc = path.resolve(root, "lib", "api-zod", "src");
|
|
|
|
// Our exports make assumptions about the title of the API being "Api" (i.e. generated output is `api.ts`).
|
|
const titleTransformer: InputTransformerFn = (config) => {
|
|
config.info ??= {};
|
|
config.info.title = "Api";
|
|
|
|
return config;
|
|
};
|
|
|
|
export default defineConfig({
|
|
"api-client-react": {
|
|
input: {
|
|
target: "./openapi.yaml",
|
|
override: {
|
|
transformer: titleTransformer,
|
|
},
|
|
},
|
|
output: {
|
|
workspace: apiClientReactSrc,
|
|
target: "generated",
|
|
client: "react-query",
|
|
mode: "split",
|
|
baseUrl: "/api",
|
|
clean: true,
|
|
prettier: true,
|
|
override: {
|
|
fetch: {
|
|
includeHttpResponseReturnType: false,
|
|
},
|
|
mutator: {
|
|
path: path.resolve(apiClientReactSrc, "custom-fetch.ts"),
|
|
name: "customFetch",
|
|
},
|
|
},
|
|
},
|
|
},
|
|
zod: {
|
|
input: {
|
|
target: "./openapi.yaml",
|
|
override: {
|
|
transformer: titleTransformer,
|
|
},
|
|
},
|
|
output: {
|
|
workspace: apiZodSrc,
|
|
client: "zod",
|
|
target: "generated",
|
|
mode: "split",
|
|
clean: true,
|
|
prettier: true,
|
|
override: {
|
|
zod: {
|
|
coerce: {
|
|
query: ['boolean', 'number', 'string'],
|
|
param: ['boolean', 'number', 'string'],
|
|
body: ['bigint', 'date'],
|
|
response: ['bigint', 'date'],
|
|
},
|
|
},
|
|
useDates: true,
|
|
useBigInt: true,
|
|
},
|
|
},
|
|
},
|
|
});
|