{"id":50314399,"url":"https://github.com/miclaldogan/bantzv2","last_synced_at":"2026-05-28T23:01:46.081Z","repository":{"id":339289509,"uuid":"1161184982","full_name":"miclaldogan/bantzv2","owner":"miclaldogan","description":"Bantz won't be a helper; he will be your Host. Your computer will become his studio, and your tasks will give the \"entertainment.\" He won't just execute code; he will \"pull strings\" behind the scenes with a smile that you can hear through the text. ","archived":false,"fork":false,"pushed_at":"2026-05-21T18:35:09.000Z","size":2197,"stargazers_count":1,"open_issues_count":10,"forks_count":1,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-05-21T22:13:01.196Z","etag":null,"topics":["ai-assistant","chatbot","llm","local-first","ollama","privacy-first","productivity","python","terminal","textual","tui"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/miclaldogan.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":"CODE_OF_CONDUCT.md","threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":"SECURITY.md","support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2026-02-18T20:37:18.000Z","updated_at":"2026-05-21T16:01:05.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/miclaldogan/bantzv2","commit_stats":null,"previous_names":["miclaldogan/bantzv2"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/miclaldogan/bantzv2","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/miclaldogan%2Fbantzv2","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/miclaldogan%2Fbantzv2/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/miclaldogan%2Fbantzv2/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/miclaldogan%2Fbantzv2/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/miclaldogan","download_url":"https://codeload.github.com/miclaldogan/bantzv2/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/miclaldogan%2Fbantzv2/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":33629560,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-05-28T02:00:06.440Z","response_time":99,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["ai-assistant","chatbot","llm","local-first","ollama","privacy-first","productivity","python","terminal","textual","tui"],"created_at":"2026-05-28T23:00:57.070Z","updated_at":"2026-05-28T23:01:46.070Z","avatar_url":"https://github.com/miclaldogan.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Bantz\n\nBantz is a local-first AI assistant that runs on your Linux machine and acts as a personal butler — it has a voice, remembers things across sessions, runs scheduled jobs overnight, controls your desktop, reads your email, and talks to you like a person who's known you long enough to be useful. The primary interface is a terminal. Everything is local by default. Nothing phones home unless you configure it to.\n\n---\n\n## Architecture\n\nThe Brain (`core/brain.py`) sits at the center. Every request — typed, spoken, or sent via Telegram — goes through the same pipeline:\n\n```\nInput  (Terminal / Voice / Telegram)\n  │\n  ▼\nTranslation Layer       core/translation_layer.py\n  │  MarianMT Turkish↔English bridge; all internal processing in English\n  │\n  ▼\nMemory Injector         core/memory_injector.py\n  │  Injects: recent messages, desktop context, persona state, location\n  │\n  ▼\nOmniMemoryManager       memory/omni_memory.py\n  │  Parallel asyncio recall — Graph (35%) + Vector (40%) + Deep (25%)\n  │  400-token budget, entity-based re-ranking, zero sequential waiting\n  │\n  ▼\nRouting Engine          core/routing_engine.py + core/intent.py\n  │  quick_route(): hardware controls (TTS stop, wake word, ducking)\n  │  cot_route():   Chain-of-Thought LLM routing — tool selection + risk\n  │\n  ▼\nExecutor / Planner      agent/executor.py + agent/planner.py\n  │  Plan-and-Solve multi-step execution with $REF variable binding\n  │  Step failure → circuit breaker, optional replan\n  │\n  ▼\nFinalizer               core/finalizer.py\n  │  Butler persona enforcement, hallucination checks, error honesty\n  │\n  ▼\nMemory persistence      MemPalace (ChromaDB + SQLite KG)\n                        core/memory.py (session log, SQLite WAL)\n```\n\nSupporting systems run alongside the main loop:\n\n- **APScheduler** (`agent/job_scheduler.py`) — persistent SQLAlchemy job store, nightly maintenance/reflection/overnight email poll\n- **Ghost Loop** (`agent/ghost_loop.py`) — wake word → VAD capture → STT → brain dispatch\n- **Affinity Engine** (`agent/affinity_engine.py`) — cumulative score [-100, 100] drives persona tier\n- **Event Bus** (`core/event_bus.py`) — decoupled pub/sub between brain, TUI, voice, notifications\n- **GPS Server** (`core/gps_server.py`) — local HTTP server receiving phone location updates\n\n---\n\n## Features\n\n### What's working\n\n**Conversation and memory**\n- Persistent memory via MemPalace: ChromaDB vector store + SQLite knowledge graph\n- Hybrid recall: graph entities + semantic search run in parallel, merged by relevance\n- Session distillation: conversations mined into memory palace after each session\n- Onboarding: first-run identity setup, stored in memory wing\n- 400-token memory budget enforced per request (35/40/25 split across layers)\n\n**Voice pipeline**\n- Wake word detection via Porcupine (runs on dedicated daemon thread, always-on)\n- VAD-based audio capture via WebRTC VAD (auto-stops when you stop talking)\n- STT via faster-whisper (local, GPU-accelerated if available)\n- TTS via Piper + aplay (local, no cloud)\n- Audio ducking: system volume lowers during Bantz speech\n- Ambient sound classification: silence / speech / noisy from mic energy (no FFT)\n- Conversation window: 60s follow-up without re-triggering wake word\n\n**Scheduling and automation**\n- APScheduler with SQLAlchemy persistent job store (survives restarts)\n- Nightly maintenance workflow (3am): database compaction, memory distillation, digest prep\n- Nightly reflection (11pm): daily summary written to reflection journal\n- Overnight email/calendar poll (every 2h, 00-07): urgent keyword detection\n- Morning briefing prep (6am): pre-generates briefing for fast delivery at wake-up time\n- Reminder system with repeat support (30s check interval)\n\n**Desktop and computer control**\n- Desktop screenshot + optional VLM analysis (self-hosted endpoint)\n- Visual element detection and click via coordinate mapping\n- pyautogui-based GUI automation (mouse, keyboard, window focus)\n- Accessibility tree reading\n- App detector: tracks active application context (optional, polling-based)\n- Browser control via subprocess + xdotool\n\n**External integrations**\n- Gmail: read, search, compose, reply (Google OAuth2 PKCE flow)\n- Google Calendar: read events, create, check conflicts\n- Google Classroom: assignments, deadlines, announcements\n- Telegram bot: full two-way remote access, screenshot-on-request, whitelist by user ID\n- GPS location from phone via MQTT relay or direct HTTP push\n\n**Personality and adaptation**\n- 1920s English butler persona enforced at the Finalizer layer\n- Affinity Engine: score persists in SQLite, drives 5-tier formality ladder\n  - -100 → clipped and resentful\n  - 0 → neutral and professional\n  - +100 → deeply bonded, proactive, affectionate\n- Highwater protection: score can't drop from a tier you've reached\n- Bonding Meter: sigmoid-gated interaction scoring, configurable rate/midpoint\n\n**Security and permissions**\n- Risk level propagated through `BantzContext`: `safe` / `moderate` / `destructive`\n- Two-pass confirm flow: destructive operations require explicit `y` before execution\n- `DESTRUCTIVE_COMMANDS` frozenset in `tools/shell.py` — rm -rf, mkfs, dd, etc.\n- Shell timeout configurable, stderr captured separately\n\n**Infrastructure**\n- SQLite WAL mode throughout, thread-safe connection pool\n- Auto-migration: JSON data files → SQLite on first run (profile, places, schedule, session)\n- DataLayer singleton: unified init for all stores, called once at startup\n- pydantic-settings config: ~70 env vars via `.env`, all aliased\n\n**Interfaces**\n- Rich Live TUI: 4fps refresh, CPU/RAM/VRAM/DISK stats every 2s, scrollable log panel, Markdown rendering for code responses\n- `bantz --once \"query\"` for scripted single-shot queries\n- Headless daemon mode (`bantz --daemon`) for systemd operation\n\n**Multi-step workflows**\n- Chain-of-Thought routing selects tools and builds multi-step plans\n- Plan-and-Solve executor: `$REF_STEP_N` variable binding between steps\n- YAML-based workflow engine for deterministic step sequences\n- Inline workflow detection: \"send email, add to calendar, remind me tomorrow\" → 3 tool calls\n- Delegate-to-subagent tool: spawns sub-agents for parallel or specialized tasks\n\n**i18n**\n- MarianMT offline translation (Turkish↔English) — no API key, runs locally\n- Configurable primary language; English used internally, translated for display\n\n### What's missing or incomplete\n\n**Wake word**: requires a Porcupine access key from Picovoice. Without it the voice pipeline silently disables itself. There's no fallback wake word engine.\n\n**VLM / vision analysis**: screenshot capture works, but VLM analysis requires a self-hosted endpoint (`BANTZ_VLM_ENDPOINT`). No built-in vision model — you bring your own.\n\n**Mood history display**: `bantz --mood-history` prints a stub message. Mood data is recorded in SQLite but there's no display command since the Textual TUI was removed.\n\n**Observer**: background log analysis via a small Ollama model (default `qwen2.5:0.5b`) — implemented but disabled by default (`BANTZ_OBSERVER_ENABLED=false`). Adds latency on low-end hardware.\n\n**RL engine**: the old Q-learning engine was replaced by the Affinity Engine. The `BANTZ_RL_ENABLED` flag exists and gates the intervention/proactive systems, but the underlying RL training loop is no longer active.\n\n**Proactive interventions**: implemented in `agent/interventions.py`, gated behind `BANTZ_RL_ENABLED`. Off by default. Not well-tested in the current build.\n\n**ollama.py stale import**: `llm/ollama.py` still imports from `bantz.interface.tui.panels.header` in a try/except block (leftover from before the Textual TUI was removed). The except swallows the ImportError so it doesn't break anything, but it's dead code.\n\n---\n\n## Installation\n\n**Requirements**: Python 3.11+, Ollama running locally\n\n```bash\ngit clone \u003crepo\u003e\ncd bantzv2\npip install -e \".[dev]\"\n```\n\n**Voice pipeline** (all optional — install only what you need):\n```bash\npip install pvporcupine pyaudio webrtcvad  # wake word + capture\npip install faster-whisper                  # STT\n# Piper TTS: install binary from https://github.com/rhasspy/piper/releases\n#            put 'piper' in PATH, download a voice model .onnx file\n```\n\n**MemPalace memory**:\n```bash\npip install mempalace\n```\n\n**Google integrations**:\n```bash\n# Create an OAuth 2.0 client in Google Cloud Console (Desktop app type)\n# Download credentials.json to ~/.local/share/bantz/\nbantz --setup google gmail\nbantz --setup google classroom\n```\n\n**Telegram**:\n```bash\nbantz --setup telegram\n```\n\n---\n\n## Configuration\n\nCreate a `.env` file in your working directory (or `~/.local/share/bantz/.env`). Minimum working config:\n\n```env\nBANTZ_OLLAMA_MODEL=llama3.1:8b\nBANTZ_OLLAMA_BASE_URL=http://localhost:11434\n\n# Optional: faster routing via a smaller model\nBANTZ_OLLAMA_ROUTING_MODEL=qwen2.5:3b\n\n# Optional: Gemini fallback when Ollama is unreachable\nBANTZ_GEMINI_ENABLED=true\nBANTZ_GEMINI_API_KEY=your_key_here\n\n# Voice (wake word)\nBANTZ_PORCUPINE_ACCESS_KEY=your_picovoice_key\n\n# Primary language (default Turkish)\nBANTZ_LANGUAGE=tr\n\n# Memory\nBANTZ_MEMPALACE_ENABLED=true\n```\n\nFull reference in `src/bantz/config.py` — every field has a comment.\n\n---\n\n## Setup wizards\n\n```bash\nbantz --setup profile          # name, timezone, city — stored in SQLite\nbantz --setup places           # named GPS locations (home, office, etc.)\nbantz --setup schedule         # weekly timetable\nbantz --setup google gmail     # Google OAuth for Gmail\nbantz --setup google classroom # Google OAuth for Classroom\nbantz --setup telegram         # Telegram bot token\nbantz --setup systemd          # install + enable systemd user service\nbantz --setup systemd --check  # show service status, PID, memory, uptime\n```\n\n---\n\n## Running\n\n```bash\n# Interactive TUI (default)\nbantz\n\n# Headless daemon — APScheduler drives all background jobs\nbantz --daemon\n\n# Single query, no TUI\nbantz --once \"what's on my calendar today?\"\n\n# System health check\nbantz --doctor\n\n# Show running config (secrets masked)\nbantz --config\n```\n\n**Scheduled job management**:\n```bash\nbantz --jobs                          # list all APScheduler jobs\nbantz --run-job nightly_maintenance   # trigger any job immediately\nbantz --maintenance                   # run maintenance workflow now\nbantz --reflect                       # run reflection now\nbantz --reflections                   # view last 10 reflections\nbantz --overnight-poll                # run one overnight poll cycle\n```\n\n**Systemd service** (recommended for daemon mode):\n```bash\nbantz --setup systemd\n# writes ~/.config/systemd/user/bantz.service\n# enables linger, enables and starts the service\n\nsystemctl --user status bantz\njournalctl --user -u bantz -f\n```\n\n---\n\n## Project layout\n\n```\nsrc/bantz/\n├── __main__.py          entry point, CLI argument routing\n├── config.py            pydantic-settings, ~70 env vars\n├── cli/\n│   └── setup.py         all setup wizards and --doctor diagnostics\n├── core/\n│   ├── brain.py         central orchestrator\n│   ├── routing_engine.py quick_route + plan-and-solve dispatch\n│   ├── intent.py        CoT LLM routing (cot_route)\n│   ├── finalizer.py     butler persona + hallucination check\n│   ├── memory_injector.py context assembly before LLM call\n│   ├── prompt_builder.py system prompt composition\n│   └── workflow.py      inline multi-tool workflow detection\n├── memory/\n│   ├── bridge.py        MemPalace adapter (replaces 8 old modules)\n│   └── omni_memory.py   parallel hybrid recall orchestrator\n├── agent/\n│   ├── executor.py      plan-and-solve step runner\n│   ├── planner.py       LLM plan generator\n│   ├── job_scheduler.py APScheduler wrapper\n│   ├── affinity_engine.py bonding score + persona tier\n│   ├── ghost_loop.py    wake→capture→STT→dispatch cycle\n│   ├── wake_word.py     Porcupine always-on listener\n│   ├── voice_capture.py WebRTC VAD recording\n│   ├── stt.py           faster-whisper transcription\n│   ├── tts.py           Piper + aplay synthesis\n│   ├── audio_ducker.py  system volume control during speech\n│   ├── ambient.py       environment sound classifier\n│   ├── observer.py      background log analysis\n│   ├── notifier.py      desktop notifications\n│   ├── interventions.py proactive suggestion queue\n│   └── workflows/       nightly maintenance, reflection, overnight poll\n├── data/\n│   ├── layer.py         DataLayer singleton, unified store init\n│   ├── sqlite_store.py  profile, places, schedule, session, KV stores\n│   └── connection_pool.py WAL-mode thread-safe SQLite pool\n├── interface/\n│   └── live_ui.py       Rich Live TUI (4fps, stats + chat)\n├── integrations/\n│   └── telegram_bot.py  Telegram remote access bot\n├── tools/               31 registered tools (shell, gmail, calendar, ...)\n├── llm/\n│   ├── ollama.py        local Ollama client\n│   └── gemini.py        Gemini fallback client\n├── personality/\n│   ├── persona.py       system prompt persona layer\n│   ├── bonding.py       interaction scoring\n│   └── greeting.py      morning briefing generation\n├── auth/                Google OAuth2 PKCE flow\n└── i18n/\n    └── bridge.py        MarianMT translation bridge\n```\n\n---\n\n## Tests\n\n```bash\npytest                   # full suite\npytest tests/core/       # core modules only\npytest --cov=bantz       # coverage report (target: 65%)\n```\n\n48 pre-existing failures in prompt content and routing regex tests — these test specific LLM output strings that drift with model changes. Everything structural (core, data, agent, cli) passes.\n\n---\n\n## Dependencies\n\nCore (always installed):\n- `ollama` — local LLM server (separate binary install, not pip)\n- `httpx` — async HTTP for Ollama and Gemini\n- `pydantic-settings` — config from env\n- `rich` — terminal UI\n- `aioconsole` — async terminal input\n- `apscheduler` + `sqlalchemy` — persistent job scheduling\n- `psutil` — system stats (CPU/RAM/VRAM/DISK)\n- `python-telegram-bot` — Telegram integration\n- `mempalace` — ChromaDB + KG memory stack\n\nOptional (install as needed):\n- `pvporcupine`, `pyaudio` — wake word detection\n- `webrtcvad` — voice activity detection\n- `faster-whisper` — local STT\n- `piper` (binary) — local TTS\n- `transformers`, `torch`, `sentencepiece` — MarianMT translation (`pip install -e \".[translation]\"`)\n- `pymupdf`, `python-docx` — document reading (`pip install -e \".[docs]\"`)\n- `pyautogui`, `pynput` — desktop automation (`pip install -e \".[automation]\"`)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmiclaldogan%2Fbantzv2","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmiclaldogan%2Fbantzv2","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmiclaldogan%2Fbantzv2/lists"}