Refactor message appending logic in useMessageOption hook
This commit is contained in:
		
							parent
							
								
									00bd19374a
								
							
						
					
					
						commit
						5b04e55a03
					
				| @ -2,7 +2,7 @@ import Markdown from "../../Common/Markdown" | |||||||
| import React from "react" | import React from "react" | ||||||
| import { Image, Tooltip } from "antd" | import { Image, Tooltip } from "antd" | ||||||
| import { WebSearch } from "./WebSearch" | import { WebSearch } from "./WebSearch" | ||||||
| import { CheckIcon, ClipboardIcon } from "lucide-react" | import { CheckIcon, ClipboardIcon, Pen, RotateCcw } from "lucide-react" | ||||||
| 
 | 
 | ||||||
| type Props = { | type Props = { | ||||||
|   message: string |   message: string | ||||||
| @ -26,7 +26,7 @@ export const PlaygroundMessage = (props: Props) => { | |||||||
| 
 | 
 | ||||||
|   return ( |   return ( | ||||||
|     <div className="group w-full text-gray-800 dark:text-gray-100"> |     <div className="group w-full text-gray-800 dark:text-gray-100"> | ||||||
|       <div className="text-base gap-4 md:gap-6 md:max-w-2xl lg:max-w-xl xl:max-w-3xl flex lg:px-0 m-auto w-full"> |       <div className="text-base  md:max-w-2xl lg:max-w-xl xl:max-w-3xl flex lg:px-0 m-auto w-full"> | ||||||
|         <div className="flex flex-row gap-4 md:gap-6 md:max-w-2xl lg:max-w-xl xl:max-w-3xl p-4 md:py-6 lg:px-0 m-auto w-full"> |         <div className="flex flex-row gap-4 md:gap-6 md:max-w-2xl lg:max-w-xl xl:max-w-3xl p-4 md:py-6 lg:px-0 m-auto w-full"> | ||||||
|           <div className="w-8 flex flex-col relative items-end"> |           <div className="w-8 flex flex-col relative items-end"> | ||||||
|             <div className="relative h-7 w-7 p-1 rounded-sm text-white flex items-center justify-center  text-opacity-100r"> |             <div className="relative h-7 w-7 p-1 rounded-sm text-white flex items-center justify-center  text-opacity-100r"> | ||||||
| @ -58,23 +58,25 @@ export const PlaygroundMessage = (props: Props) => { | |||||||
|               <Markdown message={props.message} /> |               <Markdown message={props.message} /> | ||||||
|             </div> |             </div> | ||||||
|             {/* source if aviable */} |             {/* source if aviable */} | ||||||
|             {props.images && props.images.length > 0 && ( |             {props.images && | ||||||
|               <div className="flex md:max-w-2xl lg:max-w-xl xl:max-w-3xl mt-4 m-auto w-full"> |               props.images && | ||||||
|                 {props.images |               props.images.filter((img) => img.length > 0).length > 0 && ( | ||||||
|                   .filter((image) => image.length > 0) |                 <div className="flex md:max-w-2xl lg:max-w-xl xl:max-w-3xl mt-4 m-auto w-full"> | ||||||
|                   .map((image, index) => ( |                   {props.images | ||||||
|                     <Image |                     .filter((image) => image.length > 0) | ||||||
|                       key={index} |                     .map((image, index) => ( | ||||||
|                       src={image} |                       <Image | ||||||
|                       alt="Uploaded Image" |                         key={index} | ||||||
|                       width={180} |                         src={image} | ||||||
|                       className="rounded-md relative" |                         alt="Uploaded Image" | ||||||
|                     /> |                         width={180} | ||||||
|                   ))} |                         className="rounded-md relative" | ||||||
|               </div> |                       /> | ||||||
|             )} |                     ))} | ||||||
|  |                 </div> | ||||||
|  |               )} | ||||||
| 
 | 
 | ||||||
|             {props.isBot && ( |             {props.isBot && props?.sources && props?.sources.length > 0 && ( | ||||||
|               <div className="mb-3 flex flex-wrap gap-2"> |               <div className="mb-3 flex flex-wrap gap-2"> | ||||||
|                 {props?.sources?.map((source, index) => ( |                 {props?.sources?.map((source, index) => ( | ||||||
|                   <a |                   <a | ||||||
| @ -87,37 +89,51 @@ export const PlaygroundMessage = (props: Props) => { | |||||||
|                 ))} |                 ))} | ||||||
|               </div> |               </div> | ||||||
|             )} |             )} | ||||||
|             {props.isBot && !props.isProcessing && ( |             {!props.isProcessing && ( | ||||||
|               <div className="flex space-x-2 gap-2"> |               <div | ||||||
|                 {!props.hideCopy && ( |                 className={`space-x-2 gap-2 mt-3 ${ | ||||||
|                   <Tooltip title="Copy to clipboard"> |                   props.currentMessageIndex !== props.totalMessages - 1 | ||||||
|                     <button |                     ? "hidden group-hover:flex" | ||||||
|                       onClick={() => { |                     : "flex" | ||||||
|                         navigator.clipboard.writeText(props.message) |                 }`}>
 | ||||||
|                         setIsBtnPressed(true) |                 {props.isBot && ( | ||||||
|                         setTimeout(() => { |                   <> | ||||||
|                           setIsBtnPressed(false) |                     {!props.hideCopy && ( | ||||||
|                         }, 2000) |                       <Tooltip title="Copy to clipboard"> | ||||||
|                       }} |                         <button | ||||||
|                       className="flex items-center justify-center w-6 h-6 rounded-full bg-gray-100 dark:bg-gray-800 hover:bg-gray-200 dark:hover:bg-gray-700 transition-colors duration-200 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-500"> |                           onClick={() => { | ||||||
|                       {!isBtnPressed ? ( |                             navigator.clipboard.writeText(props.message) | ||||||
|                         <ClipboardIcon className="w-3 h-3 text-gray-400 group-hover:text-gray-500" /> |                             setIsBtnPressed(true) | ||||||
|                       ) : ( |                             setTimeout(() => { | ||||||
|                         <CheckIcon className="w-3 h-3 text-green-400 group-hover:text-green-500" /> |                               setIsBtnPressed(false) | ||||||
|                       )} |                             }, 2000) | ||||||
|                     </button> |                           }} | ||||||
|                   </Tooltip> |                           className="flex items-center justify-center w-6 h-6 rounded-full bg-gray-100 dark:bg-gray-800 hover:bg-gray-200 dark:hover:bg-gray-700 transition-colors duration-200 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-500"> | ||||||
|                 )} |                           {!isBtnPressed ? ( | ||||||
|  |                             <ClipboardIcon className="w-3 h-3 text-gray-400 group-hover:text-gray-500" /> | ||||||
|  |                           ) : ( | ||||||
|  |                             <CheckIcon className="w-3 h-3 text-green-400 group-hover:text-green-500" /> | ||||||
|  |                           )} | ||||||
|  |                         </button> | ||||||
|  |                       </Tooltip> | ||||||
|  |                     )} | ||||||
| 
 | 
 | ||||||
|                 {/* {props.currentMessageIndex === props.totalMessages - 1 && ( |                     {props.currentMessageIndex === props.totalMessages - 1 && ( | ||||||
|                   <Tooltip title="Regenerate"> |                       <Tooltip title="Regenerate"> | ||||||
|                     <button |                         <button | ||||||
|                       onClick={props.onRengerate} |                           onClick={props.onRengerate} | ||||||
|                       className="flex items-center justify-center w-6 h-6 rounded-full bg-gray-100 dark:bg-gray-800 hover:bg-gray-200 dark:hover:bg-gray-700 transition-colors duration-200 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-500"> |                           className="flex items-center justify-center w-6 h-6 rounded-full bg-gray-100 dark:bg-gray-800 hover:bg-gray-200 dark:hover:bg-gray-700 transition-colors duration-200 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-500"> | ||||||
|                       <ArrowPathIcon className="w-3 h-3 text-gray-400 group-hover:text-gray-500" /> |                           <RotateCcw className="w-3 h-3 text-gray-400 group-hover:text-gray-500" /> | ||||||
|                     </button> |                         </button> | ||||||
|                   </Tooltip> |                       </Tooltip> | ||||||
|                 )} */} |                     )} | ||||||
|  |                   </> | ||||||
|  |                 )} | ||||||
|  |                 <Tooltip title="Edit"> | ||||||
|  |                   <button className="flex items-center justify-center w-6 h-6 rounded-full bg-gray-100 dark:bg-gray-800 hover:bg-gray-200 dark:hover:bg-gray-700 transition-colors duration-200 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-500"> | ||||||
|  |                     <Pen className="w-3 h-3 text-gray-400 group-hover:text-gray-500" /> | ||||||
|  |                   </button> | ||||||
|  |                 </Tooltip> | ||||||
|               </div> |               </div> | ||||||
|             )} |             )} | ||||||
|           </div> |           </div> | ||||||
|  | |||||||
| @ -148,27 +148,37 @@ export const useMessageOption = () => { | |||||||
|       baseUrl: cleanUrl(url) |       baseUrl: cleanUrl(url) | ||||||
|     }) |     }) | ||||||
| 
 | 
 | ||||||
