From 60fed78d17f2417ae80b08ffa26d1638753f093e Mon Sep 17 00:00:00 2001 From: John Costa Date: Thu, 10 Jul 2025 10:03:55 +0100 Subject: [PATCH] feat: config object to abstract user information --- src/ai/index.ts | 25 +++++++++---------------- src/config/index.ts | 27 +++++++++++++++++++++++++++ src/index.ts | 3 ++- src/telegram/index.ts | 15 ++++++++++++--- 4 files changed, 50 insertions(+), 20 deletions(-) create mode 100644 src/config/index.ts diff --git a/src/ai/index.ts b/src/ai/index.ts index 9321885..0fdebf7 100644 --- a/src/ai/index.ts +++ b/src/ai/index.ts @@ -1,28 +1,19 @@ import { createRequesty } from "@requesty/ai-sdk"; -import { generateText, tool, ToolResultUnion, type CoreMessage } from "ai"; +import { generateText, tool, type CoreMessage } from "ai"; import z from "zod"; const requesty = createRequesty({ apiKey: process.env.REQUESTY_API_KEY, }); -const system = ` +const getSystem = (bossInfo: string, userInfo: string) => ` Todays date: ${new Date().toISOString()} -You are a personal assistant to John Costa, a software engineer. And you will mostly talk to Rio, John's Fiancee. -Your job is to make sure that Rio's queries are answered, without bothering John. +# Boss Info +${bossInfo} -About John: -- He is 23. -- He is a bit silly. -- He loves cat memes. -- He is a programmer -- He loves Rio - -You will be speaking to Rio. Only forward Rio's messages if you believe them to be urgent. -You must always return a message to Rio if you have forwarded the message. - -You may also give John tasks, with a time and date attached to them. +# You are speaking with +${userInfo} `; const createTools = () => ({ @@ -70,6 +61,8 @@ export type ToolActions = { export const getResponse = async ( actions: ToolActions, messages: CoreMessage[], + bossInfo: string, + userInfo: string, ): Promise => { const tools = createTools(); for (const [k, v] of Object.entries(tools)) { @@ -78,7 +71,7 @@ export const getResponse = async ( const result = await generateText({ model: requesty("smart/task"), - system, + system: getSystem(bossInfo, userInfo), messages, tools, }); diff --git a/src/config/index.ts b/src/config/index.ts new file mode 100644 index 0000000..93b8aa1 --- /dev/null +++ b/src/config/index.ts @@ -0,0 +1,27 @@ +export type Config = { + description: string; + + // Map: Telegram Username -> User information for AI context. + whitelist: Record; +}; + +export const testConfig: Config = { + description: ` +Your boss is John Costa. + +About John: +- He is 23. +- He is a bit silly. +- He loves cat memes. +- He is a programmer +- He loves Rio + +He is very busy so he wishes you to do your best to answer users questions. + `, + whitelist: { + Johncosta27: ` + This is Rio. She is John's wife, and she might have important things to tell John. + But you should try and not let her past you because John is very busy. +`, + }, +}; diff --git a/src/index.ts b/src/index.ts index df79a15..b7711fa 100644 --- a/src/index.ts +++ b/src/index.ts @@ -1,6 +1,7 @@ +import { testConfig } from "./config"; import { setupTelegram } from "./telegram"; setupTelegram({ bossChatId: "1502730007", - whitelist: new Set(["Johncosta27"]), + config: testConfig, }); diff --git a/src/telegram/index.ts b/src/telegram/index.ts index eaffe5a..d25ece4 100644 --- a/src/telegram/index.ts +++ b/src/telegram/index.ts @@ -1,6 +1,7 @@ import type { CoreMessage } from "ai"; import TelegramBot from "node-telegram-bot-api"; import { getResponse } from "../ai"; +import { Config } from "../config"; const CHAT_MAX_LENGTH = 100; @@ -42,16 +43,18 @@ const createChat = () => { type TelegramOptions = { bossChatId: string; - whitelist: Set; + config: Config; }; -export const setupTelegram = ({ bossChatId, whitelist }: TelegramOptions) => { +export const setupTelegram = ({ bossChatId, config }: TelegramOptions) => { console.log("Setting up telegram bot"); const bot = new TelegramBot(process.env.TELEGRAM_TOKEN ?? "", { polling: true, }); + const whitelistUsers = Object.keys(config.whitelist); + const chats = createChat(); bot.on("message", async (msg, meta) => { @@ -74,11 +77,15 @@ export const setupTelegram = ({ bossChatId, whitelist }: TelegramOptions) => { return; } - if (!whitelist.has(fromUsername)) { + if (!whitelistUsers.includes(fromUsername)) { bot.sendMessage(msg.chat.id, "Sorry, you are not part of the whitelist."); return; } + const userInfo = + config.whitelist[fromUsername] ?? + `This is ${msg.from?.first_name} ${msg.from?.last_name}. We don't know anything about them.`; + chats.addMessage(msg.chat.id, text); const messages = await getResponse( @@ -96,6 +103,8 @@ export const setupTelegram = ({ bossChatId, whitelist }: TelegramOptions) => { }, // SAFETY: addMessage is called before, therefore this function cannot throw. chats.getChat(msg.chat.id), + config.description, + userInfo, ); chats.setMessages(msg.chat.id, messages);