A dynamic Choose-Your-Own-Adventure (CYOA) engine that generates interactive stories using AI. The engine accepts free-text scenario descriptions and automatically creates structured rules, working with both local and remote LLMs through a unified provider interface.
- Dynamic Scenario Generation: Input any free-text description to generate a complete scenario with rules, actions, and events
- AI-Powered Narrator: Uses LLMs to create engaging, context-aware story progression
- Multi-Provider Support: Works with OpenAI, Ollama, LMStudio, and other OpenAI-compatible endpoints
- Local LLM Support: Full support for running models locally via LMStudio or Ollama
- Local Embeddings: Run semantic memory search completely locally without OpenAI API
- Smart Optimization: Automatic context reduction, memory consolidation, and caching for faster performance
- Rule Enforcement: Server-side validation ensures stories follow generated rules
- Memory System: Public and private memory for entities with proper visibility controls
- Semantic Memory Search: Find relevant memories by meaning, not just keywords
- Monte Carlo Balancing: Automatic difficulty balancing through simulation
- RESTful API: FastAPI-based backend with comprehensive endpoints
- React Frontend: Modern web interface for story interaction
- Comprehensive Testing: HTTP-based API testing and debugging tools
- QuickStart Guide - NEW! Get started in minutes
- Release & Deployment Guide - NEW! Release process, branching strategy, and deployment
- Performance Guide - Monitor and optimize LLM call performance
- LM Studio Setup Guide - Complete guide for running QuietStories with LM Studio locally
- Local Embeddings Guide - Set up local embeddings for semantic memory search
- Optimization Guide - Performance tips and local LLM configuration
- Logging Guide - Centralized logging and monitoring setup
- Grafana Integration - Observability stack for production monitoring
┌─────────────────┐ ┌─────────────────┐ ┌─────────────────┐
│ Frontend │ │ Backend │ │ LLM APIs │
│ (React/Vite) │◄──►│ (FastAPI) │◄──►│ (OpenAI/ │
│ │ │ │ │ Ollama/ │
│ - Chat UI │ │ - REST API │ │ LMStudio) │
│ - Admin Panel │ │ - Scenario │ │ │
│ - State Mgmt │ │ Engine │ │ - Embeddings │
└─────────────────┘ └─────────────────┘ └─────────────────┘
│ │ │
└───────────────────────┼───────────────────────┘
│
┌─────────────────┐
│ Database │
│ (SQLite) │
│ │
│ - Scenarios │
│ - Sessions │
│ - Memories │
└─────────────────┘
The system consists of:
- Backend (
backend/): FastAPI server with scenario generation, compilation, and orchestration - Frontend (
frontend/): React + TypeScript + Vite web application - Engine (
backend/engine/): Core logic for scenario validation, compilation, and turn processing - Providers (
backend/providers/): LLM provider interfaces (OpenAI, Ollama, Generic) - Database (
backend/db/): SQLite-based data persistence - Schemas (
backend/schemas/): JSON schemas for validation - Utils (
backend/utils/): Utilities for logging, debugging, and Monte Carlo simulation
- Python 3.11+
- Node.js 18+ (for frontend)
- For Local LLMs: Ollama or LM Studio (see setup guides below)
- For Semantic Search: ChromaDB (optional, for memory search)
🚀 Running Completely Local?
- Follow the LM Studio Setup Guide for step-by-step instructions
- See Local Embeddings Guide to enable semantic memory search locally
- No OpenAI API key required!
-
Clone and navigate to the project:
git clone https://github.com/AB-Law/QuietStories.git cd QuietStories -
Set up Python environment:
# Install dependencies pip install -r requirements.txt # Copy environment template cp .env.example .env # Edit .env with your API keys and settings nano .env
-
Configure environment variables:
# For OpenAI (cloud) MODEL_PROVIDER=openai OPENAI_API_KEY=your_api_key_here MODEL_NAME=gpt-4o-mini # For LM Studio (local) - See LMSTUDIO_SETUP.md for complete guide MODEL_PROVIDER=lmstudio LMSTUDIO_API_BASE=http://localhost:1234/v1 MODEL_NAME=llama-3.2-3b-instruct # For Ollama (local) MODEL_PROVIDER=ollama OPENAI_API_BASE=http://localhost:11434/v1 MODEL_NAME=llama3.2:3b # Optional: Local embeddings for semantic memory search EMBEDDING_PROVIDER=ollama # or 'lmstudio' or 'none' EMBEDDING_MODEL_NAME=nomic-embed-text # Logging (optional) LOG_LEVEL=INFO # DEBUG, INFO, WARNING, ERROR LOG_FILE=logs/app.log
-
Start the backend server:
python -m uvicorn backend.main:app --reload
The API will be available at
http://localhost:8000
-
Navigate to frontend directory:
cd frontend -
Install dependencies:
npm install
-
Start development server:
npm run dev
The frontend will be available at
http://localhost:5173
For the easiest way to run QuietStories, use Docker Compose:
# Clone the repository
git clone https://github.com/AB-Law/QuietStories.git
cd QuietStories
# Start all services (API, frontend, and optional logging)
docker-compose up
# Or start just the API and frontend
docker-compose --profile full upThe application will be available at:
- API:
http://localhost:8000 - Frontend:
http://localhost:5173 - API Documentation:
http://localhost:8000/docs
When running QuietStories in Docker with LM Studio or Ollama on your host machine:
For LM Studio:
- Start LM Studio on your host (not in Docker) with the local server running on port 1234
- Run Docker Compose - the configuration is already set up to connect to your host's LM Studio
- No additional configuration needed -
docker-compose.ymlautomatically useshost.docker.internal:1234
For Ollama:
- Start Ollama on your host (not in Docker) - default port is 11434
- Set environment variable: Create a
.envfile with:MODEL_PROVIDER=ollama OPENAI_API_BASE=http://host.docker.internal:11434/v1
- Run Docker Compose with your environment file
See LMSTUDIO_SETUP.md for detailed LM Studio setup instructions.
api: FastAPI backend serverweb: React frontend applicationchroma: ChromaDB for semantic memory (optional)loki,grafana,promtail: Logging and monitoring stack (optional)
For production deployment, use the provided Docker images and deployment script:
# Quick deployment with the deployment script
./scripts/deploy.sh
# Or manually with docker-compose
docker-compose -f docker-compose.prod.yml up -dThe deployment script provides easy options:
# Deploy with latest stable version (from main branch)
./scripts/deploy.sh
# Deploy with dev version (from dev branch)
./scripts/deploy.sh --tag dev
# Deploy with specific version
./scripts/deploy.sh --tag v1.0.0
# Pull latest images and show logs
./scripts/deploy.sh --pull --logsServices will be available at:
- Frontend: http://localhost (port 80)
- API: http://localhost:8000
- API Docs: http://localhost:8000/docs
- ChromaDB: http://localhost:8001
For complete deployment and release documentation, see RELEASE.md.
curl -X POST "http://localhost:8000/scenarios/generate" \
-H "Content-Type: application/json" \
-d '{"description": "A fantasy adventure with dragons and magic"}'curl -X POST "http://localhost:8000/sessions" \
-H "Content-Type: application/json" \
-d '{"scenario_id": "scenario-123", "seed": 42}'curl -X POST "http://localhost:8000/sessions/session-123/turns" \
-H "Content-Type: application/json" \
-d '{"action": "explore", "params": {}}'The project includes comprehensive testing tools:
# Test scenario generation
python random/api_test.py generate "A fantasy adventure"
# Test complete workflow
python random/api_test.py workflow "Complete test scenario"
# List scenarios
python random/api_test.py list-scenarios# Run all tests
pytest
# Run with coverage
pytest --cov=backend --cov-report=html# Start server with debug logging
LOG_LEVEL=DEBUG python -m uvicorn backend.main:app --reload
# Run tests with debug output
python random/api_test.py workflow "test" --log-level DEBUGQuietStories uses a two-branch workflow for stable releases and ongoing development:
mainbranch: Production-ready stable releases. All code is thoroughly tested.devbranch: Integration branch for active development. New features merge here first.- Feature branches: Created from
devwith naming convention:feature/name,bugfix/name, orchore/name
Development Flow:
feature/new-feature → dev → main (tagged as v1.x.x)
Docker images are automatically built for both branches:
ghcr.io/ab-law/quietstories-api:latest(from main)ghcr.io/ab-law/quietstories-api:dev(from dev)
For detailed information on releases, versioning, and deployment, see RELEASE.md.
QuietStories/
├── backend/ # FastAPI backend
│ ├── api/ # API endpoints
│ ├── engine/ # Core engine logic
│ ├── providers/ # LLM providers
│ ├── db/ # Database layer
│ ├── schemas/ # JSON schemas
│ └── utils/ # Utilities
├── frontend/ # React frontend
├── tests/ # Unit tests
├── random/ # Development tools and docs
└── data/ # SQLite database
This project uses automated code quality checks to ensure consistent code standards:
Pre-commit hooks automatically run code quality checks before each commit:
- Black: Code formatting (88 character line length)
- isort: Import sorting (compatible with Black)
- mypy: Static type checking
- Frontend Build: TypeScript compilation and Vite build check
The hooks check both backend/ and frontend/ directories as needed.
Before pushing code, the following build checks are performed:
- Backend: mypy type checking, Black formatting validation, isort import validation
- Frontend: TypeScript compilation and Vite build
If any checks fail, the push is blocked until issues are resolved.
After cloning the repository:
# Install pre-commit hooks
pip install pre-commit
pre-commit install
# The hooks will now run automatically on commit
# Pre-push checks run automatically on pushYou can also run checks manually:
# Backend checks
python -m mypy backend --ignore-missing-imports
python -m black --check backend
python -m isort --check-only backend
# Frontend build
cd frontend && npm run buildAll these checks are automatically run before each commit via pre-commit hooks.
- ScenarioSpec: JSON structure defining scenario rules, actions, and events
- Outcome: Turn result containing narrative and state changes
- POV (Point of View): Current entity perspective for memory visibility
- Negativity Budget: Difficulty balancing mechanism
- Monte Carlo Simulation: Automatic scenario balancing
- New API Endpoint: Add to
backend/api/ - New Engine Feature: Add to
backend/engine/ - New Provider: Implement in
backend/providers/ - New Schema: Add to
backend/schemas/
| Variable | Description | Default |
|---|---|---|
MODEL_PROVIDER |
LLM provider (openai/ollama/generic) | openai |
OPENAI_API_KEY |
OpenAI API key | - |
MODEL_NAME |
Model name | gpt-4 |
LOG_LEVEL |
Logging level | INFO |
LOG_FILE |
Log file path | - |
DATABASE_URL |
Database URL | sqlite:///data/quietstories.db |
- Download LMStudio: https://lmstudio.ai/
- Load a model (e.g., Mistral 7B)
- Start the local server
- Configure:
MODEL_PROVIDER=lmstudio OPENAI_API_BASE=http://localhost:5101/v1 MODEL_NAME=local-model
- Install Ollama: https://ollama.ai/
- Pull a model:
ollama pull llama2 - Set environment:
MODEL_PROVIDER=ollama MODEL_NAME=llama2
For detailed setup and optimization: See OPTIMIZATION_GUIDE.md
- Fork the repository
- Create a feature branch:
git checkout -b feature/your-feature - Make changes and add tests
- Run tests:
pytest - Commit with conventional format:
git commit -m "feat: add new feature" - Push and create PR
feat:- New featuresfix:- Bug fixesdocs:- Documentationstyle:- Code style changesrefactor:- Code refactoringtest:- Testingchore:- Maintenance
- Server won't start: Check Python version (3.11+) and dependencies
- API connection failed: Ensure backend is running on port 8000
- LLM errors: Check API keys and model availability
- Database errors: Ensure
data/directory exists and is writable
# Start with detailed logging
LOG_LEVEL=DEBUG python -m uvicorn backend.main:app --reload
# Use VSCode debugger (F5) for breakpointsCheck logs in:
- Console output (when running server)
logs/app.log(if configured)- Test output with
--log-level DEBUG
This project is licensed under the MIT License - see the LICENSE file for details.
- Built with FastAPI, React, and modern Python tooling
- Inspired by interactive fiction and AI storytelling
- Thanks to the open-source community for amazing tools /Users/akshayb/projects/QuietStories/README.md