#!/bin/bash
# Generate conftest.py boilerplate
# Usage: ./generate-conftest.sh [--async] [--db] [--api]

set -e

OUTPUT="tests/conftest.py"

# Check if tests directory exists
if [[ ! -d "tests" ]]; then
    echo "Creating tests directory..."
    mkdir -p tests
fi

# Check if conftest.py already exists
if [[ -f "$OUTPUT" ]]; then
    read -p "conftest.py already exists. Overwrite? [y/N] " -n 1 -r
    echo
    if [[ ! $REPLY =~ ^[Yy]$ ]]; then
        exit 0
    fi
fi

# Parse arguments
ASYNC=""
DB=""
API=""

while [[ $# -gt 0 ]]; do
    case $1 in
        --async)
            ASYNC=1
            shift
            ;;
        --db)
            DB=1
            shift
            ;;
        --api)
            API=1
            shift
            ;;
        *)
            shift
            ;;
    esac
done

# Generate conftest.py
cat > "$OUTPUT" << 'HEADER'
"""
Pytest configuration and fixtures.
Generated by generate-conftest.sh
"""
import pytest
HEADER

# Add async imports if needed
if [[ -n "$ASYNC" ]]; then
    cat >> "$OUTPUT" << 'ASYNC_IMPORTS'
import asyncio
ASYNC_IMPORTS
fi

# Add database imports if needed
if [[ -n "$DB" ]]; then
    cat >> "$OUTPUT" << 'DB_IMPORTS'
from sqlalchemy import create_engine
from sqlalchemy.orm import sessionmaker
ASYNC_IMPORTS
fi

# Add API imports if needed
if [[ -n "$API" ]]; then
    cat >> "$OUTPUT" << 'API_IMPORTS'
from fastapi.testclient import TestClient
# or: from flask.testing import FlaskClient
ASYNC_IMPORTS
fi

# Add base fixtures
cat >> "$OUTPUT" << 'BASE_FIXTURES'


# ============================================================
# Test Configuration
# ============================================================

def pytest_configure(config):
    """Register custom markers."""
    config.addinivalue_line("markers", "slow: marks tests as slow")
    config.addinivalue_line("markers", "integration: marks integration tests")
    config.addinivalue_line("markers", "e2e: marks end-to-end tests")


def pytest_collection_modifyitems(config, items):
    """Skip slow tests unless --slow flag is provided."""
    if not config.getoption("--slow", default=False):
        skip_slow = pytest.mark.skip(reason="use --slow to run")
        for item in items:
            if "slow" in item.keywords:
                item.add_marker(skip_slow)


def pytest_addoption(parser):
    """Add custom CLI options."""
    parser.addoption(
        "--slow",
        action="store_true",
        default=False,
        help="run slow tests"
    )


# ============================================================
# Common Fixtures
# ============================================================

@pytest.fixture
def sample_data():
    """Provide sample test data."""
    return {
        "id": 1,
        "name": "Test",
        "active": True,
    }


@pytest.fixture
def temp_file(tmp_path):
    """Create a temporary file for testing."""
    file_path = tmp_path / "test_file.txt"
    file_path.write_text("test content")
    return file_path
BASE_FIXTURES

# Add async fixtures if requested
if [[ -n "$ASYNC" ]]; then
    cat >> "$OUTPUT" << 'ASYNC_FIXTURES'


# ============================================================
# Async Fixtures
# ============================================================

@pytest.fixture(scope="session")
def event_loop():
    """Create event loop for async tests."""
    loop = asyncio.new_event_loop()
    yield loop
    loop.close()


@pytest.fixture
async def async_client():
    """Async HTTP client fixture."""
    import aiohttp
    async with aiohttp.ClientSession() as session:
        yield session
ASYNC_FIXTURES
fi

# Add database fixtures if requested
if [[ -n "$DB" ]]; then
    cat >> "$OUTPUT" << 'DB_FIXTURES'


# ============================================================
# Database Fixtures
# ============================================================

@pytest.fixture(scope="session")
def db_engine():
    """Create test database engine."""
    engine = create_engine("sqlite:///:memory:")
    # Create tables here
    yield engine
    engine.dispose()


@pytest.fixture
def db_session(db_engine):
    """Create database session with transaction rollback."""
    Session = sessionmaker(bind=db_engine)
    session = Session()
    yield session
    session.rollback()
    session.close()
DB_FIXTURES
fi

# Add API fixtures if requested
if [[ -n "$API" ]]; then
    cat >> "$OUTPUT" << 'API_FIXTURES'


# ============================================================
# API Fixtures
# ============================================================

@pytest.fixture
def app():
    """Create test application."""
    from myapp import create_app
    app = create_app(testing=True)
    return app


@pytest.fixture
def client(app):
    """Create test client."""
    return TestClient(app)


@pytest.fixture
def authenticated_client(client):
    """Create authenticated test client."""
    # Add authentication logic here
    client.headers["Authorization"] = "Bearer test-token"
    return client
API_FIXTURES
fi

echo "Generated $OUTPUT"
echo ""
echo "Options used:"
[[ -n "$ASYNC" ]] && echo "  --async: Async fixtures included"
[[ -n "$DB" ]] && echo "  --db: Database fixtures included"
[[ -n "$API" ]] && echo "  --api: API fixtures included"
