# File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.

from __future__ import annotations

from typing import Optional

import httpx

from ...._types import Body, Omit, Query, Headers, NotGiven, SequenceNotStr, omit, not_given
from ...._utils import path_template, maybe_transform, async_maybe_transform
from ...._compat import cached_property
from ...._resource import SyncAPIResource, AsyncAPIResource
from ...._response import (
    to_raw_response_wrapper,
    to_streamed_response_wrapper,
    async_to_raw_response_wrapper,
    async_to_streamed_response_wrapper,
)
from ...._base_client import make_request_options
from ....types.agent.v1 import agent_list_params, agent_create_params, agent_update_params
from ....types.agent.v1.agent_list_response import AgentListResponse
from ....types.agent.v1.agent_create_response import AgentCreateResponse
from ....types.agent.v1.agent_delete_response import AgentDeleteResponse
from ....types.agent.v1.agent_update_response import AgentUpdateResponse
from ....types.agent.v1.agent_retrieve_response import AgentRetrieveResponse

__all__ = ["AgentsResource", "AsyncAgentsResource"]


class AgentsResource(SyncAPIResource):
    """
    Create, manage, and execute AI agents with tool access, sandbox environments, and async run workflows
    """

    @cached_property
    def with_raw_response(self) -> AgentsResourceWithRawResponse:
        """
        This property can be used as a prefix for any HTTP method call to return
        the raw response object instead of the parsed content.

        For more information, see https://www.github.com/CaseMark/casedev-python#accessing-raw-response-data-eg-headers
        """
        return AgentsResourceWithRawResponse(self)

    @cached_property
    def with_streaming_response(self) -> AgentsResourceWithStreamingResponse:
        """
        An alternative to `.with_raw_response` that doesn't eagerly read the response body.

        For more information, see https://www.github.com/CaseMark/casedev-python#with_streaming_response
        """
        return AgentsResourceWithStreamingResponse(self)

    def create(
        self,
        *,
        instructions: str,
        name: str,
        description: str | Omit = omit,
        disabled_tools: Optional[SequenceNotStr[str]] | Omit = omit,
        enabled_tools: Optional[SequenceNotStr[str]] | Omit = omit,
        model: str | Omit = omit,
        sandbox: Optional[agent_create_params.Sandbox] | Omit = omit,
        vault_groups: Optional[SequenceNotStr[str]] | Omit = omit,
        vault_ids: Optional[SequenceNotStr[str]] | Omit = omit,
        # Use the following arguments if you need to pass additional parameters to the API that aren't available via kwargs.
        # The extra values given here take precedence over values defined on the client or passed to this method.
        extra_headers: Headers | None = None,
        extra_query: Query | None = None,
        extra_body: Body | None = None,
        timeout: float | httpx.Timeout | None | NotGiven = not_given,
    ) -> AgentCreateResponse:
        """Creates a new agent definition with a scoped API key.

        The agent can then be used
        to create and execute runs.

        Args:
          instructions: System instructions that define agent behavior

          name: Display name for the agent

          description: Optional description of the agent

          disabled_tools: Denylist of tools the agent cannot use. Mutually exclusive with enabledTools —
              set one or the other, not both.

          enabled_tools: Allowlist of tools the agent can use. Mutually exclusive with disabledTools —
              set one or the other, not both.

          model: LLM model identifier (e.g. anthropic/claude-sonnet-4.6). Defaults to
              anthropic/claude-sonnet-4.6

          sandbox: Custom sandbox configuration (cpu, memoryMiB)

          vault_groups: Restrict agent to vaults within specific vault group IDs

          vault_ids: Restrict agent to specific vault IDs

          extra_headers: Send extra headers

          extra_query: Add additional query parameters to the request

          extra_body: Add additional JSON properties to the request

          timeout: Override the client-level default timeout for this request, in seconds
        """
        return self._post(
            "/agent/v1/agents",
            body=maybe_transform(
                {
                    "instructions": instructions,
                    "name": name,
                    "description": description,
                    "disabled_tools": disabled_tools,
                    "enabled_tools": enabled_tools,
                    "model": model,
                    "sandbox": sandbox,
                    "vault_groups": vault_groups,
                    "vault_ids": vault_ids,
                },
                agent_create_params.AgentCreateParams,
            ),
            options=make_request_options(
                extra_headers=extra_headers, extra_query=extra_query, extra_body=extra_body, timeout=timeout
            ),
            cast_to=AgentCreateResponse,
        )

    def retrieve(
        self,
        id: str,
        *,
        # Use the following arguments if you need to pass additional parameters to the API that aren't available via kwargs.
        # The extra values given here take precedence over values defined on the client or passed to this method.
        extra_headers: Headers | None = None,
        extra_query: Query | None = None,
        extra_body: Body | None = None,
        timeout: float | httpx.Timeout | None | NotGiven = not_given,
    ) -> AgentRetrieveResponse:
        """
        Retrieves a single agent definition by ID.

        Args:
          extra_headers: Send extra headers

          extra_query: Add additional query parameters to the request

          extra_body: Add additional JSON properties to the request

          timeout: Override the client-level default timeout for this request, in seconds
        """
        if not id:
            raise ValueError(f"Expected a non-empty value for `id` but received {id!r}")
        return self._get(
            path_template("/agent/v1/agents/{id}", id=id),
            options=make_request_options(
                extra_headers=extra_headers, extra_query=extra_query, extra_body=extra_body, timeout=timeout
            ),
            cast_to=AgentRetrieveResponse,
        )

    def update(
        self,
        id: str,
        *,
        description: Optional[str] | Omit = omit,
        disabled_tools: Optional[SequenceNotStr[str]] | Omit = omit,
        enabled_tools: Optional[SequenceNotStr[str]] | Omit = omit,
        instructions: str | Omit = omit,
        model: str | Omit = omit,
        name: str | Omit = omit,
        sandbox: Optional[object] | Omit = omit,
        vault_groups: Optional[SequenceNotStr[str]] | Omit = omit,
        vault_ids: Optional[SequenceNotStr[str]] | Omit = omit,
        # Use the following arguments if you need to pass additional parameters to the API that aren't available via kwargs.
        # The extra values given here take precedence over values defined on the client or passed to this method.
        extra_headers: Headers | None = None,
        extra_query: Query | None = None,
        extra_body: Body | None = None,
        timeout: float | httpx.Timeout | None | NotGiven = not_given,
    ) -> AgentUpdateResponse:
        """Updates an agent definition.

        Only provided fields are changed.

        Args:
          description: Updated agent description. Pass null to clear if supported by the client.

          disabled_tools: Denylist of tools the agent cannot use. Mutually exclusive with enabledTools —
              set one or the other, not both. Pass null to clear.

          enabled_tools: Allowlist of tools the agent can use. Mutually exclusive with disabledTools —
              set one or the other, not both. Pass null to clear.

          instructions: Updated system instructions that guide agent behavior

          model: Model identifier the agent should use for future runs

          name: Updated agent display name

          sandbox: Sandbox configuration override for future agent runs. Pass null to clear.

          vault_groups: Vault group IDs the agent can access. Pass null to clear.

          vault_ids: Vault IDs the agent can access directly. Pass null to clear.

          extra_headers: Send extra headers

          extra_query: Add additional query parameters to the request

          extra_body: Add additional JSON properties to the request

          timeout: Override the client-level default timeout for this request, in seconds
        """
        if not id:
            raise ValueError(f"Expected a non-empty value for `id` but received {id!r}")
        return self._patch(
            path_template("/agent/v1/agents/{id}", id=id),
            body=maybe_transform(
                {
                    "description": description,
                    "disabled_tools": disabled_tools,
                    "enabled_tools": enabled_tools,
                    "instructions": instructions,
                    "model": model,
                    "name": name,
                    "sandbox": sandbox,
                    "vault_groups": vault_groups,
                    "vault_ids": vault_ids,
                },
                agent_update_params.AgentUpdateParams,
            ),
            options=make_request_options(
                extra_headers=extra_headers, extra_query=extra_query, extra_body=extra_body, timeout=timeout
            ),
            cast_to=AgentUpdateResponse,
        )

    def list(
        self,
        *,
        cursor: str | Omit = omit,
        limit: int | Omit = omit,
        # Use the following arguments if you need to pass additional parameters to the API that aren't available via kwargs.
        # The extra values given here take precedence over values defined on the client or passed to this method.
        extra_headers: Headers | None = None,
        extra_query: Query | None = None,
        extra_body: Body | None = None,
        timeout: float | httpx.Timeout | None | NotGiven = not_given,
    ) -> AgentListResponse:
        """
        Lists all active agents for the authenticated organization.

        Args:
          cursor: Pagination cursor (agent ID from previous page). Returns agents created before
              this agent.

          limit: Maximum number of agents to return (default 50, max 250)

          extra_headers: Send extra headers

          extra_query: Add additional query parameters to the request

          extra_body: Add additional JSON properties to the request

          timeout: Override the client-level default timeout for this request, in seconds
        """
        return self._get(
            "/agent/v1/agents",
            options=make_request_options(
                extra_headers=extra_headers,
                extra_query=extra_query,
                extra_body=extra_body,
                timeout=timeout,
                query=maybe_transform(
                    {
                        "cursor": cursor,
                        "limit": limit,
                    },
                    agent_list_params.AgentListParams,
                ),
            ),
            cast_to=AgentListResponse,
        )

    def delete(
        self,
        id: str,
        *,
        # Use the following arguments if you need to pass additional parameters to the API that aren't available via kwargs.
        # The extra values given here take precedence over values defined on the client or passed to this method.
        extra_headers: Headers | None = None,
        extra_query: Query | None = None,
        extra_body: Body | None = None,
        timeout: float | httpx.Timeout | None | NotGiven = not_given,
    ) -> AgentDeleteResponse:
        """
        Soft-deletes an agent and revokes its scoped API key.

        Args:
          extra_headers: Send extra headers

          extra_query: Add additional query parameters to the request

          extra_body: Add additional JSON properties to the request

          timeout: Override the client-level default timeout for this request, in seconds
        """
        if not id:
            raise ValueError(f"Expected a non-empty value for `id` but received {id!r}")
        return self._delete(
            path_template("/agent/v1/agents/{id}", id=id),
            options=make_request_options(
                extra_headers=extra_headers, extra_query=extra_query, extra_body=extra_body, timeout=timeout
            ),
            cast_to=AgentDeleteResponse,
        )