|     let newMessage: Message[] = [ |     let newMessage: Message[] = [] | ||||||
|       ...messages, |  | ||||||
|       { |  | ||||||
|         isBot: false, |  | ||||||
|         name: "You", |  | ||||||
|         message, |  | ||||||
|         sources: [], |  | ||||||
|         images: [image] |  | ||||||
|       }, |  | ||||||
|       { |  | ||||||
|         isBot: true, |  | ||||||
|         name: selectedModel, |  | ||||||
|         message: "▋", |  | ||||||
|         sources: [] |  | ||||||
|       } |  | ||||||
|     ] |  | ||||||
| 
 |  | ||||||
|     const appendingIndex = newMessage.length - 1 |  | ||||||
|     if (!isRegenerate) { |     if (!isRegenerate) { | ||||||
|       setMessages(newMessage) |       newMessage = [ | ||||||
|  |         ...messages, | ||||||
|  |         { | ||||||
|  |           isBot: false, | ||||||
|  |           name: "You", | ||||||
|  |           message, | ||||||
|  |           sources: [], | ||||||
|  |           images: [image] | ||||||
|  |         }, | ||||||
|  |         { | ||||||
|  |           isBot: true, | ||||||
|  |           name: selectedModel, | ||||||
|  |           message: "▋", | ||||||
|  |           sources: [] | ||||||
|  |         } | ||||||
|  |       ] | ||||||
|  |     } else { | ||||||
|  |       newMessage = [ | ||||||
|  |         ...messages, | ||||||
|  |         { | ||||||
|  |           isBot: true, | ||||||
|  |           name: selectedModel, | ||||||
|  |           message: "▋", | ||||||
|  |           sources: [] | ||||||
|  |         } | ||||||
|  |       ] | ||||||
|     } |     } | ||||||
|  |     setMessages(newMessage) | ||||||
|  |     const appendingIndex = newMessage.length - 1 | ||||||
| 
 | 
 | ||||||
