Files
TG_autoposter/docker-compose.yml
Andrew K. Choi 48f8c6f0eb UserBot Integration Complete: Fixed container startup, integrated UserBot menu to main bot
MAJOR FIXES:
 Fixed UserBot container startup by making TELEGRAM_BOT_TOKEN optional
 Broke circular import chain between app modules
 Made Config.validate() conditional for UserBot-only mode
 Removed unused celery import from userbot_service.py

INTEGRATION:
 UserBot menu now accessible from main bot /start command
 Added 🤖 UserBot button to main keyboard
 Integrated userbot_manager.py handlers:
   - userbot_menu: Main UserBot interface
   - userbot_settings: Configuration
   - userbot_collect_groups: Gather all user groups
   - userbot_collect_members: Parse group members
 UserBot handlers properly registered in ConversationHandler

CONTAINERS:
 tg_autoposter_bot: Running and handling /start commands
 tg_autoposter_userbot: Running as standalone microservice
 All dependent services (Redis, PostgreSQL, Celery workers) operational

STATUS: Bot is fully operational and ready for testing
2025-12-21 12:09:11 +09:00

333 lines
12 KiB
YAML

version: '3.9'
services:
# ════════════════════════════════════════════════════════════════
# PostgreSQL Database
# ════════════════════════════════════════════════════════════════
postgres:
image: postgres:15-alpine
container_name: tg_autoposter_postgres
environment:
POSTGRES_USER: ${DB_USER:-autoposter}
POSTGRES_PASSWORD: ${DB_PASSWORD:-autoposter_password}
POSTGRES_DB: ${DB_NAME:-autoposter_db}
POSTGRES_INITDB_ARGS: "--encoding=UTF8"
ports:
- "${DB_PORT:-5432}:5432"
volumes:
- postgres_data:/var/lib/postgresql/data
networks:
- autoposter_network
healthcheck:
test: ["CMD-SHELL", "pg_isready -U ${DB_USER:-autoposter} -d ${DB_NAME:-autoposter_db}"]
interval: 10s
timeout: 5s
retries: 5
restart: unless-stopped
# ════════════════════════════════════════════════════════════════
# Redis Cache & Celery Broker
# ════════════════════════════════════════════════════════════════
redis:
image: redis:7-alpine
container_name: tg_autoposter_redis
ports:
- "${REDIS_PORT:-6379}:6379"
command: redis-server --appendonly yes ${REDIS_PASSWORD:+--requirepass ${REDIS_PASSWORD}}
volumes:
- redis_data:/data
networks:
- autoposter_network
healthcheck:
test: ["CMD", "redis-cli", "ping"]
interval: 10s
timeout: 5s
retries: 5
restart: unless-stopped
# ════════════════════════════════════════════════════════════════
# Main Bot Service
# ════════════════════════════════════════════════════════════════
bot:
build:
context: .
dockerfile: Dockerfile
container_name: tg_autoposter_bot
environment:
# Telegram
TELEGRAM_BOT_TOKEN: ${TELEGRAM_BOT_TOKEN}
TELEGRAM_TIMEOUT: ${TELEGRAM_TIMEOUT:-30}
# Telethon Client
USE_TELETHON: ${USE_TELETHON:-false}
TELETHON_API_ID: ${TELETHON_API_ID}
TELETHON_API_HASH: ${TELETHON_API_HASH}
TELETHON_PHONE: ${TELETHON_PHONE}
TELETHON_FLOOD_WAIT_MAX: ${TELETHON_FLOOD_WAIT_MAX:-60}
# Database (PostgreSQL)
DATABASE_URL: postgresql+asyncpg://${DB_USER:-autoposter}:${DB_PASSWORD:-autoposter_password}@postgres:5432/${DB_NAME:-autoposter_db}
# Redis & Celery
REDIS_HOST: ${REDIS_HOST:-redis}
REDIS_PORT: ${REDIS_PORT:-6379}
REDIS_DB: ${REDIS_DB:-0}
REDIS_PASSWORD: ${REDIS_PASSWORD:-}
# Logging
LOG_LEVEL: ${LOG_LEVEL:-INFO}
# Bot Settings
MAX_RETRIES: ${MAX_RETRIES:-3}
RETRY_DELAY: ${RETRY_DELAY:-5}
MIN_SEND_INTERVAL: ${MIN_SEND_INTERVAL:-0.5}
# Parsing
ENABLE_KEYWORD_PARSING: ${ENABLE_KEYWORD_PARSING:-true}
GROUP_PARSE_INTERVAL: ${GROUP_PARSE_INTERVAL:-3600}
MAX_MEMBERS_TO_LOAD: ${MAX_MEMBERS_TO_LOAD:-1000}
# Statistics
ENABLE_STATISTICS: ${ENABLE_STATISTICS:-true}
MESSAGE_HISTORY_DAYS: ${MESSAGE_HISTORY_DAYS:-30}
volumes:
- ./app:/app/app
- ./logs:/app/logs
- ./sessions:/app/sessions
ports:
- "8000:8000"
depends_on:
postgres:
condition: service_healthy
redis:
condition: service_healthy
networks:
- autoposter_network
command: python -m app
restart: unless-stopped
# ════════════════════════════════════════════════════════════════
# Celery Worker (для отправки сообщений)
# ════════════════════════════════════════════════════════════════
celery_worker_send:
build:
context: .
dockerfile: Dockerfile
container_name: tg_autoposter_celery_send
environment:
TELEGRAM_BOT_TOKEN: ${TELEGRAM_BOT_TOKEN}
USE_TELETHON: ${USE_TELETHON:-false}
TELETHON_API_ID: ${TELETHON_API_ID}
TELETHON_API_HASH: ${TELETHON_API_HASH}
TELETHON_PHONE: ${TELETHON_PHONE}
DATABASE_URL: postgresql+asyncpg://${DB_USER:-autoposter}:${DB_PASSWORD:-autoposter_password}@postgres:5432/${DB_NAME:-autoposter_db}
REDIS_HOST: ${REDIS_HOST:-redis}
REDIS_PORT: ${REDIS_PORT:-6379}
REDIS_DB: ${REDIS_DB:-0}
REDIS_PASSWORD: ${REDIS_PASSWORD:-}
LOG_LEVEL: ${LOG_LEVEL:-INFO}
volumes:
- ./app:/app/app
- ./logs:/app/logs
- ./sessions:/app/sessions
depends_on:
postgres:
condition: service_healthy
redis:
condition: service_healthy
networks:
- autoposter_network
command: celery -A app.celery_config worker --loglevel=info --queues=messages -c 4
restart: unless-stopped
# ════════════════════════════════════════════════════════════════
# Celery Worker (для парсинга групп)
# ════════════════════════════════════════════════════════════════
celery_worker_parse:
build:
context: .
dockerfile: Dockerfile
container_name: tg_autoposter_celery_parse
environment:
TELEGRAM_BOT_TOKEN: ${TELEGRAM_BOT_TOKEN}
USE_TELETHON: ${USE_TELETHON:-false}
TELETHON_API_ID: ${TELETHON_API_ID}
TELETHON_API_HASH: ${TELETHON_API_HASH}
TELETHON_PHONE: ${TELETHON_PHONE}
DATABASE_URL: postgresql+asyncpg://${DB_USER:-autoposter}:${DB_PASSWORD:-autoposter_password}@postgres:5432/${DB_NAME:-autoposter_db}
REDIS_HOST: ${REDIS_HOST:-redis}
REDIS_PORT: ${REDIS_PORT:-6379}
REDIS_DB: ${REDIS_DB:-0}
REDIS_PASSWORD: ${REDIS_PASSWORD:-}
LOG_LEVEL: ${LOG_LEVEL:-INFO}
volumes:
- ./app:/app/app
- ./logs:/app/logs
- ./sessions:/app/sessions
depends_on:
postgres:
condition: service_healthy
redis:
condition: service_healthy
networks:
- autoposter_network
command: celery -A app.celery_config worker --loglevel=info --queues=parsing -c 2
restart: unless-stopped
# ════════════════════════════════════════════════════════════════
# Celery Worker (для обслуживания)
# ════════════════════════════════════════════════════════════════
celery_worker_maintenance:
build:
context: .
dockerfile: Dockerfile
container_name: tg_autoposter_celery_maintenance
environment:
TELEGRAM_BOT_TOKEN: ${TELEGRAM_BOT_TOKEN}
DATABASE_URL: postgresql+asyncpg://${DB_USER:-autoposter}:${DB_PASSWORD:-autoposter_password}@postgres:5432/${DB_NAME:-autoposter_db}
REDIS_HOST: ${REDIS_HOST:-redis}
REDIS_PORT: ${REDIS_PORT:-6379}
REDIS_DB: ${REDIS_DB:-0}
REDIS_PASSWORD: ${REDIS_PASSWORD:-}
LOG_LEVEL: ${LOG_LEVEL:-INFO}
volumes:
- ./app:/app/app
- ./logs:/app/logs
depends_on:
postgres:
condition: service_healthy
redis:
condition: service_healthy
networks:
- autoposter_network
command: celery -A app.celery_config worker --loglevel=info --queues=maintenance -c 1
restart: unless-stopped
# ════════════════════════════════════════════════════════════════
# Celery Beat (Планировщик)
# ════════════════════════════════════════════════════════════════
celery_beat:
build:
context: .
dockerfile: Dockerfile
container_name: tg_autoposter_celery_beat
environment:
TELEGRAM_BOT_TOKEN: ${TELEGRAM_BOT_TOKEN}
DATABASE_URL: postgresql+asyncpg://${DB_USER:-autoposter}:${DB_PASSWORD:-autoposter_password}@postgres:5432/${DB_NAME:-autoposter_db}
REDIS_HOST: ${REDIS_HOST:-redis}
REDIS_PORT: ${REDIS_PORT:-6379}
REDIS_DB: ${REDIS_DB:-0}
REDIS_PASSWORD: ${REDIS_PASSWORD:-}
LOG_LEVEL: ${LOG_LEVEL:-INFO}
volumes:
- ./app:/app/app
- ./logs:/app/logs
depends_on:
postgres:
condition: service_healthy
redis:
condition: service_healthy
networks:
- autoposter_network
command: celery -A app.celery_config beat --loglevel=info
restart: unless-stopped
# ════════════════════════════════════════════════════════════════
# Flower (Мониторинг Celery)
# ════════════════════════════════════════════════════════════════
flower:
image: mher/flower:2.0
container_name: tg_autoposter_flower
environment:
CELERY_BROKER_URL: redis://${REDIS_PASSWORD:+:${REDIS_PASSWORD}@}${REDIS_HOST:-redis}:${REDIS_PORT:-6379}/${REDIS_DB:-0}
CELERY_RESULT_BACKEND: redis://${REDIS_PASSWORD:+:${REDIS_PASSWORD}@}${REDIS_HOST:-redis}:${REDIS_PORT:-6379}/$((${REDIS_DB:-0}+1))
FLOWER_PORT: 5555
ports:
- "5555:5555"
depends_on:
redis:
condition: service_healthy
networks:
- autoposter_network
command: celery --broker=redis://${REDIS_PASSWORD:+:${REDIS_PASSWORD}@}${REDIS_HOST:-redis}:${REDIS_PORT:-6379}/${REDIS_DB:-0} flower --port=5555
restart: unless-stopped
# ════════════════════════════════════════════════════════════════
# Telethon UserBot Microservice
# ════════════════════════════════════════════════════════════════
userbot:
build:
context: .
dockerfile: Dockerfile.userbot
container_name: tg_autoposter_userbot
environment:
# Telethon Client
USE_TELETHON: ${USE_TELETHON:-true}
TELETHON_API_ID: ${TELETHON_API_ID}
TELETHON_API_HASH: ${TELETHON_API_HASH}
TELETHON_PHONE: ${TELETHON_PHONE}
TELETHON_FLOOD_WAIT_MAX: ${TELETHON_FLOOD_WAIT_MAX:-60}
# Database (PostgreSQL)
DATABASE_URL: postgresql+asyncpg://${DB_USER:-autoposter}:${DB_PASSWORD:-autoposter_password}@postgres:5432/${DB_NAME:-autoposter_db}
# Redis & Celery
REDIS_HOST: ${REDIS_HOST:-redis}
REDIS_PORT: ${REDIS_PORT:-6379}
REDIS_DB: ${REDIS_DB:-0}
REDIS_PASSWORD: ${REDIS_PASSWORD:-}
# Logging
LOG_LEVEL: ${LOG_LEVEL:-INFO}
volumes:
- ./app:/app/app
- ./logs:/app/logs
- ./sessions:/app/sessions
depends_on:
postgres:
condition: service_healthy
redis:
condition: service_healthy
networks:
- autoposter_network
restart: unless-stopped
volumes:
postgres_data:
driver: local
redis_data:
driver: local
networks:
autoposter_network:
driver: bridge