1import * as Prisma from "alchemy/Prisma";
2import * as Config from "effect/Config";
3import * as Effect from "effect/Effect";
4import { HttpServerRequest } from "effect/http/HttpServerRequest";
5import * as HttpServerResponse from "effect/http/HttpServerResponse";
6import { Connection, Project, region, appNameConfig } from "./Database.ts";
7
8const messageConfig = Config.String("PRISMA_EFFECT_MESSAGE").pipe(
9 Effect.orElseSucceed(() => "hello from Effect-native Prisma Compute"),
10);
11
12export default class Api extends Prisma.Compute<Api>()(
13 "Api",
14 Effect.gen(function* () {
15 const project = yield* Project;
16
17 return {
18 project,
19 appName: yield* appNameConfig,
20 regionId: region,
21 branchGitName: "main",
22 main: import.meta.filename,
23 port: 3000,
24 healthCheck: { path: "/api/health" },
25 env: {
26 PRISMA_EFFECT_MESSAGE: yield* messageConfig,
27 },
28 destroyOldDeployment: true,
29 };
30 }),
31 Effect.gen(function* () {
32 const db = yield* Prisma.Connect(Connection);
33
34 return {
35 fetch: Effect.gen(function* () {
36 const request = yield* HttpServerRequest;
37 const url = new URL(request.url, "http://localhost");
38
39 if (url.pathname !== "/" && url.pathname !== "/api/health") {
40 return HttpServerResponse.text("Not found", { status: 404 });
41 }
42
43 if (request.method !== "GET") {
44 return HttpServerResponse.text("Method not allowed", { status: 405 });
45 }
46
47 yield* db.databaseUrl;
48
49 const response: Record<string, string | boolean> = {
50 ok: true,
51 mode: "effect-native",
52 databaseBinding: "ready",
53 };
54
55 if (url.pathname === "/") {
56 response.message = yield* messageConfig;
57 }
58
59 return yield* HttpServerResponse.json(response);
60 }),
61 };
62 }).pipe(Effect.provide(Prisma.ConnectBinding)),
63) {}