eddeee888 / graphql-code-generator-plugins

List of GraphQL Code Generator plugins that complements the official plugins.
MIT License
51 stars 12 forks source link

Drizzle types as Mappers not picked up #245

Closed marceloverdijk closed 5 months ago

marceloverdijk commented 6 months ago

Sample repo with the reproducible issue can be found here

Config:

import type { CodegenConfig } from '@graphql-codegen/cli';
import { defineConfig } from '@eddeee888/gcg-typescript-resolver-files';

const config: CodegenConfig = {
  schema: './src/graphql/schema.graphql',
  generates: {
    'src/graphql/schema': defineConfig({
      mode: 'merged',
    }),
  },
};

export default config;

schema.graphql:

scalar CountryCode

type Query {
    continents(first: Int = 10, offset: Int = 0): [Continent!]
    continent(id: ID!): Continent
    countries(first: Int = 10, offset: Int = 0): [Country!]
    country(id: ID!): Country
}

type Continent {
    id: ID!
    code: String!
    name: String!
}

type Country {
    id: ID!
    code: CountryCode!
    name: String!
    continent: Continent!
}

schema.mappers.ts:

// Exported mappers from Drizzle don't work...

// export type { Continent as ContinentMapper } from '@/model/schema';
export type { Country as CountryMapper } from '../drizzle/schema';

// Manual mappers do work though...

export interface ContinentMapper {
  id: string;
  code: string;
};

Drizzle schema.ts:

import { sqliteTable, text } from 'drizzle-orm/sqlite-core';

export const continent = sqliteTable(
  'continent',
  {
      id: text('id').primaryKey(),
      name: text('name').notNull(),
  },
);

export type Continent = typeof continent.$inferSelect;

export const country = sqliteTable(
  'country',
  {
      id: text('id').primaryKey(),
    alpha2Code: text('alpha2_code').notNull(),
      name: text('name').notNull(),
    continentId: text('continent_id').notNull().references(() => continent.id),
  },
);

export type Country = typeof country.$inferSelect;

Generated Continent.ts:

import type   { ContinentResolvers } from './types.generated';
    export const Continent: ContinentResolvers = {
    /* Implement Continent resolver logic here */
        name: () => { /* Continent.name resolver is required because Continent.name exists but ContinentMapper.name does not */ }
    };

This is as expected, as indeed the ContinentMapper.name does not exist.

Generated Country.ts:

import type   { CountryResolvers } from './types.generated';
    export const Country: CountryResolvers = {
    /* Implement Country resolver logic here */
        code: () => { /* Country.code resolver is required because Country.code exists but CountryMapper.code does not */ },
        continent: () => { /* Country.continent resolver is required because Country.continent exists but CountryMapper.continent does not */ },
        id: () => { /* Country.id resolver is required because Country.id exists but CountryMapper.id does not */ },
        name: () => { /* Country.name resolver is required because Country.name exists but CountryMapper.name does not */ }
    };

ISSUE:

id and name are part of the drizzle/schema#Country type, which is exported in schema.mappers.ts as CountryMapper, yet the generated CountryResolvers is not regnosing them, and generated a unwanted resolvers for them.

Note that in types.generated.ts the CountryMapper is imported, so at least it seems to have picked up that mapper:

import { GraphQLResolveInfo, GraphQLScalarType, GraphQLScalarTypeConfig } from 'graphql';
import { ContinentMapper, CountryMapper } from './../schema.mappers';
..
marceloverdijk commented 6 months ago

Maybe this is related to https://github.com/eddeee888/graphql-code-generator-plugins/pull/242 ? Are you planning a new release soon?

eddeee888 commented 5 months ago

Hi @marceloverdijk ! Yes, I'm going to release a new patch soon. Apologies, I missed your issue in the last few weeks 🙏

Could you try this alpha version to see if it fixes your issue please?

yarn add -ED @eddeee888/gcg-typescript-resolver-files@pr242-run423-1
marceloverdijk commented 5 months ago

No worries. Not sure if I can test it the coming days, but looking forward to the new release anyway.

marceloverdijk commented 5 months ago

@eddeee888 I did a quick test with @eddeee888/gcg-typescript-resolver-files@pr242-run423-1 but I get the same result unfortunately:

@@ -1,8 +1,8 @@
 import type   { CountryResolvers } from './types.generated';
     export const Country: CountryResolvers = {
     /* Implement Country resolver logic here */
-        code: () => { /* Country.code resolver is required because Country.code exists but CountryMapper.code does not */ },
-        continent: () => { /* Country.continent resolver is required because Country.continent exists but CountryMapper.continent does not */ },
-        id: () => { /* Country.id resolver is required because Country.id exists but CountryMapper.id does not */ },
-        name: () => { /* Country.name resolver is required because Country.name exists but CountryMapper.name does not */ }
+        code: async (_parent, _arg, _ctx) => { /* Country.code resolver is required because Country.code exists but CountryMapper.code does not */ },
+        continent: async (_parent, _arg, _ctx) => { /* Country.continent resolver is required because Country.continent exists but CountryMapper.continent does not */ },
+        id: async (_parent, _arg, _ctx) => { /* Country.id resolver is required because Country.id exists but CountryMapper.id does not */ },
+        name: async (_parent, _arg, _ctx) => { /* Country.name resolver is required because Country.name exists but CountryMapper.name does not */ }
     };

Note the async part was added which is I assume another update in the alpha version.

eddeee888 commented 5 months ago

Ah I see, thanks for trying it! I will take a look deeper into your issue tonight 👀

eddeee888 commented 5 months ago

Hi @marceloverdijk,

I've got a PR ready: https://github.com/eddeee888/graphql-code-generator-plugins/pull/248

Could you try this alpha version please:

yarn add -DE @eddeee888/gcg-typescript-resolver-files@pr248-run448-1
marceloverdijk commented 5 months ago

Hi @eddeee888 yes that solves it 🥳

The resolver is now genereated as expected:

import type { CountryResolvers } from './types.generated';
export const Country: CountryResolvers = {
  /* Implement Country resolver logic here */
  code: async (_parent, _arg, _ctx) => {
    /* Country.code resolver is required because Country.code exists but CountryMapper.code does not */
  },
  continent: async (_parent, _arg, _ctx) => {
    /* Country.continent resolver is required because Country.continent exists but CountryMapper.continent does not */
  },
};

Thx a lot!

eddeee888 commented 5 months ago

This fix is now released in v0.7.5 Thank you for reporting and collaborating with me throughout this process! 🕺