-
-
Save crashmax-dev/96b0a95d7e4a091dcbc3e9f2c9a52195 to your computer and use it in GitHub Desktop.
reatomGql real example
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { fingerprint } from 'src/infrastructure/fingerprint'; | |
import { Client, fetchExchange, makeOperation, mapExchange } from 'urql'; | |
export const client = new Client({ | |
url: '/api/graphql', | |
requestPolicy: 'network-only', | |
exchanges: [ | |
mapExchange({ | |
async onOperation(operation) { | |
return makeOperation(operation.kind, operation, { | |
...operation.context, | |
fetchOptions: { | |
headers: { | |
fingerprint, | |
'apollo-require-preflight': 'true', | |
}, | |
}, | |
}); | |
}, | |
}), | |
// It is important that fetchExchange should follow after mapExchange. | |
fetchExchange, | |
], | |
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { atom, onConnect, withDataAtom } from '@reatom/framework'; | |
import { ROUTES } from 'src/config/routes'; | |
import { reatomQuery } from 'src/infrastructure/graphql/reatomGql'; | |
import { GET_LIST } from 'src/queries/list'; | |
const paginationAtom = atom(100); | |
export const fetchList = reatomQuery(GET_LIST, (ctx, id: string) => ({ | |
id, | |
take: ctx.get(paginationAtom), | |
})).pipe(withDataAtom([])); | |
onConnect(fetchVisitsList.dataAtom, (ctx) => { | |
const id = ctx.get(ROUTES.LIST.params.id); | |
id && fetchList(ctx, id); | |
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { parseAtoms, noop, type Atom, atom } from '@reatom/framework'; | |
import { | |
type GqlAction, | |
reatomGql, | |
SKIP, | |
type CtxGql, | |
} from 'src/infrastructure/graphql'; | |
import { type TypedDocumentNode } from 'urql'; | |
import { type z } from 'zod'; | |
import { reatomZod } from './reatomZod'; | |
import { type PartialDeep, type ZodAtomization } from './reatomZod/types'; | |
export const reatomZodGql = < | |
Schema extends z.ZodFirstPartySchemaTypes, | |
VariableData, | |
>( | |
type: Schema, | |
{ | |
name, | |
query, | |
prepare, | |
initState, | |
type: gqlType = 'mutation', | |
debounce = 500, | |
}: { | |
name: string; | |
query: TypedDocumentNode<any, { data: VariableData }>; | |
prepare: (ctx: CtxGql, data: z.infer<Schema>) => SKIP | VariableData; | |
initState?: PartialDeep<z.infer<Schema>>; | |
type?: 'query' | 'mutation'; | |
debounce?: number; | |
}, | |
): { | |
model: ZodAtomization<Schema>; | |
state: Atom<z.infer<Schema>>; | |
sync: GqlAction<unknown, [], z.infer<Schema>>; | |
} => { | |
const state = atom((ctx) => parseAtoms(ctx, model), `${name}.state`); | |
const fetchQuery = reatomGql({ | |
type: gqlType, | |
query, | |
prepare: (ctx) => { | |
const data = prepare(ctx, ctx.get(state)); | |
return data === SKIP ? SKIP : { data }; | |
}, | |
debounce, | |
abort: 'last-in-win', | |
}); | |
const model = reatomZod(type, { | |
sync: (ctx) => { | |
fetchQuery(ctx).catch(noop); | |
}, | |
initState, | |
name, | |
}); | |
return { | |
model, | |
sync: fetchQuery, | |
state, | |
}; | |
}; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
export const updateNotificationPreference = reatomMutation( | |
UPDATE_NOTIFICATIONS_PREFERENCES, | |
(ctx, item: NotificationPreference) => ({ preferences: [item] }), | |
).pipe( | |
withStatusesAtom(), | |
withStatusNotification({ | |
success: 'account:notifications.success', | |
error: 'account:notifications.error', | |
}), | |
); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { onConnect, withCache, withDataAtom } from '@reatom/framework'; | |
import { ROUTES } from 'src/config/routes'; | |
import { | |
reatomMutation, | |
reatomQuery, | |
} from 'src/infrastructure/graphql/reatomGql'; | |
import { AUTH_QUERIES } from 'src/queries/user/auth'; | |
import { ME } from 'src/queries/user/profile'; | |
export const fetchMe = reatomQuery(ME).pipe( | |
withDataAtom(null, (ctx, data) => data.me), | |
withCache({ length: 1, staleTime: Infinity, swr: false }), | |
); | |
onConnect(fetchMe.dataAtom, fetchMe); | |
export const logout = reatomMutation(AUTH_QUERIES.LOGOUT); | |
logout.onSettle.onCall(() => { | |
// TODO just recrate Reatom ctx in the app root and stay with SPA | |
// ensure to drop whole states | |
window.location.pathname = ROUTES.LOGIN.abs; | |
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { type AsyncAction } from "@reatom/framework"; | |
import { t, type Namespace, type TFuncKey } from "i18next"; | |
import { notification } from "src/shared/notifications"; | |
export const withErrorNotification = | |
<T extends AsyncAction>(key: TFuncKey<Namespace>) => | |
(anAsync: T): T => { | |
anAsync.onReject.onCall((ctx, error) => | |
notification.error({ message: t(key) as string }) | |
); | |
return anAsync; | |
}; | |
export const withStatusNotification = | |
<T extends AsyncAction>({ | |
success, | |
error, | |
}: { | |
success?: TFuncKey<Namespace>; | |
error?: TFuncKey<Namespace>; | |
}) => | |
(anAsync: T): T => { | |
if (error) { | |
anAsync.onReject.onCall((ctx, e) => | |
notification.error({ message: t(error) as string }) | |
); | |
} | |
if (success) { | |
anAsync.onFulfill.onCall((ctx, e) => | |
notification.success({ message: t(success) as string }) | |
); | |
} | |
return anAsync; | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment