Graphql-code-generator: [TS] Types are incorrect for some conditional fragments

Created on 21 May 2019  路  2Comments  路  Source: dotansimha/graphql-code-generator

Describe the bug

When using conditional fragments, the generated types use TS intersection types to represent GraphQL union types. This causes issues when using __typename as a discriminant.

To Reproduce
This is a contrived example, but should be enough to reproduce the behavior:

  1. My GraphQL schema:
scalar Date
scalar PaymentSourceId

# Abstraction for payment sources like Stripe, Paypal, ACH etc.
interface PaymentSource {
  id: PaymentSourceId!
  createdAt: Date
  updatedAt: Date
}

type PaypalPaymentSource implements PaymentSource {
  id: PaymentSourceId!
  createdAt: Date
  updatedAt: Date

  # PayPal specific attributes
  paymentId: String!
}

type StripePaymentSource implements PaymentSource {
  id: PaymentSourceId!
  createdAt: Date
  updatedAt: Date

  # Stripe specific attributes
  owner: String
}
  1. My GraphQL operations:
fragment PaymentSource on PaymentSource {
  id
  type
  ... on StripePaymentSource {
    owner 
  }
}
  1. My codegen.yml config file:
generates:
  src/generated/graphql.tsx:
    plugins:
      - 'typescript'
      - 'typescript-operations'
      - 'typescript-react-apollo'
    config:
      skipTypename: false
      nonOptionalTypename: true
      avoidOptionals: false

Generated types
The types are here: https://gist.github.com/cecchi/54c96b5c8c681da22478390c7a07df61

The relevant type is:

export type PaymentSourceFragment = {
  __typename?:
    | "PaypalPaymentSource"
    | "AffirmPaymentSource"
    | "StripePaymentSource";
} & Pick<PaymentSource, "id"> &
  ({ __typename?: "StripePaymentSource" } & Pick<StripePaymentSource, "owner">);

Expected behavior

The fragment PaymentSourceFragment is typed in such a way that the __typename is explicitly "StripePaymentSource", because that is the only type that we defined a conditional fragment for. The value "PaypalPaymentSource" should still be an acceptable __typename for that fragment. This is an issue when using the typename as a discriminant (for example, if we wanted to render distinct UIs for Paypal and Stripe, but we only required additional data beyond the common fields for the Stripe UI).

Screen Shot 2019-05-20 at 6 04 12 PM

bug plugins

All 2 comments

Hi @cecchi , I think it's fixed in this PR as well: https://github.com/dotansimha/graphql-code-generator/pull/1923

Awesome, thanks!

Was this page helpful?
0 / 5 - 0 ratings

Related issues

quolpr picture quolpr  路  3Comments

NickClark picture NickClark  路  3Comments

iamdanthedev picture iamdanthedev  路  3Comments

dotansimha picture dotansimha  路  3Comments

SimenB picture SimenB  路  3Comments