Docs: Update README and CLAUDE.md for recent architecture changes
Some checks failed
Auto Build and Push Docker Image / build (push) Failing after 46s

- Updated docs to reflect switch to Bigrams (order 1)
- Documented incremental DB updates and performance caching
- Added mention of @-ping protection in features
- Updated AI context guidance (20 messages instead of 50)
- Fixed AI_SYSTEM_PROMPT env fallback in index.ts
This commit is contained in:
2026-05-14 13:38:23 +02:00
parent cb70812739
commit e49bd060d2
3 changed files with 38 additions and 55 deletions

View File

@@ -4,7 +4,7 @@ This file provides guidance to Claude Code (claude.ai/code) when working with co
## Project Overview ## Project Overview
Telegram bot built with TypeScript and [Telegraf](https://telegraf.js.org/). Uses Markov chains with trigrams to generate sentences from learned messages. Optional KI/LLM integration via OpenAI-compatible API. Each chat has its own isolated data. Telegram bot built with TypeScript and [Telegraf](https://telegraf.js.org/). Uses Markov chains with bigrams to generate sentences from learned messages. Optional KI/LLM integration via OpenAI-compatible API. Each chat has its own isolated data.
## Commands ## Commands
@@ -20,52 +20,54 @@ docker compose up -d --build # Docker deployment
``` ```
src/ src/
├── index.ts # Bot entry point, commands, setup wizard ├── index.ts # Bot entry point, commands, setup wizard
├── markov.ts # Markov chain with trigram support ├── markov.ts # Markov chain with bigram support (order 1)
├── database.ts # SQLite persistence layer ├── database.ts # SQLite persistence layer (optimized)
└── ai.ts # OpenAI-compatible client └── ai.ts # OpenAI-compatible client
``` ```
**Data flow (Markov):** **Data flow (Markov):**
1. Message received → `chain.learn(text)`SQLite 1. Message received → `chain.learn(text)``updateChain(learned)` → SQLite (incremental)
2. Trigger check (reply/mention/random) 2. Trigger check (reply/mention/random)
3. If triggered → `chain.generate()` → reply 3. If triggered → `chain.generate()` sanitize (@-removal) → reply
**Data flow (AI):** **Data flow (AI):**
1. `/ask-ai` or trigger word detected 1. `/ask-ai` or trigger word detected
2. Load last 50 messages as context 2. Load last 20 messages as context
3. Build prompt (global + group prompt) 3. Build prompt (global + group prompt)
4. Call OpenAI-compatible API → reply 4. Call OpenAI-compatible API → sanitize (@-removal) → reply
**Per-chat isolation:** **Per-chat isolation:**
- Each chat has separate Markov chain data - Each chat has separate Markov chain data
- Each chat has separate AI settings - Each chat has separate AI settings
- Each chat has separate message context (50 messages) - Each chat has separate message context (20 messages)
## Key Implementation Details ## Key Implementation Details
### Markov Chain (markov.ts) ### Markov Chain (markov.ts)
- Uses **trigrams** (order=2): "word1 word2" → "word3" - Uses **bigrams** (order=1): "word1" → "word2" for higher creativity
- Weighted random selection based on frequency - Weighted random selection based on frequency
- Generates sentences up to 20 words - No character filtering (keeps emojis/punctuation)
### Database (database.ts) ### Database (database.ts)
- SQLite with `better-sqlite3` (synchronous API) - SQLite with `better-sqlite3` (synchronous API)
- **Optimized storage:** `updateChain` uses `ON CONFLICT` for incremental updates (no full rewrites)
- Tables: - Tables:
- `chat_settings` - Markov probability - `chat_settings` - Markov probability
- `markov_transitions` - Word transitions - `markov_transitions` - Word transitions
- `markov_starts` - Sentence starts - `markov_starts` - Sentence starts
- `ai_settings` - KI configuration per chat - `ai_settings` - KI configuration per chat
- `message_context` - Last 50 messages per chat - `message_context` - Last 20 messages per chat
- `setup_sessions` - Setup wizard state - `setup_sessions` - Setup wizard state
- Automatic cleanup every 24h - Automatic cleanup every 24h
### AI Client (ai.ts) ### AI Client (ai.ts)
- OpenAI-compatible API (works with OpenAI, Ollama, OpenRouter, etc.) - OpenAI-compatible API (works with OpenAI, Ollama, OpenRouter, etc.)
- Parameters: `temperature: 0.8`, `presence_penalty: 0.6`, `frequency_penalty: 0.6`
- Prompt system: - Prompt system:
- Global: `data/system-prompt.txt``.env` fallback → default - Global: `data/system-prompt.txt``.env` fallback → default
- Group-specific: stored in DB per chat - Group-specific: stored in DB per chat
- API key masking for security - API key masking for security
- Context: Last 50 messages - Context: Last 20 messages
### Setup Wizard ### Setup Wizard
- Started via `/ai setup` in group - Started via `/ai setup` in group
@@ -73,6 +75,12 @@ src/
- API keys never shown in full - API keys never shown in full
- Steps: Provider → API Key → Model → URL → Trigger/Prob → Group Prompt - Steps: Provider → API Key → Model → URL → Trigger/Prob → Group Prompt
### Performance Features
- **Admin Cache:** 5-minute cache for chat administrators to reduce API calls
- **Bot Info Cache:** Cached bot username and ID
- **Incremental DB:** Markov updates don't delete existing data
- **Typing Status:** AI responses show "typing" status while generating
## Environment ## Environment
```env ```env
@@ -80,46 +88,14 @@ BOT_TOKEN= # Telegram bot token (required)
AI_DEFAULT_API_KEY= # Default API key (optional) AI_DEFAULT_API_KEY= # Default API key (optional)
AI_DEFAULT_BASE_URL= # Default API URL (default: OpenAI) AI_DEFAULT_BASE_URL= # Default API URL (default: OpenAI)
AI_DEFAULT_MODEL= # Default model (default: gpt-4o-mini) AI_DEFAULT_MODEL= # Default model (default: gpt-4o-mini)
AI_SYSTEM_PROMPT= # Global system prompt (fallback, see below) AI_SYSTEM_PROMPT= # Global system prompt (fallback)
``` ```
**System Prompt Loading:** **System Prompt Loading:**
1. `data/system-prompt.txt` (persistent, editable without rebuild) 1. `data/system-prompt.txt` (persistent, editable without rebuild)
2. `AI_SYSTEM_PROMPT` env variable (fallback) 2. `AI_SYSTEM_PROMPT` env variable (fallback)
3. Hardcoded default (last resort) 3. Hardcoded default (last resort)
AI_DEFAULT_MODEL= # Default model (default: gpt-4o-mini)
AI_SYSTEM_PROMPT= # Global system prompt
```
## Database Schema ## Response Triggers & Sanitization
```sql - **@-Ping Protection:** All responses (AI & Markov) have `@` symbols removed before sending to prevent user notifications.
-- Markov
chat_settings (chat_id, probability)
markov_transitions (chat_id, key, next_word, count)
markov_starts (chat_id, key, count)
-- AI
ai_settings (chat_id, enabled, trigger_word, random_prob, group_prompt, provider, base_url, model, api_key)
message_context (chat_id, role, content, timestamp)
setup_sessions (user_id, chat_id, step, data)
```
## Response Triggers
### Markov (always active)
1. Reply to bot's message → always respond
2. @username mention → always respond
3. Random probability (configurable per chat)
### AI (when enabled)
1. `/ask-ai [text]` command
2. Trigger word (configurable, default: "ask-ai")
3. Random probability (configurable, default: 0%)
## Security
- API keys stored in database, never logged
- API keys masked in `/ai status` output: `sk-***...***xyz`
- Setup only via private chat
- Admin-only configuration commands

View File

@@ -5,11 +5,12 @@ Ein Telegram-Bot, der mithilfe von Markov Chains neue Sätze aus vorherigen Nach
## Features ## Features
- Lernt von allen Text-Nachrichten in einer Gruppe - Lernt von allen Text-Nachrichten in einer Gruppe
- Generiert grammatikalisch sinnvolle Sätze mit Trigrammen - Generiert kreative Sätze mit Bigrammen (hohe Diversität)
- **Automatischer @-Ping-Schutz** (entfernt @ vor dem Senden)
- Antwortet bei Reply, Erwähnung (@username) oder zufällig - Antwortet bei Reply, Erwähnung (@username) oder zufällig
- Pro-Chat-Wahrscheinlichkeit einstellbar (Admins) - Pro-Chat-Wahrscheinlichkeit einstellbar (Admins)
- **KI/LLM-Integration** (OpenAI, Ollama, OpenRouter, etc.) - **KI/LLM-Integration** (OpenAI, Ollama, OpenRouter, etc.)
- Persistente SQLite-Datenbank - **Leistungsoptimiert:** Inkrementelle SQLite-Updates statt kompletter Rewrites
- Docker-Support - Docker-Support
## Schnellstart ## Schnellstart
@@ -154,8 +155,8 @@ src/
└── ai.ts # OpenAI-kompatibler Client └── ai.ts # OpenAI-kompatibler Client
``` ```
- **Markov Chain** mit Trigrammen für bessere Grammatik - **Markov Chain** mit Bigrammen für hohe Kreativität und Abwechslung
- **SQLite** für persistente Speicherung - **SQLite** mit performanten ON CONFLICT Updates
- Pro Chat separate Daten/Lernkurve - Pro Chat separate Daten/Lernkurve
### Datenbank-Cleanup ### Datenbank-Cleanup

View File

@@ -56,14 +56,20 @@ function initSystemPrompt(): string {
// Load from persistent file // Load from persistent file
try { try {
const prompt = readFileSync(PERSISTENT_PROMPT_FILE, 'utf-8').trim(); let prompt = readFileSync(PERSISTENT_PROMPT_FILE, 'utf-8').trim();
// Fallback to .env if file is empty
if (!prompt && process.env.AI_SYSTEM_PROMPT) {
prompt = process.env.AI_SYSTEM_PROMPT.trim();
}
if (!prompt) { if (!prompt) {
console.warn('system-prompt.txt is empty, AI will use minimal default'); console.warn('system-prompt.txt and AI_SYSTEM_PROMPT env are empty, AI will use minimal default');
} }
return prompt || 'Du bist ein freundlicher Chat-Bot.'; return prompt || 'Du bist ein freundlicher Chat-Bot.';
} catch (error) { } catch (error) {
console.warn('Could not load system-prompt.txt:', error); console.warn('Could not load system-prompt.txt, checking .env fallback:', error);
return 'Du bist ein freundlicher Chat-Bot.'; return process.env.AI_SYSTEM_PROMPT || 'Du bist ein freundlicher Chat-Bot.';
} }
} }