mirror of
https://github.com/danny-avila/LibreChat.git
synced 2025-12-18 01:10:14 +01:00
128 lines
3.1 KiB
JavaScript
128 lines
3.1 KiB
JavaScript
import endpoints from './endpoints';
|
|
import { atom, selector, useSetRecoilState, useResetRecoilState, useRecoilCallback } from 'recoil';
|
|
import buildTree from '~/utils/buildTree';
|
|
import getDefaultConversation from '~/utils/getDefaultConversation';
|
|
|
|
// current conversation, can be null (need to be fetched from server)
|
|
// sample structure
|
|
// {
|
|
// conversationId: 'new',
|
|
// title: 'New Chat',
|
|
// user: null,
|
|
// // endpoint: [azureOpenAI, openAI, bingAI, chatGPTBrowser]
|
|
// endpoint: 'azureOpenAI',
|
|
// // for azureOpenAI, openAI, chatGPTBrowser only
|
|
// model: 'gpt-3.5-turbo',
|
|
// // for azureOpenAI, openAI only
|
|
// chatGptLabel: null,
|
|
// promptPrefix: null,
|
|
// temperature: 1,
|
|
// top_p: 1,
|
|
// presence_penalty: 0,
|
|
// frequency_penalty: 0,
|
|
// // for bingAI only
|
|
// jailbreak: false,
|
|
// jailbreakConversationId: null,
|
|
// conversationSignature: null,
|
|
// clientId: null,
|
|
// invocationId: 1,
|
|
// toneStyle: null,
|
|
// };
|
|
|
|
const conversation = atom({
|
|
key: 'conversation',
|
|
default: null
|
|
});
|
|
|
|
// current messages of the conversation, must be an array
|
|
// sample structure
|
|
// [{text, sender, messageId, parentMessageId, isCreatedByUser}]
|
|
const messages = atom({
|
|
key: 'messages',
|
|
default: []
|
|
});
|
|
|
|
const messagesTree = selector({
|
|
key: 'messagesTree',
|
|
get: ({ get }) => {
|
|
return buildTree(get(messages), false);
|
|
}
|
|
});
|
|
|
|
const latestMessage = atom({
|
|
key: 'latestMessage',
|
|
default: null
|
|
});
|
|
|
|
const useConversation = () => {
|
|
const setConversation = useSetRecoilState(conversation);
|
|
const setMessages = useSetRecoilState(messages);
|
|
const resetLatestMessage = useResetRecoilState(latestMessage);
|
|
|
|
const switchToConversation = useRecoilCallback(
|
|
({ snapshot }) =>
|
|
async (_conversation, messages = null, preset = null) => {
|
|
const prevConversation = await snapshot.getPromise(conversation);
|
|
const endpointsFilter = await snapshot.getPromise(endpoints.endpointsFilter);
|
|
_switchToConversation(_conversation, messages, preset, {
|
|
endpointsFilter,
|
|
prevConversation
|
|
});
|
|
},
|
|
[]
|
|
);
|
|
|
|
const _switchToConversation = (
|
|
conversation,
|
|
messages = null,
|
|
preset = null,
|
|
{ endpointsFilter = {}, prevConversation = {} }
|
|
) => {
|
|
let { endpoint = null } = conversation;
|
|
|
|
if (endpoint === null)
|
|
// get the default model
|
|
conversation = getDefaultConversation({
|
|
conversation,
|
|
endpointsFilter,
|
|
prevConversation,
|
|
preset
|
|
});
|
|
|
|
setConversation(conversation);
|
|
setMessages(messages);
|
|
resetLatestMessage();
|
|
};
|
|
|
|
const newConversation = (template = {}, preset) => {
|
|
switchToConversation(
|
|
{
|
|
conversationId: 'new',
|
|
title: 'New Chat',
|
|
...template
|
|
},
|
|
[],
|
|
preset
|
|
);
|
|
};
|
|
|
|
const searchPlaceholderConversation = () => {
|
|
switchToConversation(
|
|
{
|
|
conversationId: 'search',
|
|
title: 'Search'
|
|
},
|
|
[]
|
|
);
|
|
};
|
|
|
|
return { newConversation, switchToConversation, searchPlaceholderConversation };
|
|
};
|
|
|
|
export default {
|
|
conversation,
|
|
messages,
|
|
messagesTree,
|
|
latestMessage,
|
|
useConversation
|
|
};
|