|     try { |     try { | ||||||
|       setIsSearchingInternet(true) |       setIsSearchingInternet(true) | ||||||
| @ -321,8 +331,6 @@ export const useMessageOption = () => { | |||||||
|       setIsProcessing(false) |       setIsProcessing(false) | ||||||
|       setStreaming(false) |       setStreaming(false) | ||||||
|     } catch (e) { |     } catch (e) { | ||||||
|       e |  | ||||||
| 
 |  | ||||||
|       if (e?.name === "AbortError") { |       if (e?.name === "AbortError") { | ||||||
|         newMessage[appendingIndex].message = newMessage[ |         newMessage[appendingIndex].message = newMessage[ | ||||||
|           appendingIndex |           appendingIndex | ||||||
| @ -393,27 +401,37 @@ export const useMessageOption = () => { | |||||||
|       baseUrl: cleanUrl(url) |       baseUrl: cleanUrl(url) | ||||||
|     }) |     }) | ||||||
| 
 | 
 | ||||||
|     let newMessage: Message[] = [ |     let newMessage: Message[] = [] | ||||||
|       ...messages, |  | ||||||
|       { |  | ||||||
|         isBot: false, |  | ||||||
|         name: "You", |  | ||||||
|         message, |  | ||||||
|         sources: [], |  | ||||||
|         images: [image] |  | ||||||
|       }, |  | ||||||
|       { |  | ||||||
|         isBot: true, |  | ||||||
|         name: selectedModel, |  | ||||||
|         message: "▋", |  | ||||||
|         sources: [] |  | ||||||
|       } |  | ||||||
|     ] |  | ||||||
| 
 |  | ||||||
|     const appendingIndex = newMessage.length - 1 |  | ||||||
|     if (!isRegenerate) { |     if (!isRegenerate) { | ||||||
|       setMessages(newMessage) |       newMessage = [ | ||||||
|  |         ...messages, | ||||||
|  |         { | ||||||
|  |           isBot: false, | ||||||
|  |           name: "You", | ||||||
|  |           message, | ||||||
|  |           sources: [], | ||||||
|  |           images: [image] | ||||||
|  |         }, | ||||||
|  |         { | ||||||
|  |           isBot: true, | ||||||
|  |           name: selectedModel, | ||||||
|  |           message: "▋", | ||||||
|  |           sources: [] | ||||||
|  |         } | ||||||
|  |       ] | ||||||
|  |     } else { | ||||||
|  |       newMessage = [ | ||||||
|  |         ...messages, | ||||||
|  |         { | ||||||
|  |           isBot: true, | ||||||
|  |           name: selectedModel, | ||||||
|  |           message: "▋", | ||||||
|  |           sources: [] | ||||||
|  |         } | ||||||
|  |       ] | ||||||
|     } |     } | ||||||
|  |     setMessages(newMessage) | ||||||
|  |     const appendingIndex = newMessage.length - 1 | ||||||
| 
 | 
 | ||||||
|     try { |     try { | ||||||
|       const prompt = await systemPromptForNonRagOption() |       const prompt = await systemPromptForNonRagOption() | ||||||
| @ -624,8 +642,12 @@ export const useMessageOption = () => { | |||||||
|   const regenerateLastMessage = async () => { |   const regenerateLastMessage = async () => { | ||||||
|     if (history.length > 0) { |     if (history.length > 0) { | ||||||
|       const lastMessage = history[history.length - 2] |       const lastMessage = history[history.length - 2] | ||||||
|       setHistory(history.slice(0, -1)) |       let newHistory = history | ||||||
|       setMessages(messages.slice(0, -1)) |       let mewMessages = messages | ||||||
|  |       newHistory.pop() | ||||||
|  |       mewMessages.pop() | ||||||
|  |       setHistory(newHistory) | ||||||
|  |       setMessages(mewMessages) | ||||||
|       await removeMessageUsingHistoryId(historyId) |       await removeMessageUsingHistoryId(historyId) | ||||||
|       if (lastMessage.role === "user") { |       if (lastMessage.role === "user") { | ||||||
|         await onSubmit({ |         await onSubmit({ | ||||||
|  | |||||||
| @ -286,11 +286,10 @@ export const updateHistory = async (id: string, title: string) => { | |||||||
| } | } | ||||||
| 
 | 
 | ||||||
| export const removeMessageUsingHistoryId = async (history_id: string) => { | export const removeMessageUsingHistoryId = async (history_id: string) => { | ||||||
|   // remove the last message
 |  | ||||||
|   const db = new PageAssitDatabase() |   const db = new PageAssitDatabase() | ||||||
|   const chatHistory = await db.getChatHistory(history_id) |   const chatHistory = await db.getChatHistory(history_id) | ||||||
|   const newChatHistory = chatHistory.slice(0, -1) |   chatHistory.shift() | ||||||
|   await db.db.set({ [history_id]: newChatHistory }) |   await db.db.set({ [history_id]: chatHistory }) | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
|  | |||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user