Add prefixes sequence check for claude

This commit is contained in:
DonMoralez 2023-12-16 14:12:06 +02:00
parent d19cc7ee36
commit 125d2997db
2 changed files with 40 additions and 6 deletions

View File

@ -40,6 +40,34 @@ async function sendClaudeRequest(request, response) {
let requestPrompt = convertClaudePrompt(request.body.messages, !request.body.exclude_assistant, request.body.assistant_prefill, isSyspromptSupported, request.body.claude_use_sysprompt, request.body.human_sysprompt_message);
console.log(chalk.green(`${divider}\nClaude request\n`) + chalk.cyan(`PROMPT\n${divider}\n${requestPrompt}\n${divider}`));
// Check Claude messages sequence and prefixes presence.
const sequence = requestPrompt.split('\n').filter(x => x.startsWith('Human:') || x.startsWith('Assistant:'));
let humanErrorCount = 0;
let assistantErrorCount = 0;
let humanFound = sequence.some(line => line.startsWith('Human:'));
let assistantFound = sequence.some(line => line.startsWith('Assistant:'));
for (let i = 0; i < sequence.length - 1; i++) {
if (sequence[i].startsWith(sequence[i + 1].split(':')[0])) {
if (sequence[i].startsWith('Human:')) {
humanErrorCount++;
} else if (sequence[i].startsWith('Assistant:')) {
assistantErrorCount++;
}
}
}
if (!humanFound) {
console.log(chalk.red(`${divider}\nWarning: No Human prefix found in the prompt.\n${divider}`));
}
if (!assistantFound) {
console.log(chalk.red(`${divider}\nWarning: No Assistant prefix found in the prompt.\n${divider}`));
}
if (humanErrorCount > 0 || assistantErrorCount > 0) {
console.log(chalk.red(`${divider}\nWarning: Detected incorrect Prefix sequence(s).\nIncorrect 'Human:' prefix(es): ${humanErrorCount}.\nIncorrect 'Assistant:' prefix(es): ${assistantErrorCount}.\nCheck the prompt above and fix it in the sillytavern.\nThe correct sequence should look like this:\nSystem prompt message <--(for new sysprompt format only)\n <------------------(Every message start with Assistant:/Human:prefix should have one empty line above)\nHuman:\n\nAssistant:\n\...\n\nHuman:\n\nAssistant:\n${divider}`));
}
const stop_sequences = ['\n\nHuman:', '\n\nSystem:', '\n\nAssistant:'];
// Add custom stop sequences

View File

@ -14,26 +14,31 @@ function convertClaudePrompt(messages, addAssistantPostfix, addAssistantPrefill,
console.log(JSON.stringify(messages, null, 2));
//Prepare messages for claude.
if (messages.length > 0) {
messages[0].role = 'system';
//Add the assistant's message to the end of messages.
if (addAssistantPostfix) {
messages.push({
role: 'assistant',
content: addAssistantPrefill || '4',
content: addAssistantPrefill || '',
});
}
// Find the index of the first message with an assistant role and check for a "'user' role/Human:" before it.
let hasUser = false;
let hasAssist = false;
const firstAssistantIndex = messages.findIndex((message, i) => {
if (i > 0 && (message.role === 'user' || message.content.includes('Human:'))) {
if (i >= 0 && (message.role === 'user' || message.content.includes('\n\nHuman: '))) {
if (message.content.includes('\n\nAssistant: ')) {
hasAssist = true;
}
hasUser = true;
}
return message.role === 'assistant' && i > 0;
});
// When 2.1 and 'Use system prompt" checked, switches to system prompt format by setting the first message's role to 'system'.
// Also, insert the human's message before the first the assistant one, in case there are no such message or prefix found.
// When 2.1 and 'Use system prompt" checked, switches to the system prompt format by setting the first message's role to the 'system'.
// Inserts the human's message before the first the assistant one, if there are no such message or prefix found.
if (withSyspromptSupport && useSystemPrompt) {
messages[0].role = 'system';
if (firstAssistantIndex > 0 && !hasUser) {
if (firstAssistantIndex > 0 && (!hasUser || (hasUser && hasAssist))) { //addSysHumanMsg for test
messages.splice(firstAssistantIndex, 0, {
role: 'user',
content: addSysHumanMsg || 'Let\'s get started.',
@ -50,6 +55,7 @@ function convertClaudePrompt(messages, addAssistantPostfix, addAssistantPrefill,
}
console.log(JSON.stringify(messages, null, 2));
// Convert messages to requestPrompt.
let requestPrompt = messages.map((v, i) => {
// Claude doesn't support message names, so we'll just add them to the message content.
@ -63,7 +69,7 @@ function convertClaudePrompt(messages, addAssistantPostfix, addAssistantPrefill,
'user': '\n\nHuman: ',
'system': i === 0 ? '' : v.name === 'example_assistant' ? '\n\nA: ' : v.name === 'example_user' ? '\n\nH: ' : '\n\n',
'FixHumMsg': '\n\nFirst message: ',
}[v.role] ?? '\n\n4';
}[v.role] ?? '\n\n';
return prefix + v.content;
}).join('');