Getting @prisma/client to work
See original GitHub issueTrying to transition from mikro-orm to prisma this week, I immediately ran up against one issue mentioned in #841, specifically:
ERROR { Error:
Invalid 'prisma.post.findMany()' invocation:
EROFS: read-only file system, chmod '/var/task/pages/api/query-engine-rhel-openssl-1.0.x'
at PrismaClientFetcher.request (/var/task/pages/api/drafts.js:206:52123)
at process._tickCallback (internal/process/next_tick.js:68:7) code: 'EROFS', meta: undefined }
After searching around, I saw many of the issues were either out of date (webpack configs don’t need to be touched anymore) or linked to solutions not meant for this repository. Quickly, I want to outline the extra two steps I took to make this work. As mentioned also in #841, this seems to be a problem with aws-lambda
not respecting file permissions on upload, and thus not allowing the Prisma binary to be executed. To get around this, we can copy to /tmp
before we run Prisma. (I wonder if there’s a way we can get a build.postDeploy
step, where we can run a copy command instead of having to do these sorts of modifications inside the app?).
Step 1
I initialize Prisma once for my project in /config/prisma.js
Inside there, I only had
import { PrismaClient } from "@prisma/client"
const Prisma = new PrismaClient();
export default Prisma;
To add the copy on app initialization, I modified it to be:
import { PrismaClient } from "@prisma/client";
import fs from "fs";
import { spawnSync } from "child_process";
if (process.env.NODE_ENV === "production") {
const binaryPath = "/tmp/query-engine-rhel-openssl-1.0.x";
if (!fs.existsSync(binaryPath)) {
spawnSync("cp", [
`${process.env.LAMBDA_TASK_ROOT}/node_modules/.prisma/client/query-engine-rhel-openssl-1.0.x`,
"/tmp/",
]);
spawnSync("chmod", [`555`, "/tmp/query-engine-rhel-openssl-1.0.x"]);
}
}
const Prisma = new PrismaClient();
export default Prisma;
Step 2
This on it’s own does not work, because it is still looking in the wrong place for the binary. But as mentioned in the Prisma doc we can define custom paths for the binaries. Therefore I added
PRISMA_QUERY_ENGINE_BINARY = /tmp/query-engine-rhel-openssl-1.0.x
to my .env
file
Finally, make sure you’ve read this guide and added this to your prisma/schema.prisma
file
generator client {
provider = "prisma-client-js"
binaryTargets = ["native", "rhel-openssl-1.0.x"]
}
Conclusion
Im not sure if a build.postDeploy
step (I believe the Vercel platform has this now to facilitate Prisma specifically) to allow copying of files or a change/patch to aws-lambda
could mitigate these steps, but it feels sort of hacky to get Prisma working this way. If anyone has better solutions, I’d love to hear them.
Issue Analytics
- State:
- Created 3 years ago
- Comments:13
Top GitHub Comments
I turns out that the binaries were not copied into the lambda. This could be solved by adding a script that triggers before upload. I have set a template up for prisma + serverless-next.js which adds a
postBuildCommands
(serverless.yml
) script to do just that.@millsp got something working. serverless-nextjs-js’s cdk construct doesn’t seem to have a way to have post command. Basically just manually move stuff after builder has finished.