mirror of
https://github.com/open-webui/open-webui
synced 2025-04-28 02:01:41 +00:00
feat: create new message pair on cmd+shift+enter
This commit is contained in:
parent
d7b64ff447
commit
ad82eae6a9
@ -559,6 +559,66 @@
|
|||||||
}, 1000);
|
}, 1000);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const createMessagePair = async (userPrompt) => {
|
||||||
|
prompt = '';
|
||||||
|
if (selectedModels.length === 0) {
|
||||||
|
toast.error($i18n.t('Model not selected'));
|
||||||
|
} else {
|
||||||
|
const modelId = selectedModels[0];
|
||||||
|
const model = $models.filter((m) => m.id === modelId).at(0);
|
||||||
|
|
||||||
|
const messages = createMessagesList(history.currentId);
|
||||||
|
const parentMessage = messages.length !== 0 ? messages.at(-1) : null;
|
||||||
|
|
||||||
|
const userMessageId = uuidv4();
|
||||||
|
const responseMessageId = uuidv4();
|
||||||
|
|
||||||
|
const userMessage = {
|
||||||
|
id: userMessageId,
|
||||||
|
parentId: parentMessage ? parentMessage.id : null,
|
||||||
|
childrenIds: [responseMessageId],
|
||||||
|
role: 'user',
|
||||||
|
content: userPrompt ? userPrompt : `[PROMPT] ${userMessageId}`,
|
||||||
|
timestamp: Math.floor(Date.now() / 1000)
|
||||||
|
};
|
||||||
|
|
||||||
|
const responseMessage = {
|
||||||
|
id: responseMessageId,
|
||||||
|
parentId: userMessageId,
|
||||||
|
childrenIds: [],
|
||||||
|
role: 'assistant',
|
||||||
|
content: `[RESPONSE] ${responseMessageId}`,
|
||||||
|
done: true,
|
||||||
|
|
||||||
|
model: modelId,
|
||||||
|
modelName: model.name ?? model.id,
|
||||||
|
modelIdx: 0,
|
||||||
|
timestamp: Math.floor(Date.now() / 1000)
|
||||||
|
};
|
||||||
|
|
||||||
|
if (parentMessage) {
|
||||||
|
parentMessage.childrenIds.push(userMessageId);
|
||||||
|
history.messages[parentMessage.id] = parentMessage;
|
||||||
|
}
|
||||||
|
history.messages[userMessageId] = userMessage;
|
||||||
|
history.messages[responseMessageId] = responseMessage;
|
||||||
|
|
||||||
|
history.currentId = responseMessageId;
|
||||||
|
|
||||||
|
await tick();
|
||||||
|
|
||||||
|
if (autoScroll) {
|
||||||
|
scrollToBottom();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (messages.length === 0) {
|
||||||
|
await initChatHandler();
|
||||||
|
} else {
|
||||||
|
await saveChatHandler($chatId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
//////////////////////////
|
//////////////////////////
|
||||||
// Chat functions
|
// Chat functions
|
||||||
//////////////////////////
|
//////////////////////////
|
||||||
@ -666,25 +726,7 @@
|
|||||||
history.messages[history.currentId].parentId === null &&
|
history.messages[history.currentId].parentId === null &&
|
||||||
history.messages[history.currentId].role === 'user'
|
history.messages[history.currentId].role === 'user'
|
||||||
) {
|
) {
|
||||||
if (!$temporaryChatEnabled) {
|
await initChatHandler();
|
||||||
chat = await createNewChat(localStorage.token, {
|
|
||||||
id: $chatId,
|
|
||||||
title: $i18n.t('New Chat'),
|
|
||||||
models: selectedModels,
|
|
||||||
system: $settings.system ?? undefined,
|
|
||||||
params: params,
|
|
||||||
history: history,
|
|
||||||
tags: [],
|
|
||||||
timestamp: Date.now()
|
|
||||||
});
|
|
||||||
|
|
||||||
currentChatPage.set(1);
|
|
||||||
await chats.set(await getChatList(localStorage.token, $currentChatPage));
|
|
||||||
await chatId.set(chat.id);
|
|
||||||
} else {
|
|
||||||
await chatId.set('local');
|
|
||||||
}
|
|
||||||
await tick();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
let _responses: string[] = [];
|
let _responses: string[] = [];
|
||||||
@ -1718,6 +1760,28 @@
|
|||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const initChatHandler = async () => {
|
||||||
|
if (!$temporaryChatEnabled) {
|
||||||
|
chat = await createNewChat(localStorage.token, {
|
||||||
|
id: $chatId,
|
||||||
|
title: $i18n.t('New Chat'),
|
||||||
|
models: selectedModels,
|
||||||
|
system: $settings.system ?? undefined,
|
||||||
|
params: params,
|
||||||
|
history: history,
|
||||||
|
tags: [],
|
||||||
|
timestamp: Date.now()
|
||||||
|
});
|
||||||
|
|
||||||
|
currentChatPage.set(1);
|
||||||
|
await chats.set(await getChatList(localStorage.token, $currentChatPage));
|
||||||
|
await chatId.set(chat.id);
|
||||||
|
} else {
|
||||||
|
await chatId.set('local');
|
||||||
|
}
|
||||||
|
await tick();
|
||||||
|
};
|
||||||
|
|
||||||
const saveChatHandler = async (_chatId) => {
|
const saveChatHandler = async (_chatId) => {
|
||||||
if ($chatId == _chatId) {
|
if ($chatId == _chatId) {
|
||||||
if (!$temporaryChatEnabled) {
|
if (!$temporaryChatEnabled) {
|
||||||
@ -1861,6 +1925,7 @@
|
|||||||
transparentBackground={$settings?.backgroundImageUrl ?? false}
|
transparentBackground={$settings?.backgroundImageUrl ?? false}
|
||||||
{submitPrompt}
|
{submitPrompt}
|
||||||
{stopResponse}
|
{stopResponse}
|
||||||
|
{createMessagePair}
|
||||||
on:call={async () => {
|
on:call={async () => {
|
||||||
await showControls.set(true);
|
await showControls.set(true);
|
||||||
}}
|
}}
|
||||||
|
@ -41,6 +41,7 @@
|
|||||||
export let transparentBackground = false;
|
export let transparentBackground = false;
|
||||||
|
|
||||||
export let submitPrompt: Function;
|
export let submitPrompt: Function;
|
||||||
|
export let createMessagePair: Function;
|
||||||
export let stopResponse: Function;
|
export let stopResponse: Function;
|
||||||
|
|
||||||
export let autoScroll = false;
|
export let autoScroll = false;
|
||||||
@ -554,6 +555,12 @@
|
|||||||
const isCtrlPressed = e.ctrlKey || e.metaKey; // metaKey is for Cmd key on Mac
|
const isCtrlPressed = e.ctrlKey || e.metaKey; // metaKey is for Cmd key on Mac
|
||||||
const commandsContainerElement = document.getElementById('commands-container');
|
const commandsContainerElement = document.getElementById('commands-container');
|
||||||
|
|
||||||
|
// Command/Ctrl + Shift + Enter to submit a message pair
|
||||||
|
if (isCtrlPressed && e.key === 'Enter' && e.shiftKey) {
|
||||||
|
e.preventDefault();
|
||||||
|
createMessagePair(prompt);
|
||||||
|
}
|
||||||
|
|
||||||
// Check if Ctrl + R is pressed
|
// Check if Ctrl + R is pressed
|
||||||
if (prompt === '' && isCtrlPressed && e.key.toLowerCase() === 'r') {
|
if (prompt === '' && isCtrlPressed && e.key.toLowerCase() === 'r') {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
|
@ -49,7 +49,7 @@
|
|||||||
|
|
||||||
let message = history.messages[history.currentId];
|
let message = history.messages[history.currentId];
|
||||||
while (message && _messages.length <= messagesCount) {
|
while (message && _messages.length <= messagesCount) {
|
||||||
_messages.push({ ...message });
|
_messages.unshift({ ...message });
|
||||||
message = message.parentId !== null ? history.messages[message.parentId] : null;
|
message = message.parentId !== null ? history.messages[message.parentId] : null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -341,7 +341,23 @@
|
|||||||
{:else}
|
{:else}
|
||||||
<div class="w-full pt-2">
|
<div class="w-full pt-2">
|
||||||
{#key chatId}
|
{#key chatId}
|
||||||
<div class="w-full flex flex-col-reverse">
|
<div class="w-full">
|
||||||
|
{#if messages.at(0)?.parentId !== null}
|
||||||
|
<Loader
|
||||||
|
on:visible={(e) => {
|
||||||
|
console.log('visible');
|
||||||
|
if (!messagesLoading) {
|
||||||
|
loadMoreMessages();
|
||||||
|
}
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<div class="w-full flex justify-center py-1 text-xs animate-pulse items-center gap-2">
|
||||||
|
<Spinner className=" size-4" />
|
||||||
|
<div class=" ">Loading...</div>
|
||||||
|
</div>
|
||||||
|
</Loader>
|
||||||
|
{/if}
|
||||||
|
|
||||||
{#each messages as message, messageIdx (message.id)}
|
{#each messages as message, messageIdx (message.id)}
|
||||||
<Message
|
<Message
|
||||||
{chatId}
|
{chatId}
|
||||||
@ -372,22 +388,6 @@
|
|||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
{/each}
|
{/each}
|
||||||
|
|
||||||
{#if messages.at(-1).parentId !== null}
|
|
||||||
<Loader
|
|
||||||
on:visible={(e) => {
|
|
||||||
console.log('visible');
|
|
||||||
if (!messagesLoading) {
|
|
||||||
loadMoreMessages();
|
|
||||||
}
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
<div class="w-full flex justify-center py-1 text-xs animate-pulse items-center gap-2">
|
|
||||||
<Spinner className=" size-4" />
|
|
||||||
<div class=" ">Loading...</div>
|
|
||||||
</div>
|
|
||||||
</Loader>
|
|
||||||
{/if}
|
|
||||||
</div>
|
</div>
|
||||||
<div class="pb-12" />
|
<div class="pb-12" />
|
||||||
{#if bottomPadding}
|
{#if bottomPadding}
|
||||||
|
@ -41,7 +41,7 @@
|
|||||||
export let readOnly = false;
|
export let readOnly = false;
|
||||||
|
|
||||||
onMount(() => {
|
onMount(() => {
|
||||||
console.log('message', idx);
|
// console.log('message', idx);
|
||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user