Specify project
Server
To Reproduce
- Remove below code in
client/src/App.tsx
- Type this in the terminal
- See the error
Expected behavior
No error when running yarn tsc
Screenshots
Describe the bug
There is a type error in the below code.
// client/src/App.tsx
const initUser = async (me: AppUserQueryResponse['me']): Promise<void> => {
if (!me) return;
await initializeEThree(me.id);
setUser(me);
};
The error occurs in setUser(me);
because the type of argument me
is not compatible with the type of setUser
func's argument.
A) The type of argument me
type AppUserQueryResponse['me']
// src/__generated__/AppUserQuery.graphql.ts
export type AppUserQueryResponse = {
readonly me: {
readonly id: string;
readonly email: string | null;
readonly verified: boolean | null;
readonly profile: {
readonly authType: AuthType;
} | null;
};
};
-> type AuthType
// src/__generated__/AppUserQuery.graphql.ts
export type AuthType = "apple" | "email" | "facebook" | "google" | "%future added value";
B) the type of setUser
func's argument
type User
// src/providers/AuthProvider.tsx
const setUser = (dispatch: React.Dispatch<SetUserAction>) => (
authUser: User,
): void => {
if (!authUser) Relay.init();
dispatch({
type: ActionType.SetUser,
payload: { user: authUser, relay: Relay.environment },
});
};
// src/types/graphql.ts
export type User = {
__typename?: 'User';
id: Scalars['String'];
email?: Maybe<Scalars['String']>;
name?: Maybe<Scalars['String']>;
nickname?: Maybe<Scalars['String']>;
thumbURL?: Maybe<Scalars['String']>;
photoURL?: Maybe<Scalars['String']>;
birthDay?: Maybe<Scalars['DateTime']>;
gender?: Maybe<Scalars['Gender']>;
phone?: Maybe<Scalars['String']>;
statusMessage?: Maybe<Scalars['String']>;
verified?: Maybe<Scalars['Boolean']>;
lastSignedIn?: Maybe<Scalars['DateTime']>;
isOnline?: Maybe<Scalars['Boolean']>;
createdAt?: Maybe<Scalars['DateTime']>;
updatedAt?: Maybe<Scalars['DateTime']>;
deletedAt?: Maybe<Scalars['DateTime']>;
profile?: Maybe<Profile>;
notifications?: Maybe<Array<Notification>>;
};
-> type AuthType
// src/types/graphql.ts
export enum AuthType {
email = 'email',
facebook = 'facebook',
google = 'google',
apple = 'apple'
}
As you can see A) AuthType in src/__generated__/AppUserQuery.graphql.ts
is union type, but B) AuthType in src/types/graphql.ts
is enum type, which makes an error since union type is not compatible with enum type.
As we know the problem, we could simply check there is no error occurred if we change AuthType's type from union to enum.
// src/__generated__/AppUserQuery.graphql.ts
// export type AuthType = "apple" | "email" | "facebook" | "google" | "%future added value";
export enum AuthType {
email = 'email',
facebook = 'facebook',
google = 'google',
apple = 'apple'
}
$ yarn tsc
yarn run v1.22.4
$ tsc
✨ Done in 5.65s.
Unfortunately, AppUserQuery.graphql.ts
is generated by relay-compiler library, which means we should not change it manually.
And it seems that this default behavior, changing enum to union type, is no problem to the community and its users according to some issues.
relay-tools/relay-compiler-language-typescript#81
relay-tools/relay-compiler-language-typescript#164
And we can't change AuthType enum type in src/types/graphql.ts
to union type either. Because AuthType enum is also generated by graphql-codegen library, and also it is widely used in the clilent side code like below and it seems irreplaceable.
// src/components/screen/Settings.tsx
switch (user?.profile?.authType) {
case AuthType.google:
signInInfoOption = {
...
// src/components/screen/SignIn.tsx
<SocialSignInButton
clientId={facebookAppId}
clientSecret={facebookSecret}
svgIcon={<SvgFacebook width={18} height={18} fill={theme.facebookIcon}/>}
onUserCreated={(user?: User): void => {
if (user) setUser(user);
}}
socialProvider={AuthType.facebook}
/>
...
So, in my opinion, we should deal with union Type AuthType in src/__generated__/AppUserQuery.graphql.ts
to fix the compatibility issue.
Possible workarounds
1. Change union type AuthType to enum Type in src/__generated__/AppUserQuery.graphql.ts
by a compiler or something else.
To be honest, I don't know how to do this.
And I'm not sure whether this change makes no side effect.
2. Current makeshift
Add // @ts-ignore ==> TODO
Related Issues
#147