# 🎵 Miku Discord Bot - Configuration System

## 📚 Overview

The bot now uses a modern, type-safe configuration system that separates secrets from general settings:

- **`.env`** - Secrets only (API keys, tokens) - **NEVER commit to git**
- **`config.yaml`** - All configuration settings - **Safe to commit**
- **`bot/config.py`** - Pydantic models with validation - **Type-safe loading**

---

## 🚀 Quick Setup

### 1. Run the Setup Script

```bash
chmod +x setup.sh
./setup.sh
```

This creates a `.env` file from `.env.example`.

### 2. Edit `.env` and Add Your Values

```bash
nano .env  # or your preferred editor
```

Required variables:
```bash
DISCORD_BOT_TOKEN=your_actual_bot_token_here
```

Optional variables:
```bash
OWNER_USER_ID=209381657369772032  # Your Discord user ID
ERROR_WEBHOOK_URL=https://discord.com/api/webhooks/...  # For error notifications
CHESHIRE_CAT_API_KEY=  # Leave empty if no auth
```

### 3. (Optional) Customize `config.yaml`

Edit `config.yaml` to adjust:
- Model names
- Service URLs
- Feature flags
- Debug modes
- Timeout values

### 4. Start the Bot

```bash
docker compose up -d
```

---

## 📋 Configuration Files

### `.env` (Secrets - DO NOT COMMIT)

Contains sensitive values that should never be shared:

| Variable | Required | Description |
|----------|----------|-------------|
| `DISCORD_BOT_TOKEN` | ✅ Yes | Discord bot token |
| `CHESHIRE_CAT_API_KEY` | No | Cheshire Cat API key (leave empty if no auth) |
| `ERROR_WEBHOOK_URL` | No | Discord webhook for errors |
| `OWNER_USER_ID` | No | Bot owner Discord ID |

### `config.yaml` (Settings - Safe to Commit)

Contains all non-secret configuration:

```yaml
services:
  llama:
    url: http://llama-swap:8080
    amd_url: http://llama-swap-amd:8080

models:
  text: llama3.1
  vision: vision
  evil: darkidol
  japanese: swallow

discord:
  language_mode: english
  api_port: 3939

autonomous:
  debug_mode: false

voice:
  debug_mode: false
```

---

## 🔧 Configuration Options

### Services

| Setting | Default | Description |
|---------|---------|-------------|
| `services.llama.url` | `http://llama-swap:8080` | LLM endpoint (NVIDIA GPU) |
| `services.llama.amd_url` | `http://llama-swap-amd:8080` | LLM endpoint (AMD GPU) |
| `services.cheshire_cat.url` | `http://cheshire-cat:80` | Memory system endpoint |
| `services.cheshire_cat.timeout_seconds` | `120` | Request timeout |
| `services.cheshire_cat.enabled` | `true` | Enable Cheshire Cat |

### Models

| Setting | Default | Description |
|---------|---------|-------------|
| `models.text` | `llama3.1` | Main text model |
| `models.vision` | `vision` | Vision model for images |
| `models.evil` | `darkidol` | Uncensored model (evil mode) |
| `models.japanese` | `swallow` | Japanese language model |

### Discord

| Setting | Default | Description |
|---------|---------|-------------|
| `discord.language_mode` | `english` | Language: `english` or `japanese` |
| `discord.api_port` | `3939` | FastAPI server port |

### Autonomous System

| Setting | Default | Description |
|---------|---------|-------------|
| `autonomous.debug_mode` | `false` | Enable detailed decision logging |

### Voice Chat

| Setting | Default | Description |
|---------|---------|-------------|
| `voice.debug_mode` | `false` | Enable voice chat debugging |

### GPU

| Setting | Default | Description |
|---------|---------|-------------|
| `gpu.prefer_amd` | `false` | Prefer AMD GPU over NVIDIA |
| `gpu.amd_models_enabled` | `true` | Enable AMD GPU models |

---

## 🐛 Debugging

### Enable Debug Mode

Set `autonomous.debug_mode: true` in `config.yaml` to see:
- Autonomous decision logs
- Mood changes
- Action selection process

### Check Configuration

The bot validates configuration on startup. If validation fails, check the logs for specific errors.

### Print Configuration Summary

When `autonomous.debug_mode` is enabled, the bot prints a configuration summary on startup showing all settings (except secrets).

---

## 🔐 Security Best Practices

### ✅ DO:
- Keep `.env` out of version control (in `.gitignore`)
- Use different API keys for development and production
- Rotate API keys periodically
- Limit API key permissions to minimum required

### ❌ DO NOT:
- Commit `.env` to git
- Share `.env` with others
- Hardcode secrets in code
- Use `.env.example` as your actual config

---

## 📦 Migration from `globals.py`

The new configuration system maintains **backward compatibility** with `globals.py`. All existing code continues to work without changes.

To migrate new code to use the config system:

**Old way:**
```python
import globals
url = globals.LLAMA_URL
model = globals.TEXT_MODEL
```

**New way:**
```python
from config import CONFIG
url = CONFIG.services.url
model = CONFIG.models.text
```

**Secrets:**
```python
from config import SECRETS
token = SECRETS.discord_bot_token
```

---

## 🔄 Environment-Specific Configs

For different environments (dev, staging, prod), create multiple config files:

```bash
config.yaml          # Default
config.dev.yaml      # Development
config.prod.yaml     # Production
```

Then override with `CONFIG_FILE` environment variable:

```bash
docker compose run --env CONFIG_FILE=config.prod.yaml miku-bot
```

---

## 🧪 Validation

The configuration system validates:
- **Types**: All values match expected types
- **Ranges**: Numeric values within bounds
- **Patterns**: String values match regex patterns
- **Required**: All required secrets present

If validation fails, the bot will not start and will print specific errors.

---

## 📖 API Reference

### `config.load_config(config_path: str = None) -> AppConfig`

Load configuration from YAML file.

### `config.load_secrets() -> Secrets`

Load secrets from environment variables.

### `config.validate_config() -> tuple[bool, list[str]]`

Validate configuration, returns `(is_valid, list_of_errors)`.

### `config.print_config_summary()`

Print a summary of current configuration (without secrets).

---

## 🆘 Troubleshooting

### "DISCORD_BOT_TOKEN not set"

Edit `.env` and add your Discord bot token.

### "Configuration validation failed"

Check the error messages in the logs and fix the specific issues.

### "Config file not found"

Ensure `config.yaml` exists in the project root.

### Bot won't start after config changes

Check that all required variables in `.env` are set. Run validation:

```python
python -c "from config import validate_config; print(validate_config())"
```

---

## 📝 Notes

- Configuration is loaded at module import time
- Secrets from `.env` override defaults in `config.yaml`
- The bot validates configuration on startup
- All legacy `globals.py` variables are still available
- Pydantic provides automatic type conversion and validation

---

## 🎯 Future Improvements

- [ ] Add config hot-reloading without restart
- [ ] Web UI for configuration management
- [ ] Config versioning and migration system
- [ ] Secret rotation automation
- [ ] Per-server configuration overrides
