Open8

prisma x Lambda

edamame88edamame88

動作させたい環境

  • pnpm workspace
  • prisma
  • Lambda (Docker, TypeScirpt)
edamame88edamame88

pnpm workspace x Docker

公式にDocker ファイルの書き方が載っている

https://pnpm.io/ja/docker

これを参考にルートディレクトリにpnpm workspace とDocker ファイルを作成

edamame88edamame88

handler.ts

import { Logger } from "@aws-lambda-powertools/logger";
import { prisma } from "database";

// Logger
const logger = new Logger({
  serviceName: "sample-lambda",
  logLevel: "INFO", // LOG_LEVELが無ければ"INFO"
});

console.log("✅DATABASE_URL", process.env.DATABASE_URL);

export const handler = async () => {
  await prisma.$queryRaw`SELECT 1`
    .then((res) => {
      logger.info(`✅prisma connection: ${res}`);
    })
    .catch((err) => {
      logger.error(`❌prisma connection: ${err}`);
    });

  logger.info("✅prisma connection: success");
  return;
};

Lambda Docker Compose file
compose.yml

services:
  sample-lambda-local:
    build:
      context: ../..
      dockerfile: Dockerfile
    environment:
      DEBUG_LOGGING_ENABLED: true
    command: ["index.handler"]
    env_file:
      - .env
    restart: always
    develop:
      watch:
        - action: rebuild
          path: ./**/*.ts
    ports:
      - "9000:8080"
    logging:
      options:
        max-size: "5m"
        max-file: "10"
    extra_hosts:
      - "host.docker.internal:host-gateway"
edamame88edamame88

Dockerfile

FROM node:22-slim AS base
ENV PNPM_HOME="/pnpm"
ENV PATH="$PNPM_HOME:$PATH"
RUN corepack enable
WORKDIR /app

# 共通のnode_modulesをinstall
FROM base AS build
COPY . .
RUN --mount=type=cache,id=pnpm,target=/pnpm/store pnpm install --frozen-lockfile

# Lambda: sample-lambda
FROM build AS sample-lambda-builder
COPY --from=build /app/node_modules ./node_modules
COPY --from=build /app/packages/sample-lambda ./packages/sample-lambda
COPY --from=build /app/packages/db ./packages/db
COPY --from=build /app/.npmrc ./
RUN pnpm --filter db build
RUN pnpm --filter sample-lambda build

FROM public.ecr.aws/lambda/nodejs:22 AS sample-lambda
WORKDIR /var/task
COPY --from=sample-lambda-builder /app/packages/sample-lambda/dist ./
COPY --from=sample-lambda-builder /app/packages/sample-lambda/node_modules ./node_modules
CMD ["index.handler"]
edamame88edamame88

エラーログ

sample-lambda-local-1  | 06 Mar 2025 22:06:01,994 [INFO] (rapid) exec '/var/runtime/bootstrap' (cwd=/var/task, handler=)
sample-lambda-local-1  | START RequestId: 38fde6ad-d69c-4fa8-85f0-44a3f5b8bbab Version: $LATEST
sample-lambda-local-1  | 06 Mar 2025 22:06:08,981 [INFO] (rapid) INIT START(type: on-demand, phase: init)
sample-lambda-local-1  | 06 Mar 2025 22:06:08,981 [INFO] (rapid) The extension's directory "/opt/extensions" does not exist, assuming no extensions to be loaded.
sample-lambda-local-1  | 06 Mar 2025 22:06:08,981 [INFO] (rapid) Starting runtime without AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY, AWS_SESSION_TOKEN , Expected?: false
sample-lambda-local-1  | 2025-03-06T22:06:09.168Z	undefined	INFO	✅DATABASE_URL postgresql://postgres:postgres-password@localhost:5432/sandbox?schema=public
sample-lambda-local-1  | 06 Mar 2025 22:06:09,176 [INFO] (rapid) INIT RTDONE(status: success)
sample-lambda-local-1  | 06 Mar 2025 22:06:09,176 [INFO] (rapid) INIT REPORT(durationMs: 195.231000)
sample-lambda-local-1  | 06 Mar 2025 22:06:09,176 [INFO] (rapid) INVOKE START(requestId: 90e6d7e0-6ae1-48ca-a4ac-10d06db15a33)
sample-lambda-local-1  | {"level":"ERROR","message":"❌prisma connection: PrismaClientInitializationError: \nInvalid `t=Object.create()` invocation in\n/var/task/index.js:31:2537\n\n  28 Note that ${a.bold(\"include\")} statements only accept relation fields.`,o})}function Gp(e,t,r){let n=t.arguments.getDeepSubSelectionValue(e.selectionPath)?.asObject();if(n){let i=n.getField(\"omit\")?.value.asObject();if(i){Jp(e,t,i);return}if(n.hasField(\"select\")){Wp(e,t);return}}if(r?.[xt(e.outputType.name)]){Hp(e,t);return}t.addErrorMessage(()=>`Unknown field at \"${e.selectionPath.join(\".\")} selectio
edamame88edamame88

エンジンファイルがうまく読み込めていないみたい。
/tmp/prisma-engines/ にlibquery_engine-*.so.nodeを配置するとうまくいきました。

https://github.com/prisma/prisma/discussions/22519#discussioncomment-12038618

FROM node:22-slim AS base
ENV PNPM_HOME="/pnpm"
ENV PATH="$PNPM_HOME:$PATH"
RUN corepack enable
WORKDIR /app

# 共通のnode_modulesをinstall
FROM base AS build
COPY . .
RUN --mount=type=cache,id=pnpm,target=/pnpm/store pnpm install --frozen-lockfile

# Lambda: sample-lambda
FROM build AS sample-lambda-builder
COPY --from=build /app/node_modules ./node_modules
COPY --from=build /app/packages/sample-lambda ./packages/sample-lambda
COPY --from=build /app/packages/db ./packages/db
COPY --from=build /app/.npmrc ./
RUN pnpm --filter db build
RUN pnpm --filter sample-lambda build

FROM public.ecr.aws/lambda/nodejs:22 AS sample-lambda
WORKDIR /var/task
+ COPY --from=sample-lambda-builder /app/packages/db/generated/client/libquery_engine-*.so.node /tmp/prisma-engines/
COPY --from=sample-lambda-builder /app/packages/sample-lambda/dist ./
COPY --from=sample-lambda-builder /app/packages/sample-lambda/node_modules ./node_modules
CMD ["index.handler"]