They can now answer
This commit is contained in:
1
.env
1
.env
@@ -1,2 +1,3 @@
|
|||||||
MODEL_PATH=./model
|
MODEL_PATH=./model
|
||||||
MODEL_NAME=Qwen2.5-7B-Instruct-Q8.gguf
|
MODEL_NAME=Qwen2.5-7B-Instruct-Q8.gguf
|
||||||
|
CONTEXT_SIZE=4096
|
||||||
@@ -5,7 +5,6 @@ EndProject
|
|||||||
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{0C9A5F05-7CED-450F-9757-C641D75F8787}"
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{0C9A5F05-7CED-450F-9757-C641D75F8787}"
|
||||||
ProjectSection(SolutionItems) = preProject
|
ProjectSection(SolutionItems) = preProject
|
||||||
compose.yaml = compose.yaml
|
compose.yaml = compose.yaml
|
||||||
prompt\nemesis.txt = prompt\nemesis.txt
|
|
||||||
EndProjectSection
|
EndProjectSection
|
||||||
EndProject
|
EndProject
|
||||||
Global
|
Global
|
||||||
|
|||||||
@@ -2,10 +2,12 @@
|
|||||||
|
|
||||||
namespace TelegramBot;
|
namespace TelegramBot;
|
||||||
|
|
||||||
public class Agent(Actor actor, long telegramId, string name, string username, TelegramBotClient bot) {
|
public class Agent(Actor actor, long telegramId, string name, string username, TelegramBotClient bot, string systemPrompt, int tokenLenght) {
|
||||||
public Actor Actor { get; } = actor;
|
public Actor Actor { get; } = actor;
|
||||||
public long TelegramId { get; } = telegramId;
|
public long TelegramId { get; } = telegramId;
|
||||||
public string Username { get; } = username;
|
public string Username { get; } = username;
|
||||||
public string Name { get; } = name;
|
public string Name { get; } = name;
|
||||||
public TelegramBotClient Bot { get; } = bot;
|
public TelegramBotClient Bot { get; } = bot;
|
||||||
|
public string SystemPrompt { get; } = systemPrompt;
|
||||||
|
public int SystemPromptLength { get; } = tokenLenght;
|
||||||
}
|
}
|
||||||
@@ -6,14 +6,16 @@ using OpenAI.Chat;
|
|||||||
|
|
||||||
namespace TelegramBot;
|
namespace TelegramBot;
|
||||||
|
|
||||||
public class OpenAiAgent
|
public class OpenAiAgent {
|
||||||
{
|
|
||||||
private ApiKeyCredential apikey;
|
private ApiKeyCredential apikey;
|
||||||
private OpenAIClient oaiClient;
|
private OpenAIClient oaiClient;
|
||||||
private ChatClient chatClient;
|
private ChatClient chatClient;
|
||||||
private HttpClient httpClient;
|
private HttpClient httpClient;
|
||||||
|
|
||||||
private Dictionary<(long, Actor), List<(ChatMessage, int)>> oaiChats = new();
|
private Dictionary<(long, Actor), List<(ChatMessage, int)>> oaiChats = new();
|
||||||
|
|
||||||
|
public int ContextSize { get; set; } = 4096;
|
||||||
|
|
||||||
public OpenAiAgent(string baseUrl, string apiKey, string model) {
|
public OpenAiAgent(string baseUrl, string apiKey, string model) {
|
||||||
OpenAIClientOptions options = new OpenAIClientOptions() {
|
OpenAIClientOptions options = new OpenAIClientOptions() {
|
||||||
Endpoint = new(baseUrl),
|
Endpoint = new(baseUrl),
|
||||||
@@ -79,8 +81,29 @@ public class OpenAiAgent
|
|||||||
return chat!;
|
return chat!;
|
||||||
}
|
}
|
||||||
|
|
||||||
public string GetChatResponse(long chatId, Actor actor) {
|
public string GetChatResponse(long chatId, Agent agent) {
|
||||||
return String.Empty;
|
int currentContextSize = agent.SystemPromptLength;
|
||||||
|
List<ChatMessage> chatHistory = new();
|
||||||
|
chatHistory.Add(new SystemChatMessage(agent.SystemPrompt));
|
||||||
|
|
||||||
|
//Fetch the chat history from the dictionary trimming to the context size
|
||||||
|
var history = GetChatHistory(chatId, agent.Actor).ToList();
|
||||||
|
history.Reverse();
|
||||||
|
//Add the chat history to the list until the context size is reached
|
||||||
|
foreach (var (message, tokenLenght) in history) {
|
||||||
|
if (currentContextSize + tokenLenght > ContextSize) break;
|
||||||
|
chatHistory.Add(message);
|
||||||
|
currentContextSize += tokenLenght;
|
||||||
|
}
|
||||||
|
//Reverse the chat history to get the correct order
|
||||||
|
chatHistory.Reverse(1, chatHistory.Count - 1);
|
||||||
|
|
||||||
|
var completion = chatClient.CompleteChat(chatHistory).Value.Content[0].Text;
|
||||||
|
|
||||||
|
//Add the response to the chat history
|
||||||
|
ChatHistoryAppend(agent.Actor, chatId, completion);
|
||||||
|
|
||||||
|
return completion;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void AddChatToDictionary(long id) {
|
public void AddChatToDictionary(long id) {
|
||||||
|
|||||||
@@ -1,13 +1,15 @@
|
|||||||
using OpenAI.Chat;
|
using OpenAI.Chat;
|
||||||
using Telegram.Bot;
|
using Telegram.Bot;
|
||||||
using Telegram.Bot.Types;
|
using Telegram.Bot.Types;
|
||||||
using Telegram.Bot.Types.Enums;using TelegramBot;
|
using Telegram.Bot.Types.Enums;
|
||||||
|
using TelegramBot;
|
||||||
using File = System.IO.File;
|
using File = System.IO.File;
|
||||||
|
|
||||||
string baseUrl = Env.Get("OPENAI_BASE_URL");
|
string baseUrl = Env.Get("OPENAI_BASE_URL");
|
||||||
string apiKey = Env.Get("OPENAI_API_KEY");
|
string apiKey = Env.Get("OPENAI_API_KEY");
|
||||||
string model = Env.Get("OPENAI_MODEL");
|
string model = Env.Get("OPENAI_MODEL");
|
||||||
var oaiAgent = new OpenAiAgent(baseUrl, apiKey, model);
|
var oaiAgent = new OpenAiAgent(baseUrl, apiKey, model);
|
||||||
|
oaiAgent.ContextSize = Int32.Parse(Env.Get("CONTEXT_SIZE"));
|
||||||
|
|
||||||
Console.WriteLine("Starting the bot...");
|
Console.WriteLine("Starting the bot...");
|
||||||
|
|
||||||
@@ -43,7 +45,9 @@ Agent Nemesis = new(
|
|||||||
nemProfile.Result.Id,
|
nemProfile.Result.Id,
|
||||||
nemProfile.Result.FirstName,
|
nemProfile.Result.FirstName,
|
||||||
nemProfile.Result.Username!,
|
nemProfile.Result.Username!,
|
||||||
nemesisBot
|
nemesisBot,
|
||||||
|
nemesisPrompt,
|
||||||
|
oaiAgent.GetTokenLenght(nemesisPrompt)
|
||||||
);
|
);
|
||||||
|
|
||||||
var kroProfile = krolikBot.GetMe();
|
var kroProfile = krolikBot.GetMe();
|
||||||
@@ -52,7 +56,9 @@ Agent Krolik = new(
|
|||||||
kroProfile.Result.Id,
|
kroProfile.Result.Id,
|
||||||
kroProfile.Result.FirstName,
|
kroProfile.Result.FirstName,
|
||||||
kroProfile.Result.Username!,
|
kroProfile.Result.Username!,
|
||||||
krolikBot
|
krolikBot,
|
||||||
|
krolikPrompt,
|
||||||
|
oaiAgent.GetTokenLenght(krolikPrompt)
|
||||||
);
|
);
|
||||||
|
|
||||||
nemesisBot.OnMessage += OnNemMessage;
|
nemesisBot.OnMessage += OnNemMessage;
|
||||||
@@ -96,10 +102,10 @@ async Task OnMessage(Message msg, Agent agent) {
|
|||||||
Message: {msg.Text}
|
Message: {msg.Text}
|
||||||
""");
|
""");
|
||||||
//Add the message to the chat history
|
//Add the message to the chat history
|
||||||
oaiAgent.ChatHistoryAppend(Actor.User, chatid, "User: "+msg.Text);
|
oaiAgent.ChatHistoryAppend(Actor.User, chatid, "User: " + msg.Text);
|
||||||
|
|
||||||
//Check if the message is a reset command
|
//Check if the message is a reset command
|
||||||
if (msg.Text == "/reset" || msg.Text == "/reset@"+agent.Username) {
|
if (msg.Text == "/reset" || msg.Text == "/reset@" + agent.Username) {
|
||||||
oaiAgent.ResetChat(chatid);
|
oaiAgent.ResetChat(chatid);
|
||||||
await agent.Bot.SendMessage(chatid, "Chat context has been reset");
|
await agent.Bot.SendMessage(chatid, "Chat context has been reset");
|
||||||
return;
|
return;
|
||||||
@@ -107,25 +113,26 @@ async Task OnMessage(Message msg, Agent agent) {
|
|||||||
|
|
||||||
// Otherwise process it normally
|
// Otherwise process it normally
|
||||||
if (msg.Text!.Contains(agent.Name, StringComparison.OrdinalIgnoreCase) ||
|
if (msg.Text!.Contains(agent.Name, StringComparison.OrdinalIgnoreCase) ||
|
||||||
msg.ReplyToMessage?.From?.Id == agent.TelegramId || msg.Chat.Type == ChatType.Private) {
|
msg.ReplyToMessage?.From?.Id == agent.TelegramId ||
|
||||||
|
msg.Chat.Type == ChatType.Private) {
|
||||||
//Check if the chat (group) is rate limited
|
//Check if the chat (group) is rate limited
|
||||||
if (IsRateLimited(chatid)) {
|
/*if (IsRateLimited(chatid)) {
|
||||||
Console.WriteLine("No response due to ratelimit.");
|
Console.WriteLine("No response due to ratelimit.");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
await AnswerChat(chatid, msg.Text, tokenlenght, agent.Actor);
|
*/
|
||||||
|
await AnswerChat(chatid, agent);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
async Task AnswerChat(long chatId, string input, int tokenLenght, Actor actor) {
|
async Task AnswerChat(long chatId, Agent agent) {
|
||||||
//Limit the message to 1024 characters to avoid out of context jump
|
|
||||||
string text = input;
|
|
||||||
if (input.Length > 1024) text = input.Substring(0, 1024);
|
|
||||||
|
|
||||||
//Get the response from the OpenAI API
|
//Get the response from the OpenAI API
|
||||||
var result = oaiAgent.GetChatResponse(chatId, actor);
|
var result = oaiAgent.GetChatResponse(chatId, agent);
|
||||||
|
Console.WriteLine(
|
||||||
|
$"""
|
||||||
|
{agent.Name} has responded with: {result}
|
||||||
|
""");
|
||||||
//Send the response to the user
|
//Send the response to the user
|
||||||
await krolikBot.SendMessage(chatId, result);
|
await agent.Bot.SendMessage(chatId, result);
|
||||||
}
|
}
|
||||||
@@ -6,6 +6,7 @@
|
|||||||
context: .
|
context: .
|
||||||
dockerfile: TelegramBot/Dockerfile
|
dockerfile: TelegramBot/Dockerfile
|
||||||
env_file:
|
env_file:
|
||||||
|
- .env
|
||||||
- TelegramBot/.env
|
- TelegramBot/.env
|
||||||
|
|
||||||
llm-server:
|
llm-server:
|
||||||
@@ -15,7 +16,7 @@
|
|||||||
- ${MODEL_PATH}:/models
|
- ${MODEL_PATH}:/models
|
||||||
ports:
|
ports:
|
||||||
- "80:80"
|
- "80:80"
|
||||||
command: -m /models/${MODEL_NAME} --port 80 --host 0.0.0.0 -n 128 -c 4096 --no-mmap -ngl 50 -fa -np 4
|
command: -m /models/${MODEL_NAME} --port 80 --host 0.0.0.0 -n 128 -c ${CONTEXT_SIZE} --no-mmap -ngl 50 -fa -np 4
|
||||||
deploy:
|
deploy:
|
||||||
resources:
|
resources:
|
||||||
reservations:
|
reservations:
|
||||||
|
|||||||
Reference in New Issue
Block a user