from __future__ import annotations

import logging
import sys
from pathlib import Path

from dotenv import load_dotenv
from mcp.server.fastmcp import FastMCP

from cog_mcp.auth import create_cognite_client
from cog_mcp.config import Config
from cog_mcp.resources import register_resources
from cog_mcp.tools import register_tools

INSTRUCTIONS = """\
This server provides access to Cognite Data Fusion (CDF) data models and instances.

## Workflow

1. Start by calling the `list_views` tool to discover available views with their \
exact space, externalId, and version. Never guess these values.

2. When you need to filter, sort, search by property, or aggregate — first call \
`get_view_schema` with the view's space, externalId, and version to get property names, \
types, and relation targets. Don't assume property names exist.

3. Call `get_filter_docs` before constructing filter expressions, and \
`get_query_docs` before using query_instances.

## Property references in filters
- View properties: `[viewSpace, "viewExternalId/version", propertyName]`
- Node built-in properties: `["node", propertyName]` — available: space, externalId, \
version, type, createdTime, lastUpdatedTime, deletedTime
- Edge built-in properties: `["edge", propertyName]` — available: space, externalId, \
version, type, startNode, endNode, createdTime, lastUpdatedTime, deletedTime
"""

# Configure logging to stderr (stdout is reserved for MCP JSON-RPC)
logging.basicConfig(
    level=logging.INFO,
    format="%(asctime)s [%(name)s] %(levelname)s: %(message)s",
    stream=sys.stderr,
)
logger = logging.getLogger("cog_mcp")


def main() -> None:
    # Load .env file if present (does not override existing env vars)
    env_path = Path.cwd() / ".env"
    if env_path.is_file():
        load_dotenv(env_path, override=False)
        logger.info(f"Loaded .env from {env_path}")
    else:
        load_dotenv(override=False)  # search default locations

    logger.info("Starting cog-mcp-experimental server")

    try:
        config = Config.from_env()
    except ValueError as e:
        logger.error(f"Configuration error: {e}")
        sys.exit(1)

    logger.info(
        f"Configured for project={config.project}, cluster={config.cluster}, "
        f"data_models={len(config.data_models)}, instance_spaces={config.instance_spaces}"
    )

    client = create_cognite_client(config)

    mcp = FastMCP("cog-mcp-experimental", instructions=INSTRUCTIONS)

    register_resources(mcp, client, config)
    register_tools(mcp, client, config)

    logger.info("Server ready, running on stdio transport")
    mcp.run(transport="stdio")


if __name__ == "__main__":
    main()
