UNPKG

@yunu-lab/rpc-react

Version:
1 lines 29.6 kB
{"version":3,"file":"index.es","sources":["../src/store/extendStore.ts","../src/providers/RpcStoreProvider.tsx","../src/hooks/useRpc.ts","../src/hooks/createRpcHooks.ts"],"sourcesContent":["/* eslint-disable @typescript-eslint/no-explicit-any */\nimport {\n Store,\n combineReducers,\n createSlice,\n PayloadAction,\n} from \"@reduxjs/toolkit\";\nimport { RpcRepository } from \"@yunu-lab/rpc-ts\";\n\nexport interface ExtendStoreOptions {\n repository: RpcRepository<any>;\n store: Store;\n slices?: Record<string, any>;\n}\n\nexport const extendStore = (options: ExtendStoreOptions) => {\n const { repository, store, slices = {} } = options;\n\n const rpcSlice = createSlice({\n name: \"rpc\",\n initialState: {} as Record<string, Record<string | number, any>>,\n reducers: {\n setData: (\n state,\n action: PayloadAction<{\n type: string;\n data: Record<string | number, any>;\n }>\n ) => {\n const { type, data } = action.payload;\n state[type] = data;\n },\n },\n });\n\n const newReducer = combineReducers({\n ...slices,\n rpc: rpcSlice.reducer,\n });\n\n store.replaceReducer(newReducer);\n\n const unsubscribe = repository.onDataChanged((events) => {\n events.forEach((event) => {\n console.log(\n event,\n \"--------------------------------events-----------------------\"\n );\n\n const { type, payload } = event;\n const storageType = repository.getStorageType(String(type));\n\n if (storageType === \"singleton\") {\n store.dispatch(\n rpcSlice.actions.setData({\n type: String(type),\n data: payload,\n })\n );\n } else {\n const dataObject = payload.reduce(\n (acc: Record<string | number, any>, item: any) => {\n const id = item.id;\n acc[id] = item;\n return acc;\n },\n {}\n );\n\n store.dispatch(\n rpcSlice.actions.setData({\n type: String(type),\n data: dataObject,\n })\n );\n }\n });\n });\n\n return {\n store,\n repository,\n unsubscribe,\n };\n};\n","import React from \"react\";\nimport { RpcRepository } from \"@yunu-lab/rpc-ts\";\nimport { createContext } from \"react\";\n\nconst RpcContext = createContext<{\n repository: RpcRepository;\n} | null>(null);\n\nexport interface RpcProviderProps {\n children: React.ReactNode;\n repository: RpcRepository;\n}\n\nexport const RpcProvider: React.FC<RpcProviderProps> = ({\n children,\n repository,\n}) => {\n return (\n <RpcContext.Provider value={{ repository }}>\n {children}\n </RpcContext.Provider>\n );\n};\n\nexport { RpcContext }; ","/* eslint-disable @typescript-eslint/no-explicit-any */\nimport React, { useContext } from \"react\";\nimport { Rpc, RpcRepository } from \"@yunu-lab/rpc-ts\";\nimport { RpcContext } from \"../providers/RpcStoreProvider\";\n\nexport interface RpcContextType<TTypes extends Record<string, Rpc<any>>> {\n repository: RpcRepository<TTypes>;\n}\n\nexport const useRpc = <\n TTypes extends Record<string, Rpc<any>>\n>(): RpcContextType<TTypes> => {\n const context = useContext(RpcContext);\n\n if (!context) {\n throw new Error(\"useRpc must be used within an RpcProvider\");\n }\n\n const repository = React.useMemo(\n () => context.repository as unknown as RpcRepository<TTypes>,\n [context.repository]\n );\n\n return {\n repository\n };\n};","/* eslint-disable @typescript-eslint/no-explicit-any */\nimport { Message, Rpc, StorageType } from \"@yunu-lab/rpc-ts\";\nimport React from \"react\";\nimport { useSelector } from \"react-redux\";\nimport { z } from \"zod\";\nimport { useRpc } from \"./useRpc\";\n\ntype InferRpcType<T> = T extends Rpc<infer S> ? z.infer<S> : never;\n\ntype ToPascalCase<S extends string> = S extends `${infer First}_${infer Rest}`\n ? `${Capitalize<First>}${ToPascalCase<Rest>}`\n : Capitalize<S>;\n\ninterface RpcState<TTypes extends Record<string, Rpc<any>>> {\n rpc: {\n [K in keyof TTypes]?: Record<string | number, InferRpcType<TTypes[K]>>;\n };\n}\n\ntype RpcHooks<TTypes extends Record<string, Rpc<any>>> = {\n // Основные хуки для каждого типа\n [K in keyof TTypes as `use${ToPascalCase<string & K>}`]: {\n (): {\n [P in K as `${P & string}s`]: InferRpcType<TTypes[P]>[];\n } & {\n [P in K as `${P & string}Map`]: Record<\n string,\n InferRpcType<TTypes[P]>\n >;\n } & {\n findById: (id: string | number) => InferRpcType<TTypes[K]> | null;\n findAll: () => InferRpcType<TTypes[K]>[];\n mergeRpc: (\n data:\n | Record<string, Partial<InferRpcType<TTypes[K]>> | null>\n | InferRpcType<TTypes[K]>[]\n ) => void;\n };\n (id: string | number): InferRpcType<TTypes[K]> | null;\n };\n} & {\n // Хуки для полных связанных данных\n [K in keyof TTypes as `use${ToPascalCase<string & K>}FullRelatedData`]: <\n TResult = InferRpcType<TTypes[K]>\n >(\n id?: string | number\n ) => TResult | TResult[] | null;\n} & {\n // Хуки для слушателей с типизацией\n [K in keyof TTypes as `use${ToPascalCase<string & K>}Listener`]: <\n RpcStorageType extends Record<keyof TTypes, StorageType> = Record<\n keyof TTypes,\n StorageType\n >\n >(\n callback: (event: {\n type: K;\n payload: RpcStorageType[K] extends \"collection\"\n ? Array<InferRpcType<TTypes[K]>>\n : RpcStorageType[K] extends \"singleton\"\n ? InferRpcType<TTypes[K]>\n : Array<InferRpcType<TTypes[K]>>;\n }) => void\n ) => () => void;\n} & {\n // Общий слушатель данных\n useDataListener: <\n RpcStorageType extends Record<keyof TTypes, StorageType> = Record<\n keyof TTypes,\n StorageType\n >\n >(\n callback: (\n events: Array<{\n type: keyof TTypes;\n payload: RpcStorageType[keyof TTypes] extends \"collection\"\n ? Array<InferRpcType<TTypes[keyof TTypes]>>\n : RpcStorageType[keyof TTypes] extends \"singleton\"\n ? InferRpcType<TTypes[keyof TTypes]>\n : Array<InferRpcType<TTypes[keyof TTypes]>>;\n }>\n ) => void,\n options?: { types?: (keyof TTypes)[] }\n ) => () => void;\n} & {\n // Хуки для связанных данных\n [K in keyof TTypes as `use${ToPascalCase<string & K>}Related`]: <\n TTarget extends keyof TTypes\n >(\n id: string | number,\n targetType: TTarget\n ) => Array<TTypes[TTarget] extends Rpc<infer S> ? z.infer<S> : never>;\n} & {\n // Хук для обработки сообщений с полной типизацией\n useHandleMessages: () => {\n handleMessages<\n RpcStorageType extends Record<keyof TTypes, StorageType>\n >(\n messages: Array<Message<TTypes>>,\n callbacks?: {\n [K in keyof TTypes]?: (\n data: RpcStorageType[K] extends \"collection\"\n ?\n | Record<\n string,\n Partial<InferRpcType<TTypes[K]>> | null\n >\n | Array<InferRpcType<TTypes[K]>>\n : RpcStorageType[K] extends \"singleton\"\n ? Partial<InferRpcType<TTypes[K]>>\n : never\n ) => void;\n }\n ): void;\n };\n};\n\nexport const createRpcHooks = <TTypes extends Record<string, Rpc<any>>>(\n typeKeys: Array<keyof TTypes>\n): RpcHooks<TTypes> => {\n const toPascalCase = (s: string): string => {\n return s\n .split(\"_\")\n .map(\n (word) =>\n word.charAt(0).toUpperCase() + word.slice(1).toLowerCase()\n )\n .join(\"\");\n };\n\n const hooks = {} as RpcHooks<TTypes>;\n\n // Основные хуки для каждого типа\n typeKeys.forEach((typeName) => {\n const hookName = `use${toPascalCase(\n String(typeName)\n )}` as keyof RpcHooks<TTypes>;\n const typeKey = typeName as keyof TTypes;\n\n function useHook(id?: string | number) {\n const { repository } = useRpc<TTypes>();\n const allData = useSelector(\n (state: RpcState<TTypes>) => state.rpc[typeKey] || {}\n );\n\n const findById = React.useCallback(\n (id: string | number) => repository.findById(typeKey, id),\n [repository]\n );\n const findAll = React.useCallback(\n () => repository.findAll(typeKey),\n [repository]\n );\n const mergeRpc = React.useCallback(\n (\n data:\n | Record<\n string,\n Partial<\n InferRpcType<TTypes[typeof typeKey]>\n > | null\n >\n | InferRpcType<TTypes[typeof typeKey]>[]\n ) => repository.mergeRpc(typeKey, data),\n [repository]\n );\n\n if (id !== undefined) {\n return findById(id);\n }\n return {\n [`${String(typeKey)}s`]: Object.values(allData) as InferRpcType<\n TTypes[typeof typeKey]\n >[],\n [`${String(typeKey)}Map`]: allData as Record<\n string,\n InferRpcType<TTypes[typeof typeKey]>\n >,\n findById,\n findAll,\n mergeRpc,\n } as any;\n }\n\n (hooks as any)[hookName] = useHook;\n\n // Хуки для полных связанных данных\n const fullRelatedHookName = `use${toPascalCase(\n String(typeName)\n )}FullRelatedData` as keyof RpcHooks<TTypes>;\n\n function useFullRelatedHook<\n TResult = InferRpcType<TTypes[typeof typeName]>\n >(id?: string | number) {\n const { repository } = useRpc<TTypes>();\n const allRpcData = useSelector(\n (state: RpcState<TTypes>) => state.rpc\n );\n const [fullData, setFullData] = React.useState<\n TResult | TResult[] | null\n >(null);\n\n // Стабилизируем данные с помощью useMemo\n const allRpcDataString = React.useMemo(\n () => JSON.stringify(allRpcData),\n [allRpcData]\n );\n\n const getData = React.useCallback(() => {\n try {\n const result = (repository as any).getFullRelatedData(\n typeName,\n id\n ) as TResult | TResult[] | null;\n setFullData(result);\n } catch {\n setFullData(null);\n }\n }, [repository, id]);\n\n React.useEffect(() => {\n console.log(\n `[${String(\n typeName\n )}FullRelatedData] Fetching full related data for id:`,\n id\n );\n getData();\n }, [getData, allRpcDataString, id]);\n return fullData;\n }\n (hooks as any)[fullRelatedHookName] = useFullRelatedHook;\n });\n\n // Хуки для слушателей с типизацией\n typeKeys.forEach((typeName) => {\n const listenerHookName = `use${toPascalCase(\n String(typeName)\n )}Listener` as keyof RpcHooks<TTypes>;\n\n function useListenerHook<\n RpcStorageType extends Record<keyof TTypes, StorageType> = Record<\n keyof TTypes,\n StorageType\n >\n >(\n callback: (event: {\n type: typeof typeName;\n payload: RpcStorageType[typeof typeName] extends \"collection\"\n ? Array<InferRpcType<TTypes[typeof typeName]>>\n : RpcStorageType[typeof typeName] extends \"singleton\"\n ? InferRpcType<TTypes[typeof typeName]>\n : Array<InferRpcType<TTypes[typeof typeName]>>;\n }) => void\n ) {\n const { repository } = useRpc<TTypes>();\n const callbackRef = React.useRef(callback);\n const listenerIdRef = React.useRef<string | number | null>(null);\n const isSubscribedRef = React.useRef(false);\n callbackRef.current = callback;\n const filteredCallback = React.useCallback(\n (\n events: Array<{\n type: typeof typeName;\n payload: any;\n }>\n ) => {\n const filteredEvents = events.filter(\n (event) => event.type === typeName\n );\n if (filteredEvents.length > 0) {\n const event = filteredEvents[0];\n console.log(\n `[${String(\n typeName\n )}Listener] Calling callback with:`,\n event\n );\n\n // Для singleton типов payload должен быть объектом, а не массивом\n const storageType = (\n repository as any\n ).getStorageType?.(String(typeName));\n if (\n storageType === \"singleton\" &&\n Array.isArray(event.payload) &&\n event.payload.length > 0\n ) {\n // Для singleton берем первый элемент из массива\n const singletonEvent = {\n ...event,\n payload: event.payload[0],\n };\n callbackRef.current(singletonEvent as any);\n } else {\n callbackRef.current(event as any);\n }\n }\n },\n []\n );\n\n React.useEffect(() => {\n // Удаляем предыдущую подписку если есть\n if (\n listenerIdRef.current &&\n typeof (repository as any).offDataChanged === \"function\"\n ) {\n (repository as any).offDataChanged(listenerIdRef.current);\n listenerIdRef.current = null;\n isSubscribedRef.current = false;\n }\n\n if (!isSubscribedRef.current) {\n listenerIdRef.current = (repository as any).onDataChanged(\n filteredCallback,\n {\n types: [typeName],\n }\n );\n isSubscribedRef.current = true;\n }\n\n return () => {\n if (\n listenerIdRef.current &&\n typeof (repository as any).offDataChanged === \"function\"\n ) {\n (repository as any).offDataChanged(\n listenerIdRef.current\n );\n listenerIdRef.current = null;\n isSubscribedRef.current = false;\n }\n };\n }, [repository, filteredCallback]);\n return () => {};\n }\n (hooks as any)[listenerHookName] = useListenerHook;\n });\n\n function useDataListener<\n RpcStorageType extends Record<keyof TTypes, StorageType> = Record<\n keyof TTypes,\n StorageType\n >\n >(\n callback: (\n events: Array<{\n type: keyof TTypes;\n payload: RpcStorageType[keyof TTypes] extends \"collection\"\n ? Array<InferRpcType<TTypes[keyof TTypes]>>\n : RpcStorageType[keyof TTypes] extends \"singleton\"\n ? InferRpcType<TTypes[keyof TTypes]>\n : Array<InferRpcType<TTypes[keyof TTypes]>>;\n }>\n ) => void,\n options?: { types?: (keyof TTypes)[] }\n ) {\n const { repository } = useRpc<TTypes>();\n const callbackRef = React.useRef(callback);\n const listenerIdRef = React.useRef<string | number | null>(null);\n callbackRef.current = callback;\n\n React.useEffect(() => {\n // Удаляем предыдущую подписку если есть\n if (\n listenerIdRef.current &&\n typeof (repository as any).offDataChanged === \"function\"\n ) {\n (repository as any).offDataChanged(listenerIdRef.current);\n listenerIdRef.current = null;\n }\n\n listenerIdRef.current = (repository as any).onDataChanged(\n callbackRef.current as any,\n {\n types: options?.types || typeKeys,\n }\n );\n return () => {\n if (\n listenerIdRef.current &&\n typeof (repository as any).offDataChanged === \"function\"\n ) {\n (repository as any).offDataChanged(listenerIdRef.current);\n listenerIdRef.current = null;\n }\n };\n }, [repository, options?.types]);\n return () => {};\n }\n (hooks as any).useDataListener = useDataListener;\n\n // Хуки для связанных данных\n typeKeys.forEach((typeName) => {\n const relatedHookName = `use${toPascalCase(\n String(typeName)\n )}Related` as keyof RpcHooks<TTypes>;\n\n function useRelatedHook<TTarget extends keyof TTypes>(\n id: string | number,\n targetType: TTarget\n ) {\n const { repository } = useRpc<TTypes>();\n const sourceData = useSelector(\n (state: RpcState<TTypes>) => state.rpc[typeName] || {}\n );\n const targetData = useSelector(\n (state: RpcState<TTypes>) => state.rpc[targetType] || {}\n );\n const [relatedData, setRelatedData] = React.useState<\n Array<TTypes[TTarget] extends Rpc<infer S> ? z.infer<S> : never>\n >([]);\n\n // Стабилизируем данные с помощью useMemo\n const sourceDataString = React.useMemo(\n () => JSON.stringify(sourceData),\n [sourceData]\n );\n const targetDataString = React.useMemo(\n () => JSON.stringify(targetData),\n [targetData]\n );\n\n const getRelatedData = React.useCallback(() => {\n try {\n const result = (repository as any).getRelated(\n typeName,\n id,\n targetType\n );\n setRelatedData(result);\n } catch {\n setRelatedData([]);\n }\n }, [repository, id, targetType]);\n\n React.useEffect(() => {\n console.log(\n `[${String(\n typeName\n )}Related] Fetching related data for id:`,\n id,\n \"targetType:\",\n targetType\n );\n getRelatedData();\n }, [\n getRelatedData,\n id,\n sourceDataString,\n targetDataString,\n targetType,\n ]);\n return relatedData;\n }\n (hooks as any)[relatedHookName] = useRelatedHook;\n });\n\n // Хук для обработки сообщений с полной типизацией\n function useHandleMessages() {\n const { repository } = useRpc<TTypes>();\n\n const handleMessages = (\n messages: Array<Message<TTypes>>,\n callbacks?: {\n [K in keyof TTypes]?: (\n data:\n | InferRpcType<TTypes[K]>[]\n | Record<\n string,\n Partial<InferRpcType<TTypes[K]>> | null\n >\n ) => void;\n }\n ) => {\n repository.handleMessages(messages, callbacks);\n };\n\n const handleMessagesTyped = <\n RpcStorageType extends Record<keyof TTypes, StorageType>\n >(\n messages: Array<Message<TTypes>>,\n callbacks?: {\n [K in keyof TTypes]?: (\n data: RpcStorageType[K] extends \"collection\"\n ?\n | Record<\n string,\n Partial<InferRpcType<TTypes[K]>> | null\n >\n | Array<InferRpcType<TTypes[K]>>\n : RpcStorageType[K] extends \"singleton\"\n ? Partial<InferRpcType<TTypes[K]>>\n : never\n ) => void;\n }\n ) => {\n repository.handleMessages<RpcStorageType>(messages, callbacks);\n };\n\n return { handleMessages, handleMessagesTyped };\n }\n\n (hooks as any).useHandleMessages = useHandleMessages;\n\n return hooks;\n};\n"],"names":["id"],"mappings":"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"}