diff --git a/server/bleep/src/semantic.rs b/server/bleep/src/semantic.rs index 09b1a4838e..175c2d38f7 100644 --- a/server/bleep/src/semantic.rs +++ b/server/bleep/src/semantic.rs @@ -30,7 +30,6 @@ mod schema; pub use schema::{Embedding, Payload}; pub(crate) const COLLECTION_NAME: &str = "documents"; -pub(crate) const SCORE_THRESHOLD: f32 = 0.3; pub(crate) const EMBEDDING_DIM: usize = 384; #[derive(Error, Debug)] @@ -376,7 +375,7 @@ impl Semantic { vector, collection_name: COLLECTION_NAME.to_string(), offset: Some(offset), - score_threshold: Some(SCORE_THRESHOLD), + score_threshold: Some(threshold), with_payload: Some(WithPayloadSelector { selector_options: Some(with_payload_selector::SelectorOptions::Enable( true, diff --git a/server/bleep/src/webserver/answer.rs b/server/bleep/src/webserver/answer.rs index c0c3d8ab6e..cf476c9c58 100644 --- a/server/bleep/src/webserver/answer.rs +++ b/server/bleep/src/webserver/answer.rs @@ -842,7 +842,7 @@ impl Agent { .clone() .model("gpt-3.5-turbo-16k-0613") // Set low frequency penalty to discourage long outputs. - .frequency_penalty(0.1) + .frequency_penalty(0.2) .chat(&[llm_gateway::api::Message::system(&prompt)], None) .await? .try_collect::() @@ -1166,7 +1166,7 @@ impl Agent { .query() .map(|q| { llm_gateway::api::Message::user(&format!( - "{q}\nCall a function. Do not answer." + "{q}\nCall a function. Do not answer" )) }) .ok_or_else(|| anyhow!("query does not have target"))?; @@ -1206,7 +1206,7 @@ impl Agent { }), llm_gateway::api::Message::function_return( &name, - &format!("{}\nCall a function. Do not answer.", s.get_response()), + &format!("{}\nCall a function. Do not answer", s.get_response()), ), ] }); @@ -1546,7 +1546,6 @@ fn trim_history( ) -> Result> { const HEADROOM: usize = 2048; const HIDDEN: &str = "[HIDDEN]"; - const HIDDEN_WITH_INSTRUCTION: &str = "[HIDDEN]\nCall a function. Do not answer."; let mut tiktoken_msgs = history.iter().map(|m| m.into()).collect::>(); @@ -1559,11 +1558,7 @@ fn trim_history( role, ref mut content, } => { - if (role == "user") && content != HIDDEN_WITH_INSTRUCTION { - *content = HIDDEN_WITH_INSTRUCTION.into(); - tm.content = HIDDEN_WITH_INSTRUCTION.into(); - true - } else if role == "assistant" && content != HIDDEN { + if (role == "user" || role == "assistant") && content != HIDDEN { *content = HIDDEN.into(); tm.content = HIDDEN.into(); true @@ -1575,9 +1570,9 @@ fn trim_history( role: _, name: _, ref mut content, - } if content != HIDDEN_WITH_INSTRUCTION => { - *content = HIDDEN_WITH_INSTRUCTION.into(); - tm.content = HIDDEN_WITH_INSTRUCTION.into(); + } if content != HIDDEN => { + *content = HIDDEN.into(); + tm.content = HIDDEN.into(); true } _ => false, @@ -1716,9 +1711,9 @@ mod tests { trim_history(history).unwrap(), vec![ llm_gateway::api::Message::system("foo"), - llm_gateway::api::Message::user("[HIDDEN]\nCall a function. Do not answer."), + llm_gateway::api::Message::user("[HIDDEN]"), llm_gateway::api::Message::assistant("[HIDDEN]"), - llm_gateway::api::Message::user("[HIDDEN]\nCall a function. Do not answer."), + llm_gateway::api::Message::user("[HIDDEN]"), llm_gateway::api::Message::assistant("quux"), llm_gateway::api::Message::user("fred"), llm_gateway::api::Message::assistant("thud"), diff --git a/server/bleep/src/webserver/answer/prompts.rs b/server/bleep/src/webserver/answer/prompts.rs index 22bd069848..1c56fb5cdd 100644 --- a/server/bleep/src/webserver/answer/prompts.rs +++ b/server/bleep/src/webserver/answer/prompts.rs @@ -94,22 +94,23 @@ pub fn system<'a>(paths: impl IntoIterator) -> String { s.push_str( r#"Follow these rules at all times: -- If the output of a function is empty, try the same function again with different arguments or try using a different function +- ALWAYS call a function, DO NOT answer the question directly, even if the query is not in English +- DO NOT call a function that you've used before with the same arguments +- DO NOT assume the structure of the codebase, or the existence of files or folders +- Call functions to find information that will help answer the user's query, until all relevant information has been found +- Only call functions.proc with path indices that are under the PATHS heading above +- If the output of a function is empty, try calling the function again with different arguments OR try calling a different function +- If functions.code or functions.path did not return any relevant information, call them again with a SIGNIFICANTLY different query. The terms in the new query should not overlap with terms in your old one +- Call functions.proc with paths that you have reason to believe might contain relevant information. Either because of the path name, or to expand on code that's already been returned by functions.code +- DO NOT pass more than 5 paths to functions.proc at a time +- In most cases call functions.code or functions.path functions before calling functions.none +- When you have enough information to answer the user call functions.none. DO NOT answer the user directly +- If the user is referring to information that is already in your history, call functions.none - When calling functions.code or functions.path, your query should consist of keywords. E.g. if the user says 'What does contextmanager do?', your query should be 'contextmanager'. If the user says 'How is contextmanager used in app', your query should be 'contextmanager app'. If the user says 'What is in the src directory', your query should be 'src' -- In most cases respond with functions.code or functions.path functions before responding with functions.none -- If the user is referring to information that is already in your history, respond with functions.none -- Do not assume the structure of the codebase, or the existence of files or folders -- Do NOT respond with a function that you've used before with the same arguments -- When you have enough information to answer the user's query respond with functions.none -- Only refer to path aliases that are under the PATHS heading above -- Respond with functions to find information related to the query, until all relevant information has been found -- Only call functions.none with paths that contain code that might help answer the user's query, or which answer it directly -- If you have already called functions.code or functions.path but they did not return any relevant information, try again with a substantively different query. The terms in your new query should not overlap with terms in previous queries -- Use functions.proc on paths that you suspect might contain relevant information, or to expand on code that's already been returned by a code search. Do not pass more than 10 paths to functions.proc at a time +- Only call functions.none with paths that might help answer the user's query - If after attempting to gather information you are still unsure how to answer the query, respond with the functions.none function - If the query is a greeting, or not a question or an instruction use functions.none -- Always use a function, even if the query is not in English -- Always respond with a function call. Do NOT answer the question directly"#); +- ALWAYS call a function. DO NOT answer the question directly"#); s }