oguimbal / pg-mem

An in memory postgres DB instance for your unit tests
MIT License
1.95k stars 94 forks source link

Unable to run drizzle-orm migration using pg-mem #311

Closed JasoonS closed 1 month ago

JasoonS commented 1 year ago

Describe the bug

When running drizzle migrations I get the following error:

/home/jasoons/Documents/code/float/temp/drizzle-pg-mem-example/node_modules/pg-mem/index.js:1388
    const type = value.type;
                       ^

TypeError: Cannot read properties of null (reading 'type')

💥 This is a nasty error, which was unexpected by pg-mem. Also known "a bug" 😁 Please file an issue !

*️⃣ Failed SQL statement: insert into "drizzle"."__drizzle_migrations" ("hash", "created_at") values($1, $2);

👉 You can file an issue at https://github.com/oguimbal/pg-mem along with a way to reproduce this error (if you can), and  the stacktrace:

    at checkNotUntypedArray (/home/jasoons/Documents/code/float/temp/drizzle-pg-mem-example/node_modules/pg-mem/index.js:1388:24)
    at buildValue (/home/jasoons/Documents/code/float/temp/drizzle-pg-mem-example/node_modules/pg-mem/index.js:1380:5)
    at /home/jasoons/Documents/code/float/temp/drizzle-pg-mem-example/node_modules/pg-mem/index.js:9272:60
    at Array.map (<anonymous>)
    at /home/jasoons/Documents/code/float/temp/drizzle-pg-mem-example/node_modules/pg-mem/index.js:9268:52
    at Array.map (<anonymous>)
    at /home/jasoons/Documents/code/float/temp/drizzle-pg-mem-example/node_modules/pg-mem/index.js:9268:35
    at StackOf.usingValue (/home/jasoons/Documents/code/float/temp/drizzle-pg-mem-example/node_modules/pg-mem/index.js:1117:24)
    at new ValuesTable (/home/jasoons/Documents/code/float/temp/drizzle-pg-mem-example/node_modules/pg-mem/index.js:9260:37)
    at buildValues (/home/jasoons/Documents/code/float/temp/drizzle-pg-mem-example/node_modules/pg-mem/index.js:3227:17) {
  location: { start: 0, end: 0 },
  [Symbol(errorDetailsIncluded)]: true
}

To Reproduce

git clone git@github.com:JasoonS/drizzle-pg-mem-example.git
cd drizzle-pg-mem-example
yarn
yarn start-mem # you can run `yarn start` with a postgres database already running locally to see it working.

pg-mem version

2.6.12

mkvlrn commented 1 year ago

Still happens in version 2.6.13. It would be a godsend to have this working in projecst using drizzle-orm.

MateWW commented 1 year ago

I've dived deeper into the root cause of this error. It seems that the error is happening because Drizzle is calling queries in some mixed way.

client.query({ text: `INSERT INTO "drizzle"."__drizzle_migrations" ("hash", "created_at") VALUES ($1, $2);` }, [
  'e42357b891c213208519fe4696442450b98c6fcbd32562a6eab5bfd1225b5b3f',
  1690826882833
])

Based on node-postgress docs they recommend using either:

client.query(`INSERT INTO "drizzle"."__drizzle_migrations" ("hash", "created_at") VALUES ($1, $2);`, [
  'e42357b891c213208519fe4696442450b98c6fcbd32562a6eab5bfd1225b5b3f',
  1690826882833
])

or

client.query({ 
text: `INSERT INTO "drizzle"."__drizzle_migrations" ("hash", "created_at") VALUES ($1, $2);`, 
values: [
  'e42357b891c213208519fe4696442450b98c6fcbd32562a6eab5bfd1225b5b3f',
  1690826882833
]})

Inside pg-mem method called adaptQuery doesn't support such a mixed approach. I was able to work around this issue by propagating values to query when query.values doesn't exist.

           private adaptQuery(query: string | PgQuery, values: any): PgQuery {
              if (typeof query === 'string') {
                  query = {
                      text: query,
                      values,
                  };
              } else {
                  // clean copy to avoid mutating things outside our scope
                  query = { ...query, values: query.values || values };  // <- before it was `{ ...query }`
              }
              if (!query.values?.length) {
                  return query;
              }

              if (query.types?.getTypeParser) {
                  throw new NotSupported('getTypeParser is not supported');
              }

              // console.log(query);
              // console.log('\n');

              query.text = replaceQueryArgs$(query.text, query.values);
              return query;
          }

I'm not sure where this should be fixed. Is that something that pg-mem could support or drizzle internally should avoid using this "mixed" approach?

TheKeveloper commented 5 months ago

I'm also running into this issue when trying to test drizzle. @MateWW are you considering submitting a PR to pg-mem with your fix?

carlhopf commented 4 months ago

@MateWW the proposed fix works great with my unit tests 👍

i think we should fix it here in pg-mem, since it seems to be a supported use-case of node-postgres