use-conversation.ts 3.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273
  1. import { useCallback, useState } from 'react'
  2. import produce from 'immer'
  3. import { useGetState } from 'ahooks'
  4. import type { ConversationItem } from '@/models/share'
  5. const storageConversationIdKey = 'conversationIdInfo'
  6. type ConversationInfoType = Omit<ConversationItem, 'inputs' | 'id'>
  7. function useConversation() {
  8. const [conversationList, setConversationList] = useState<ConversationItem[]>([])
  9. const [pinnedConversationList, setPinnedConversationList] = useState<ConversationItem[]>([])
  10. const [currConversationId, doSetCurrConversationId, getCurrConversationId] = useGetState<string>('-1')
  11. // when set conversation id, we do not have set appId
  12. const setCurrConversationId = useCallback((id: string, appId: string, isSetToLocalStroge = true, newConversationName = '') => {
  13. doSetCurrConversationId(id)
  14. if (isSetToLocalStroge && id !== '-1') {
  15. // conversationIdInfo: {[appId1]: conversationId1, [appId2]: conversationId2}
  16. const conversationIdInfo = globalThis.localStorage?.getItem(storageConversationIdKey) ? JSON.parse(globalThis.localStorage?.getItem(storageConversationIdKey) || '') : {}
  17. conversationIdInfo[appId] = id
  18. globalThis.localStorage?.setItem(storageConversationIdKey, JSON.stringify(conversationIdInfo))
  19. }
  20. }, [doSetCurrConversationId])
  21. const getConversationIdFromStorage = (appId: string) => {
  22. const conversationIdInfo = globalThis.localStorage?.getItem(storageConversationIdKey) ? JSON.parse(globalThis.localStorage?.getItem(storageConversationIdKey) || '') : {}
  23. const id = conversationIdInfo[appId]
  24. return id
  25. }
  26. const isNewConversation = currConversationId === '-1'
  27. // input can be updated by user
  28. const [newConversationInputs, setNewConversationInputs] = useState<Record<string, any> | null>(null)
  29. const resetNewConversationInputs = () => {
  30. if (!newConversationInputs)
  31. return
  32. setNewConversationInputs(produce(newConversationInputs, (draft) => {
  33. Object.keys(draft).forEach((key) => {
  34. draft[key] = ''
  35. })
  36. }))
  37. }
  38. const [existConversationInputs, setExistConversationInputs] = useState<Record<string, any> | null>(null)
  39. const currInputs = isNewConversation ? newConversationInputs : existConversationInputs
  40. const setCurrInputs = isNewConversation ? setNewConversationInputs : setExistConversationInputs
  41. // info is muted
  42. const [newConversationInfo, setNewConversationInfo] = useState<ConversationInfoType | null>(null)
  43. const [existConversationInfo, setExistConversationInfo] = useState<ConversationInfoType | null>(null)
  44. const currConversationInfo = isNewConversation ? newConversationInfo : existConversationInfo
  45. return {
  46. conversationList,
  47. setConversationList,
  48. pinnedConversationList,
  49. setPinnedConversationList,
  50. currConversationId,
  51. getCurrConversationId,
  52. setCurrConversationId,
  53. getConversationIdFromStorage,
  54. isNewConversation,
  55. currInputs,
  56. newConversationInputs,
  57. existConversationInputs,
  58. resetNewConversationInputs,
  59. setCurrInputs,
  60. currConversationInfo,
  61. setNewConversationInfo,
  62. existConversationInfo,
  63. setExistConversationInfo,
  64. }
  65. }
  66. export default useConversation