import { createHabitRoutes } from "./habits/routes"; import { ApiError } from "./habits/service"; import { Hono } from "hono"; import { sql } from "drizzle-orm"; import { createAuth, type AppDatabase, type AuthEnv } from "./auth"; import type { AuthConfig } from "./auth/config"; import type { FetchDiscord } from "./auth/discord"; import { createSharingRoutes, type DiscordFetch } from "./sharing/routes"; import type { DiscordSharingConfig } from "./sharing/config"; export function createApi(db: AppDatabase, config: AuthConfig, request?: FetchDiscord, now?: () => number, discordRequest?: DiscordFetch, sharingConfig: DiscordSharingConfig = { token: "", channelId: "" }) { const app = new Hono(); const auth = createAuth(db, config, request, now); app.get("/api/health", c => { db.get(sql`SELECT 1`); return c.json({ status: "ok" }); }); app.route("/api/auth", auth.routes); app.get("/api/me", auth.requireAuth, c => c.json(c.get("user"))); app.route("/api", createHabitRoutes(db, auth, now ?? Date.now)); app.route("/api/sharing", createSharingRoutes(db, auth, sharingConfig, now ?? Date.now, discordRequest)); app.notFound(c => c.json({ error: "Not found" }, 404)); app.onError((_error, c) => { c.header("Cache-Control", "no-store"); if (_error instanceof ApiError) return c.json({ error: _error.message }, _error.status); return c.json({ error: "Internal server error" }, 500); }); return app; }