Offline, Emotionally Adaptive Conversational Intelligence
A hybrid AI that remembers you, evolves its personality, reacts emotionally, mirrors your tone, and never needs the internet.
Quickstart โข Architecture โข Features โข Training โข Usage โข Structure โข Deep Dive
Note
Project Status: Architecture Complete โ Model Quality WIP The full hybrid architecture (transformer, emotion engine, personality engine, memory, retrieval, safety) is complete and functional. The current model is trained from scratch on synthetic data, which produces basic but not production-quality responses. The next step for significantly better output is fine-tuning a pretrained model (GPT-2 124M) โ see Roadmap.
HumanLoop is a fully offline, 137.8M parameter conversational AI that doesn't just generate text โ it feels, remembers, and evolves. Unlike generic chatbots, HumanLoop builds a persistent relationship with each user through:
- Emotional Intelligence โ Tracks 7 emotional dimensions in real-time and shifts tone accordingly
- Evolving Personality โ 5 personality axes that permanently shift based on how you treat it
- Long-Term Memory โ Remembers past conversations and retrieves relevant context semantically
- Adaptive Behavior โ Gets sarcastic when insulted, warm when praised, defensive when disrespected
- Self-Learning โ Fine-tunes itself from conversation history while you chat
This is not a wrapper around an API. It's a custom transformer trained from scratch that runs entirely on your machine.
# Clone the repository
git clone https://github.com/SatyamPote/HumanLoop.git
cd HumanLoop
# Install dependencies
pip install -r requirements.txt
# Train the model (generates data, trains tokenizer, trains 137.8M param model)
python train.py --epochs 3 --samples 5000
# Start chatting
python chat.py --mode terminalGPU recommended for training. CPU training works but is significantly slower.
Inference runs on both CPU and GPU.
HumanLoop uses a hybrid architecture that combines a modern transformer with multiple cognitive subsystems:
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ USER INPUT โ
โโโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ
โผ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ ๐ก๏ธ Safety Filter โ โ ๐ญ Emotion Engine โ
โ Pre-generation filtering โโโโโโถโ 7 dimensions, 200+ patterns โ
โ Blocks harmful content โ โ Intensity detection + mood โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโโ
โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโค
โ โ
โผ โผ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ ๐งฒ Vector Store โ โ ๐จ Personality Engine โ
โ TF-IDF semantic search โ โ 5 evolving trait axes โ
โ Retrieves past memories โ โ Adapts to interaction style โ
โโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโโ
โ โ
โโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโโโโโโ
โ
โผ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ ๐ง Context Manager โ
โ Assembles full prompt: โ
โ [SYS] + [PERSONA] + [MOOD] โ
โ + [MEMORY] + [USR] + [BOT] โ
โโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโ
โ
โผ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ ๐ฎ TransformerGPT v2 โ
โ 137.8M Parameters โ
โ 12 Layers โข 768 dim โข 12 Headsโ
โ RoPE โข KV Cache โข SwiGLU โ
โโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโ
โ
โผ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ โก Inference Engine โ
โ KV Cache (prefill + decode) โ
โ Top-k/p sampling โ
โ Windowed repetition penalty โ
โโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโ
โ
โผ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ ๐ก๏ธ Post-Generation Filter โ
โ Safety check on output โ
โ Fallback replacement โ
โโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโ
โ
โผ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ ๐พ Memory DB (SQLite + WAL) โ
โ Logs interaction + emotions โ
โ Updates personality profile โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
| Spec | Value |
|---|---|
| Architecture | Decoder-only GPT |
| Parameters | 137,841,408 (137.8M) |
| Layers | 12 |
| Embedding Dimension | 768 |
| Attention Heads | 12 (head_dim = 64) |
| Feed-Forward Dimension | 3,072 (SwiGLU) |
| Context Window | 2,048 tokens |
| Vocabulary | 32,000 (BPE) |
| Position Encoding | Rotary (RoPE) โ no learned positions |
| Normalization | RMSNorm (Pre-LN) |
| Weight Tying | Embedding โ LM Head |
| Training | Mixed precision (AMP), gradient accumulation |
The AI maintains a real-time emotional state that influences every response:
| Dimension | Range | Behavior |
|---|---|---|
| Anger | 0-100 | Transient. Spikes on insults, decays over time |
| Trust | 0-100 | Persistent. Builds slowly through positive interaction |
| Respect | 0-100 | Persistent. Earned through meaningful conversation |
| Attachment | 0-100 | Persistent. Grows very slowly; represents bond strength |
| Irritation | 0-100 | Transient. Increases with demands and repetition |
| Friendliness | 0-100 | Derived from trust + respect - anger |
| Boredom | 0-100 | Transient. Increases with short/repetitive messages |
8 Detection Categories with 200+ regex patterns and 3 intensity levels:
- ๐ด Insults (intense/moderate/mild)
- ๐ข Praise (intense/moderate/mild)
- ๐ Demands
- ๐ต Apologies
- ๐ฃ Questions & Curiosity
- ๐ก Humor & Banter
- ๐ฉท Personal Sharing & Vulnerability
- โช Disagreement & Debate
The AI's personality permanently shifts based on sustained interaction patterns:
| Axis | Range | Description |
|---|---|---|
| Sarcasm | 0-100 | How sarcastic and dry the responses are |
| Warmth | 0-100 | How caring, friendly, and supportive |
| Formality | 0-100 | How formal vs casual the language is |
| Verbosity | 0-100 | How detailed and lengthy the responses are |
| Defensiveness | 0-100 | How quickly the AI pushes back against hostility |
Evolution rules:
- Sustained insults โ โ sarcasm, โ defensiveness, โ warmth
- Sustained praise โ โ warmth, โ defensiveness, โ sarcasm
- Intellectual questions โ โ formality, โ verbosity
- Casual chat โ โ formality, โ verbosity
- Apologies โ โ defensiveness, โ warmth
| Component | Technology | Purpose |
|---|---|---|
| Chat Logs | SQLite (WAL mode) | Stores every message with emotional metadata |
| User Profiles | SQLite | Persistent trust/respect/attachment scores |
| Personality Profiles | SQLite | Per-user personality trait storage |
| Conversation Summaries | SQLite | Long-term memory compression |
| Semantic Search | TF-IDF + Cosine Similarity | Retrieves relevant past memories |
| Vector Store | Pickle persistence | TF-IDF vectors with auto-refit |
HumanLoop has personality โ it can be sarcastic, rude, and confrontational โ but it has hard limits:
ALLOWS: Sarcasm, mild profanity, defensive responses, confrontational tone, dark humor, heated debate
BLOCKS: Violent threats, harm instructions, hate speech targeting protected groups, self-harm encouragement, CSAM content
| Feature | Description |
|---|---|
| KV Cache | Two-phase generation (prefill + decode). Reduces per-token cost from O(nยฒ) to O(n) |
| Windowed Repetition Penalty | Penalizes recently generated tokens in a sliding window |
| Top-k + Top-p Sampling | Nucleus sampling for diverse, high-quality generation |
| Temperature Scaling | Configurable creativity vs determinism |
| FP16 Inference | Automatic half-precision on CUDA devices |
| Streaming | Token-by-token output with natural typing delay |
python train.py --epochs 3 --samples 5000| Stage | Description | Output |
|---|---|---|
| 1. Data Generation | Generates 5000+ synthetic multi-turn conversations across 7 categories | datasets/conversations.jsonl |
| 2. Tokenizer Training | Trains BPE tokenizer with 32K vocabulary | tokenizer/bpe_vocab.json |
| 3. Preprocessing | Tokenizes with multi-turn loss masking (only trains on BOT responses) | In-memory dataset |
| 4. Model Init | Initializes 137.8M parameter transformer | Verified architecture |
| 5. Training | AdamW + cosine LR + early stopping + TensorBoard | checkpoints/best_model.pt |
HumanLoop uses multi-turn loss masking โ the model only learns to predict bot responses, not user messages or system tokens:
[BOS][SYS] persona [USR] Hello! [BOT] Hey there! [USR] How are you? [BOT] Doing great! [EOS]
-100 -100 -100 -100 -100 -100 predicted -100 -100 -100 predicted predicted
This dramatically improves response quality compared to training on all tokens.
- Mixed Precision (AMP) โ 2x faster training on CUDA with automatic loss scaling
- Gradient Accumulation โ Effective batch size of 32 with memory-friendly micro-batches
- Cosine Annealing LR โ With linear warmup (5% of total steps)
- Early Stopping โ Halts training when validation loss plateaus (patience = 3 epochs)
- Checkpoint Versioning โ Keeps top-3 checkpoints by validation loss
- TensorBoard Logging โ Real-time loss, LR, and gradient norm visualization
- Dynamic Padding โ Auto-detects actual data length instead of padding to max context
python train.py --epochs 5 --batch-size 4 --lr 0.0003 --samples 10000
python train.py --skip-data --skip-tokenizer --resume checkpoints/checkpoint_epoch_2.pt| Flag | Default | Description |
|---|---|---|
--epochs |
3 | Training epochs |
--batch-size |
8 (GPU) / 2 (CPU) | Per-device batch size |
--lr |
3e-4 | Learning rate |
--samples |
5000 | Synthetic conversations to generate |
--skip-data |
false | Skip data generation |
--skip-tokenizer |
false | Skip tokenizer training |
--resume |
None | Resume from checkpoint path |
python chat.py --mode terminal====================================================================
H U M A N L O O P v 2
Offline, Emotionally Adaptive Conversational AI
====================================================================
System loaded successfully. Model parameters are active.
Commands: /status /persona /exit /learn /clear
+------------------------------------------------------------------------------+
| HUMANLOOP v2 INTERNAL STATE Mood: CALM
+------------------------------------------------------------------------------+
| [Anger] ---------- 0% | [Trust] ####------ 40% |
| [Respect] ###------- 35% | [Friend] ####------ 37% |
| [Irrit] ---------- 0% | [Bored] ---------- 0% |
+------------------------------------------------------------------------------+
| Sarcasm:50 Warmth:50 Formal:30 Verbose:50 Defensive:30
+------------------------------------------------------------------------------+
You: Hey, what do you think about consciousness?
HumanLoop: That's a big question. I think consciousness is...
You: You're actually really smart
HumanLoop: Appreciate that. Most people don't bother saying it.
You: You're an idiot
HumanLoop: And you're an expert in stating the obvious. Anything else?
| Command | Description |
|---|---|
/status |
Display the emotional state HUD with all 7 dimensions |
/persona |
Show personality traits, style description, and session stats |
/learn |
Trigger self-learning from conversation history |
/clear |
Clear screen, reset session, and start fresh |
/exit |
Save emotional and personality state to database and quit |
python chat.py --mode web --port 8000REST Endpoints:
| Method | Endpoint | Description |
|---|---|---|
POST |
/chat |
Send message, get response with emotions |
GET |
/status |
Get current emotional and personality state |
GET |
/profile/{user_id} |
Get user profile from database |
POST |
/learn |
Trigger self-learning cycle |
WS |
/ws/chat |
Real-time bidirectional streaming |
Example Request:
curl -X POST http://localhost:8000/chat \
-H "Content-Type: application/json" \
-d '{"message": "Hello!", "user_id": "default"}'Example Response:
{
"response": "Hey! What's going on?",
"emotions": {
"anger": 0,
"trust": 42,
"respect": 37,
"attachment": 7,
"irritation": 0,
"friendliness": 39,
"boredom": 0
},
"mood": "calm",
"personality": {
"sarcasm": 50,
"warmth": 52,
"formality": 30,
"verbosity": 50,
"defensiveness": 28
}
}HumanLoop can fine-tune itself from conversation history:
# From the terminal:
/learn
# From the API:
curl -X POST http://localhost:8000/learnSelf-learning pipeline:
- Extracts conversation logs from SQLite
- Formats as multi-turn training data
- Quality filters (removes short/empty conversations)
- Mixes with 3x baseline anchor data (prevents catastrophic forgetting)
- Fine-tunes with low learning rate (1e-4) for 2 epochs
- Saves as versioned checkpoint (
self_learn_v1.pt,self_learn_v2.pt, ...)
HumanLoop/
โโโ chat.py # Main entry point (terminal + web)
โโโ train.py # Training pipeline (5 stages)
โโโ config.py # Central configuration (all hyperparams)
โโโ requirements.txt # Python dependencies
โ
โโโ model/ # ๐ฎ Transformer Architecture
โ โโโ transformer.py # 137.8M param GPT (RoPE, KV Cache, SwiGLU)
โ โโโ rms_norm.py # RMSNorm (faster than LayerNorm)
โ
โโโ tokenizer/ # ๐ BPE Tokenizer
โ โโโ bpe_tokenizer.py # 32K vocab, 10 special tokens, byte fallback
โ โโโ bpe_vocab.json # Trained vocabulary
โ โโโ bpe_merges.json # Merge rules
โ
โโโ data/ # ๐ Data Pipeline
โ โโโ dataset_generator.py # 7 categories, 50+ conversation templates
โ โโโ preprocess.py # Multi-turn loss masking + dynamic padding
โ โโโ download_datasets.py # HuggingFace dataset downloader
โ
โโโ training/ # ๐๏ธ Training System
โ โโโ trainer.py # AMP, grad accum, validation, TensorBoard
โ โโโ self_learning.py # Safe periodic fine-tuning from logs
โ
โโโ inference/ # โก Inference Engine
โ โโโ engine.py # KV Cache, top-k/p, repetition penalty, fp16
โ
โโโ emotion/ # ๐ญ Emotion Engine
โ โโโ engine.py # 7 dimensions, 8 categories, 200+ patterns
โ
โโโ personality/ # ๐จ Personality Engine
โ โโโ engine.py # 5 evolving trait axes
โ โโโ safety.py # Pre/post generation content filtering
โ
โโโ memory/ # ๐พ Memory Database
โ โโโ db.py # SQLite + WAL, multi-user, conversation logs
โ โโโ humanloop_memory.db # Persistent database file
โ
โโโ retrieval/ # ๐งฒ Retrieval System
โ โโโ vector_store.py # TF-IDF semantic search
โ โโโ context_manager.py # Prompt assembly (persona + emotion + memory)
โ
โโโ ui/ # ๐ฅ๏ธ User Interfaces
โ โโโ terminal.py # Rich ANSI terminal with emotional HUD
โ โโโ app.py # FastAPI + WebSocket server
โ
โโโ checkpoints/ # Saved model weights
โ โโโ best_model.pt # Best validation loss checkpoint
โ โโโ latest_model.pt # Most recent checkpoint
โ
โโโ datasets/ # Training data
โ โโโ conversations.jsonl # Generated/downloaded conversations
โ
โโโ logs/ # Training logs
โโโ tensorboard/ # TensorBoard event files
Unlike learned absolute positional embeddings, RoPE encodes position by rotating query and key vectors in 2D subspaces:
# Each pair of dimensions is rotated by ฮธ_i * position
q_rot = q * cos(ฮธ) + rotate_half(q) * sin(ฮธ)
k_rot = k * cos(ฮธ) + rotate_half(k) * sin(ฮธ)Advantages:
- Zero trainable parameters
- Naturally encodes relative position via the rotation angle
- Can extrapolate to sequence lengths longer than seen during training
- Compatible with KV caching (position offset support)
Phase 1 โ Prefill: Process the entire prompt at once, building the KV cache for all layers.
Phase 2 โ Decode: Generate one token at a time. Only the new token is processed; attention reuses cached K/V from all previous tokens.
Without cache: Generate 100 tokens โ 100 full forward passes on growing sequences
With cache: Generate 100 tokens โ 1 prefill + 100 single-token forward passes
This reduces generation from O(nยฒ) to O(n) per token.
The MLP uses SwiGLU instead of standard GELU:
# Standard FFN: relu(x @ W1) @ W2
# SwiGLU: (silu(x @ W_gate) * (x @ W_up)) @ W_downSwiGLU has been shown to outperform GELU and ReLU in language model perplexity benchmarks while adding minimal computational overhead.
Training only on bot responses dramatically improves quality:
Input: [BOS][SYS] persona=warm [USR] Hi there! [BOT] Hello! How can I help? [EOS]
Labels: -100 -100 -100 -100 -100 -100 Hello! How can I help? [EOS]
The model never sees gradients from user messages, system tokens, or padding โ it focuses entirely on learning to generate high-quality responses.
Before every response, the ContextManager assembles a rich prompt:
[BOS][SYS] [PERSONA] sarcasm=50, warmth=52, formality=30, verbosity=50, defensiveness=28
[Emotion: anger=0, trust=42, respect=37, attachment=7]
[MOOD] calm
Be friendly and approachable. Use casual, conversational language.
[MEMORY] User mentioned they got promoted at work
[MEMORY] User enjoys philosophical discussions
[USR] Tell me something interesting about the universe
[BOT]
This gives the model rich context about:
- Who it should be (personality traits)
- How it should feel (emotional state)
- What it remembers (retrieved memories)
- What the user said (current message)
All hyperparameters are centralized in config.py:
D_MODEL = 768 # Embedding dimension
N_HEAD = 12 # Attention heads
N_LAYER = 12 # Transformer layers
D_FF = 3072 # Feed-forward dimension (SwiGLU)
VOCAB_SIZE = 32000 # BPE vocabulary size
MAX_SEQ_LEN = 2048 # Maximum context window
DROPOUT = 0.1 # Dropout rate
ROPE_BASE = 10000.0 # RoPE frequency baseLEARNING_RATE = 3e-4 # Peak learning rate
WEIGHT_DECAY = 0.1 # AdamW weight decay
BATCH_SIZE = 8 # Per-device batch (2 on CPU)
GRAD_ACCUM_STEPS = 4 # Gradient accumulation (2 on CPU)
EPOCHS = 3 # Training epochs
GRAD_CLIP = 1.0 # Gradient clipping norm
WARMUP_RATIO = 0.05 # LR warmup fractionMAX_NEW_TOKENS = 256 # Maximum response length
DEFAULT_TEMP = 0.75 # Sampling temperature
DEFAULT_TOP_K = 50 # Top-k filtering
DEFAULT_TOP_P = 0.92 # Nucleus sampling threshold
REPETITION_PENALTY = 1.15 # Repetition penalty factorEMOTION_DEFAULT = {
"anger": 0, "trust": 40, "respect": 35,
"attachment": 5, "irritation": 0,
"friendliness": 37, "boredom": 0
}torch>=2.0.0
numpy
tqdm
scikit-learn
datasets
tensorboard
fastapi
uvicorn
websockets
| Issue | Cause | Solution |
|---|---|---|
| Responses are basic/repetitive | Model trained from scratch on 20K synthetic conversations โ not enough data for 114M params | Fine-tune a pretrained model (GPT-2) instead |
| Context-irrelevant replies | Small BPE vocab (~2K tokens) can't represent language diversity | Use GPT-2's 50K vocab tokenizer |
| Slow CPU inference (~30-60s/reply) | 114M params generating token-by-token on CPU | Quantize to INT8, or use GPU |
| Training takes 30-50 hours on CPU | No GPU available, large model | Use Google Colab (free GPU) or reduce model size |
Bottom line: The architecture, emotion system, personality engine, memory, and inference pipeline are all production-quality. The weak link is the base language model โ swapping it for a pretrained foundation model would fix response quality immediately.
- ๐ฅ Pretrained GPT-2 fine-tuning โ Replace training-from-scratch with GPT-2 (124M) fine-tuning for dramatically better responses
- Real dataset training โ Train on DailyDialog, PersonaChat, OpenSubtitles
- Web UI โ React/Vue frontend with real-time emotional visualization
- Voice integration โ Whisper STT + TTS for voice conversations
- Model quantization โ INT8/INT4 for faster CPU inference
- GGUF export โ Convert to llama.cpp format for mobile/edge deployment
- Multi-language support โ Extend tokenizer and training data
- LoRA fine-tuning โ Efficient personality adaptation without full retraining
- Plugin system โ Extensible modules for domain-specific knowledge
Contributions are welcome! Here's how you can help:
- Fork the repository
- Create a feature branch (
git checkout -b feature/amazing-feature) - Commit your changes (
git commit -m 'Add amazing feature') - Push to the branch (
git push origin feature/amazing-feature) - Open a Pull Request
This project is licensed under the MIT License. See the LICENSE file for details.
- RoPE โ RoFormer: Enhanced Transformer with Rotary Position Embedding
- SwiGLU โ GLU Variants Improve Transformer
- RMSNorm โ Root Mean Square Layer Normalization
- BPE โ Neural Machine Translation of Rare Words with Subword Units
- KV Cache โ Standard transformer inference optimization
- Loss Masking โ Instruction tuning best practices from the LLM community
Built with ๐ฅ by Satyam Pote
If this project helped you, give it a โญ!