class AsyncAgentsResource(AsyncAPIResource):
    """
    Create, manage, and execute AI agents with tool access, sandbox environments, and async run workflows
    """

    @cached_property
    def with_raw_response(self) -> AsyncAgentsResourceWithRawResponse:
        """
        This property can be used as a prefix for any HTTP method call to return
        the raw response object instead of the parsed content.

        For more information, see https://www.github.com/CaseMark/casedev-python#accessing-raw-response-data-eg-headers
        """
        return AsyncAgentsResourceWithRawResponse(self)

    @cached_property
    def with_streaming_response(self) -> AsyncAgentsResourceWithStreamingResponse:
        """
        An alternative to `.with_raw_response` that doesn't eagerly read the response body.

        For more information, see https://www.github.com/CaseMark/casedev-python#with_streaming_response
        """
        return AsyncAgentsResourceWithStreamingResponse(self)

    async def create(
        self,
        *,
        instructions: str,
        name: str,
        description: str | Omit = omit,
        disabled_tools: Optional[SequenceNotStr[str]] | Omit = omit,
        enabled_tools: Optional[SequenceNotStr[str]] | Omit = omit,
        model: str | Omit = omit,
        sandbox: Optional[agent_create_params.Sandbox] | Omit = omit,
        vault_groups: Optional[SequenceNotStr[str]] | Omit = omit,
        vault_ids: Optional[SequenceNotStr[str]] | Omit = omit,
        # Use the following arguments if you need to pass additional parameters to the API that aren't available via kwargs.
        # The extra values given here take precedence over values defined on the client or passed to this method.
        extra_headers: Headers | None = None,
        extra_query: Query | None = None,
        extra_body: Body | None = None,
        timeout: float | httpx.Timeout | None | NotGiven = not_given,
    ) -> AgentCreateResponse:
        """Creates a new agent definition with a scoped API key.

        The agent can then be used
        to create and execute runs.

        Args:
          instructions: System instructions that define agent behavior

          name: Display name for the agent

          description: Optional description of the agent

          disabled_tools: Denylist of tools the agent cannot use. Mutually exclusive with enabledTools —
              set one or the other, not both.

          enabled_tools: Allowlist of tools the agent can use. Mutually exclusive with disabledTools —
              set one or the other, not both.

          model: LLM model identifier (e.g. anthropic/claude-sonnet-4.6). Defaults to
              anthropic/claude-sonnet-4.6

          sandbox: Custom sandbox configuration (cpu, memoryMiB)

          vault_groups: Restrict agent to vaults within specific vault group IDs

          vault_ids: Restrict agent to specific vault IDs

          extra_headers: Send extra headers

          extra_query: Add additional query parameters to the request

          extra_body: Add additional JSON properties to the request

          timeout: Override the client-level default timeout for this request, in seconds
        """
        return await self._post(
            "/agent/v1/agents",
            body=await async_maybe_transform(
                {
                    "instructions": instructions,
                    "name": name,
                    "description": description,
                    "disabled_tools": disabled_tools,
                    "enabled_tools": enabled_tools,
                    "model": model,
                    "sandbox": sandbox,
                    "vault_groups": vault_groups,
                    "vault_ids": vault_ids,
                },
                agent_create_params.AgentCreateParams,
            ),
            options=make_request_options(
                extra_headers=extra_headers, extra_query=extra_query, extra_body=extra_body, timeout=timeout
            ),
            cast_to=AgentCreateResponse,
        )

    async def retrieve(
        self,
        id: str,
        *,
        # Use the following arguments if you need to pass additional parameters to the API that aren't available via kwargs.
        # The extra values given here take precedence over values defined on the client or passed to this method.
        extra_headers: Headers | None = None,
        extra_query: Query | None = None,
        extra_body: Body | None = None,
        timeout: float | httpx.Timeout | None | NotGiven = not_given,
    ) -> AgentRetrieveResponse:
        """
        Retrieves a single agent definition by ID.

        Args:
          extra_headers: Send extra headers

          extra_query: Add additional query parameters to the request

          extra_body: Add additional JSON properties to the request

          timeout: Override the client-level default timeout for this request, in seconds
        """
        if not id:
            raise ValueError(f"Expected a non-empty value for `id` but received {id!r}")
        return await self._get(
            path_template("/agent/v1/agents/{id}", id=id),
            options=make_request_options(
                extra_headers=extra_headers, extra_query=extra_query, extra_body=extra_body, timeout=timeout
            ),
            cast_to=AgentRetrieveResponse,
        )

    async def update(
        self,
        id: str,
        *,
        description: Optional[str] | Omit = omit,
        disabled_tools: Optional[SequenceNotStr[str]] | Omit = omit,
        enabled_tools: Optional[SequenceNotStr[str]] | Omit = omit,
        instructions: str | Omit = omit,
        model: str | Omit = omit,
        name: str | Omit = omit,
        sandbox: Optional[object] | Omit = omit,
        vault_groups: Optional[SequenceNotStr[str]] | Omit = omit,
        vault_ids: Optional[SequenceNotStr[str]] | Omit = omit,
        # Use the following arguments if you need to pass additional parameters to the API that aren't available via kwargs.
        # The extra values given here take precedence over values defined on the client or passed to this method.
        extra_headers: Headers | None = None,
        extra_query: Query | None = None,
        extra_body: Body | None = None,
        timeout: float | httpx.Timeout | None | NotGiven = not_given,
    ) -> AgentUpdateResponse:
        """Updates an agent definition.

        Only provided fields are changed.

        Args:
          description: Updated agent description. Pass null to clear if supported by the client.

          disabled_tools: Denylist of tools the agent cannot use. Mutually exclusive with enabledTools —
              set one or the other, not both. Pass null to clear.

          enabled_tools: Allowlist of tools the agent can use. Mutually exclusive with disabledTools —
              set one or the other, not both. Pass null to clear.

          instructions: Updated system instructions that guide agent behavior

          model: Model identifier the agent should use for future runs

          name: Updated agent display name

          sandbox: Sandbox configuration override for future agent runs. Pass null to clear.

          vault_groups: Vault group IDs the agent can access. Pass null to clear.

          vault_ids: Vault IDs the agent can access directly. Pass null to clear.

          extra_headers: Send extra headers

          extra_query: Add additional query parameters to the request

          extra_body: Add additional JSON properties to the request

          timeout: Override the client-level default timeout for this request, in seconds
        """
        if not id:
            raise ValueError(f"Expected a non-empty value for `id` but received {id!r}")
        return await self._patch(
            path_template("/agent/v1/agents/{id}", id=id),
            body=await async_maybe_transform(
                {
                    "description": description,
                    "disabled_tools": disabled_tools,
                    "enabled_tools": enabled_tools,
                    "instructions": instructions,
                    "model": model,
                    "name": name,
                    "sandbox": sandbox,
                    "vault_groups": vault_groups,
                    "vault_ids": vault_ids,
                },
                agent_update_params.AgentUpdateParams,
            ),
            options=make_request_options(
                extra_headers=extra_headers, extra_query=extra_query, extra_body=extra_body, timeout=timeout
            ),
            cast_to=AgentUpdateResponse,
        )

    async def list(
        self,
        *,
        cursor: str | Omit = omit,
        limit: int | Omit = omit,
        # Use the following arguments if you need to pass additional parameters to the API that aren't available via kwargs.
        # The extra values given here take precedence over values defined on the client or passed to this method.
        extra_headers: Headers | None = None,
        extra_query: Query | None = None,
        extra_body: Body | None = None,
        timeout: float | httpx.Timeout | None | NotGiven = not_given,
    ) -> AgentListResponse:
        """
        Lists all active agents for the authenticated organization.

        Args:
          cursor: Pagination cursor (agent ID from previous page). Returns agents created before
              this agent.

          limit: Maximum number of agents to return (default 50, max 250)

          extra_headers: Send extra headers

          extra_query: Add additional query parameters to the request

          extra_body: Add additional JSON properties to the request

          timeout: Override the client-level default timeout for this request, in seconds
        """
        return await self._get(
            "/agent/v1/agents",
            options=make_request_options(
                extra_headers=extra_headers,
                extra_query=extra_query,
                extra_body=extra_body,
                timeout=timeout,
                query=await async_maybe_transform(
                    {
                        "cursor": cursor,
                        "limit": limit,
                    },
                    agent_list_params.AgentListParams,
                ),
            ),
            cast_to=AgentListResponse,
        )

    async def delete(
        self,
        id: str,
        *,
        # Use the following arguments if you need to pass additional parameters to the API that aren't available via kwargs.
        # The extra values given here take precedence over values defined on the client or passed to this method.
        extra_headers: Headers | None = None,
        extra_query: Query | None = None,
        extra_body: Body | None = None,
        timeout: float | httpx.Timeout | None | NotGiven = not_given,
    ) -> AgentDeleteResponse:
        """
        Soft-deletes an agent and revokes its scoped API key.

        Args:
          extra_headers: Send extra headers

          extra_query: Add additional query parameters to the request

          extra_body: Add additional JSON properties to the request

          timeout: Override the client-level default timeout for this request, in seconds
        """
        if not id:
            raise ValueError(f"Expected a non-empty value for `id` but received {id!r}")
        return await self._delete(
            path_template("/agent/v1/agents/{id}", id=id),
            options=make_request_options(
                extra_headers=extra_headers, extra_query=extra_query, extra_body=extra_body, timeout=timeout
            ),
            cast_to=AgentDeleteResponse,
        )


