"""MCP tool registrations for tool policies."""

from mcp.server.fastmcp import Context


def register_tools(mcp, api_fn):
    @mcp.tool()
    async def create_policy(
        project_id: str,
        name: str,
        profile: str = "coding",
        allow: str = "",
        also_allow: str = "",
        deny: str = "",
        fs_workspace_only: bool = True,
        exec_security: str = "allowlist",
        exec_timeout_seconds: int = 300,
        is_default: bool = False,
        ctx: Context = None,
    ) -> dict | str:
        """Create a tool policy for a project.

        Args:
            project_id: The project this policy belongs to.
            name: Human-readable label for the policy (e.g. 'Default Coding Policy').
            profile: Preset profile — 'minimal', 'coding', or 'full'.
            allow: Comma-separated tool names to explicitly allow (replaces profile list if set).
            also_allow: Comma-separated tool names to add on top of profile (additive).
            deny: Comma-separated tool names to block regardless of other settings.
            fs_workspace_only: Restrict file operations to the workspace directory.
            exec_security: Execution security level — 'deny', 'allowlist', or 'full'.
            exec_timeout_seconds: Maximum execution time for commands in seconds.
            is_default: Set this as the project's default policy.
        """
        return await api_fn(ctx).create_policy(
            project_id, name, profile, allow, also_allow, deny,
            fs_workspace_only, exec_security, exec_timeout_seconds, is_default,
        )

    @mcp.tool()
    async def list_policies(project_id: str, ctx: Context = None) -> list[dict] | str:
        """List tool policies for a project.

        Args:
            project_id: The project to list policies for.
        """
        return await api_fn(ctx).list_policies(project_id)

    @mcp.tool()
    async def get_policy(policy_id: int, ctx: Context = None) -> dict | str:
        """Get a single tool policy by ID.

        Args:
            policy_id: The numeric ID of the policy.
        """
        return await api_fn(ctx).get_policy(policy_id)

    @mcp.tool()
    async def update_policy(
        policy_id: int,
        name: str | None = None,
        profile: str | None = None,
        allow: str | None = None,
        also_allow: str | None = None,
        deny: str | None = None,
        fs_workspace_only: bool | None = None,
        exec_security: str | None = None,
        exec_timeout_seconds: int | None = None,
        is_default: bool | None = None,
        ctx: Context = None,
    ) -> dict | str:
        """Update fields on an existing tool policy.

        Args:
            policy_id: The numeric ID of the policy to update.
            name: New name (optional).
            profile: New profile preset (optional).
            allow: New explicit allow list (optional).
            also_allow: New additive allow list (optional).
            deny: New deny list (optional).
            fs_workspace_only: New fs_workspace_only setting (optional).
            exec_security: New execution security level (optional).
            exec_timeout_seconds: New execution timeout in seconds (optional).
            is_default: Set as project default (optional).
        """
        return await api_fn(ctx).update_policy(
            policy_id, name, profile, allow, also_allow, deny,
            fs_workspace_only, exec_security, exec_timeout_seconds, is_default,
        )

    @mcp.tool()
    async def delete_policy(policy_id: int, ctx: Context = None) -> dict | str:
        """Delete a tool policy by ID.

        Args:
            policy_id: The numeric ID of the policy to delete.
        """
        return await api_fn(ctx).delete_policy(policy_id)

    @mcp.tool()
    async def resolve_policy(policy_id: int, ctx: Context = None) -> dict | str:
        """Return the fully resolved tool list for a policy.

        Expands the profile preset, merges allow/also_allow, and subtracts deny
        to produce the final flat list of permitted tools.

        Args:
            policy_id: The numeric ID of the policy to resolve.
        """
        return await api_fn(ctx).resolve_policy(policy_id)
