Search code examples
node.jsnext.jsprisma

How to run Prisma seed file in NextJS


Prisma normally allows you to run a seed.ts file on your NextJS project to populate your DB with data after you run npx prisma migrate dev.

To do this this, you write your seed.ts file and then add the following to your package.json:

seed.ts:

import logger from "../utils/pino-logger";
import { BytesLike, ethers } from "ethers";
import { PrismaClient } from "@prisma/client";
const prisma = new PrismaClient();

async function main() {
  const wallet = new ethers.Wallet(process.env.PRIVATE_KEY! as BytesLike);
  const nonce = await prisma.wallet.create({
    data: {
      nonce: await wallet.getTransactionCount("pending"),
    },
  });

  logger.debug({ nonce: nonce });
}

main()
  .then(async () => {
    await prisma.$disconnect();
  })
  .catch(async (e) => {
    console.error(e);
    await prisma.$disconnect();
    process.exit(1);
  });

package.json

"prisma": {
  "seed": "ts-node prisma/seed.ts"
},

I have tried this option, but it gives me the following error:

import logger from "utils/pino-logger";
^^^^^^

SyntaxError: Cannot use import statement outside a module
    at Object.compileFunction (node:vm:352:18)
    at wrapSafe (node:internal/modules/cjs/loader:1032:15)
    at Module._compile (node:internal/modules/cjs/loader:1067:27)
    at Module.m._compile (/Users/dimitriborgers/Documents/3mint/3mint-core/node_modules/ts-node/src/index.ts:1618:23)
    at Module._extensions..js (node:internal/modules/cjs/loader:1155:10)
    at Object.require.extensions.<computed> [as .ts] (/Users/dimitriborgers/Documents/3mint/3mint-core/node_modules/ts-node/src/index.ts:1621:12)
    at Module.load (node:internal/modules/cjs/loader:981:32)
    at Function.Module._load (node:internal/modules/cjs/loader:822:12)
    at Function.executeUserEntryPoint [as runMain] (node:internal/modules/run_main:77:12)
    at phase4 (/Users/dimitriborgers/Documents/3mint/3mint-core/node_modules/ts-node/src/bin.ts:649:14)

Prisma recommends using ts-node --compiler-options {\"module\":\"CommonJS\"} prisma/seed.ts if you're having an issue. But, if I do this, I get this error:

Error: Cannot find module 'utils/pino-logger'
Require stack:
- /Users/dimitriborgers/Documents/3mint/3mint-core/prisma/seed.ts
    at Function.Module._resolveFilename (node:internal/modules/cjs/loader:933:15)
    at Function.Module._resolveFilename.sharedData.moduleResolveFilenameHook.installedValue [as _resolveFilename] (/Users/dimitriborgers/Documents/3mint/3mint-core/node_modules/@cspotcode/source-map-support/source-map-support.js:811:30)
    at Function.Module._load (node:internal/modules/cjs/loader:778:27)
    at Module.require (node:internal/modules/cjs/loader:1005:19)
    at require (node:internal/modules/cjs/helpers:102:18)
    at Object.<anonymous> (/Users/dimitriborgers/Documents/3mint/3mint-core/prisma/seed.ts:1:1)
    at Module._compile (node:internal/modules/cjs/loader:1103:14)
    at Module.m._compile (/Users/dimitriborgers/Documents/3mint/3mint-core/node_modules/ts-node/src/index.ts:1618:23)
    at Module._extensions..js (node:internal/modules/cjs/loader:1155:10)
    at Object.require.extensions.<computed> [as .ts] (/Users/dimitriborgers/Documents/3mint/3mint-core/node_modules/ts-node/src/index.ts:1621:12) {
  code: 'MODULE_NOT_FOUND',
  requireStack: [ '/Users/dimitriborgers/Documents/3mint/3mint-core/prisma/seed.ts' ]
}

I'm using ts.config to put a base url of "baseUrl": ".". However, even if I change that and fix the error for pino-logger, the issue pops up for ethers, which is a library I don't really control (and would rather not do an absolute path to a node module).

Running seed command `ts-node --compiler-options {"module":"CommonJS"} prisma/seed.ts` ...
TypeError: Cannot read properties of undefined (reading 'toHexString')
    at isHexable (/Users/dimitriborgers/Documents/3mint/3mint-core/node_modules/@ethersproject/bytes/src.ts/index.ts:58:21)
    at hexlify (/Users/dimitriborgers/Documents/3mint/3mint-core/node_modules/@ethersproject/bytes/src.ts/index.ts:228:9)
    at new SigningKey (/Users/dimitriborgers/Documents/3mint/3mint-core/node_modules/@ethersproject/signing-key/src.ts/index.ts:35:51)
    at new Wallet (/Users/dimitriborgers/Documents/3mint/3mint-core/node_modules/@ethersproject/wallet/src.ts/index.ts:87:36)
    at /Users/dimitriborgers/Documents/3mint/3mint-core/prisma/seed.ts:7:18
    at step (/Users/dimitriborgers/Documents/3mint/3mint-core/prisma/seed.ts:33:23)
    at Object.next (/Users/dimitriborgers/Documents/3mint/3mint-core/prisma/seed.ts:14:53)
    at /Users/dimitriborgers/Documents/3mint/3mint-core/prisma/seed.ts:8:71
    at new Promise (<anonymous>)
    at __awaiter (/Users/dimitriborgers/Documents/3mint/3mint-core/prisma/seed.ts:4:12)

Any way to fix this??


Solution

  • There's a few things going on here. I'll try to explain why your earlier attempts had issues below, but your last attempt with ts-node --compiler-options {"module":"CommonJS"} prisma/seed.ts is the closest. The error you are receiving sounds like process.env.PRIVATE_KEY is not set. Try logging that value or hardcoding it to verify. If you're using a .env file, you'll probably need to call dotenv manually at the start of the file or register it on the CLI. The dotenv README has some usage examples.

    For your first attempt with ts-node prisma/seed.ts, the error Cannot use import statement outside a module indicates that Node is running in CommonJS mode, but the code it's trying to run uses the modern module syntax with import or export. When you added --compiler-options {\"module\":\"CommonJS\"}, TypeScript started converting the import to require instead. See the TypeScript module docs for more info on that.

    For the next issue, you noted that you had "baseUrl": "." for the utils/pino-logger import and it still couldn't find it. That's because the tsconfig.json file only tells TypeScript to allow imports relative to the root directory, but TypeScript doesn't rewrite the module paths or influence Node's resolution strategy. For more details on that see this GitHub issue or this Stack Overflow question.

    I hope that's helpful!