class AgentsResourceWithRawResponse:
    def __init__(self, agents: AgentsResource) -> None:
        self._agents = agents

        self.create = to_raw_response_wrapper(
            agents.create,
        )
        self.retrieve = to_raw_response_wrapper(
            agents.retrieve,
        )
        self.update = to_raw_response_wrapper(
            agents.update,
        )
        self.list = to_raw_response_wrapper(
            agents.list,
        )
        self.delete = to_raw_response_wrapper(
            agents.delete,
        )


class AsyncAgentsResourceWithRawResponse:
    def __init__(self, agents: AsyncAgentsResource) -> None:
        self._agents = agents

        self.create = async_to_raw_response_wrapper(
            agents.create,
        )
        self.retrieve = async_to_raw_response_wrapper(
            agents.retrieve,
        )
        self.update = async_to_raw_response_wrapper(
            agents.update,
        )
        self.list = async_to_raw_response_wrapper(
            agents.list,
        )
        self.delete = async_to_raw_response_wrapper(
            agents.delete,
        )


class AgentsResourceWithStreamingResponse:
    def __init__(self, agents: AgentsResource) -> None:
        self._agents = agents

        self.create = to_streamed_response_wrapper(
            agents.create,
        )
        self.retrieve = to_streamed_response_wrapper(
            agents.retrieve,
        )
        self.update = to_streamed_response_wrapper(
            agents.update,
        )
        self.list = to_streamed_response_wrapper(
            agents.list,
        )
        self.delete = to_streamed_response_wrapper(
            agents.delete,
        )


class AsyncAgentsResourceWithStreamingResponse:
    def __init__(self, agents: AsyncAgentsResource) -> None:
        self._agents = agents

        self.create = async_to_streamed_response_wrapper(
            agents.create,
        )
        self.retrieve = async_to_streamed_response_wrapper(
            agents.retrieve,
        )
        self.update = async_to_streamed_response_wrapper(
            agents.update,
        )
        self.list = async_to_streamed_response_wrapper(
            agents.list,
        )
        self.delete = async_to_streamed_response_wrapper(
            agents.delete,
        )
