11import datetime
22from contextlib import AbstractAsyncContextManager
33from pathlib import Path
4- from typing import Any , Literal , cast , overload
4+ from typing import Any , cast
55
66import mcp .types
77from mcp import ClientSession
@@ -107,6 +107,7 @@ async def __aexit__(self, exc_type, exc_val, exc_tb):
107107 self ._session = None
108108
109109 # --- MCP Client Methods ---
110+
110111 async def ping (self ) -> None :
111112 """Send a ping request."""
112113 await self .session .send_ping ()
@@ -128,23 +129,100 @@ async def send_roots_list_changed(self) -> None:
128129 """Send a roots/list_changed notification."""
129130 await self .session .send_roots_list_changed ()
130131
131- async def list_resources (self ) -> list [mcp .types .Resource ]:
132- """Send a resources/list request."""
132+ # --- Resources ---
133+
134+ async def list_resources_mcp (self ) -> mcp .types .ListResourcesResult :
135+ """Send a resources/list request and return the complete MCP protocol result.
136+
137+ Returns:
138+ mcp.types.ListResourcesResult: The complete response object from the protocol,
139+ containing the list of resources and any additional metadata.
140+
141+ Raises:
142+ RuntimeError: If called while the client is not connected.
143+ """
133144 result = await self .session .list_resources ()
145+ return result
146+
147+ async def list_resources (self ) -> list [mcp .types .Resource ]:
148+ """Retrieve a list of resources available on the server.
149+
150+ Returns:
151+ list[mcp.types.Resource]: A list of Resource objects.
152+
153+ Raises:
154+ RuntimeError: If called while the client is not connected.
155+ """
156+ result = await self .list_resources_mcp ()
134157 return result .resources
135158
136- async def list_resource_templates (self ) -> list [mcp .types .ResourceTemplate ]:
137- """Send a resources/listResourceTemplates request."""
159+ async def list_resource_templates_mcp (
160+ self ,
161+ ) -> mcp .types .ListResourceTemplatesResult :
162+ """Send a resources/listResourceTemplates request and return the complete MCP protocol result.
163+
164+ Returns:
165+ mcp.types.ListResourceTemplatesResult: The complete response object from the protocol,
166+ containing the list of resource templates and any additional metadata.
167+
168+ Raises:
169+ RuntimeError: If called while the client is not connected.
170+ """
138171 result = await self .session .list_resource_templates ()
172+ return result
173+
174+ async def list_resource_templates (
175+ self ,
176+ ) -> list [mcp .types .ResourceTemplate ]:
177+ """Retrieve a list of resource templates available on the server.
178+
179+ Returns:
180+ list[mcp.types.ResourceTemplate]: A list of ResourceTemplate objects.
181+
182+ Raises:
183+ RuntimeError: If called while the client is not connected.
184+ """
185+ result = await self .list_resource_templates_mcp ()
139186 return result .resourceTemplates
140187
188+ async def read_resource_mcp (
189+ self , uri : AnyUrl | str
190+ ) -> mcp .types .ReadResourceResult :
191+ """Send a resources/read request and return the complete MCP protocol result.
192+
193+ Args:
194+ uri (AnyUrl | str): The URI of the resource to read. Can be a string or an AnyUrl object.
195+
196+ Returns:
197+ mcp.types.ReadResourceResult: The complete response object from the protocol,
198+ containing the resource contents and any additional metadata.
199+
200+ Raises:
201+ RuntimeError: If called while the client is not connected.
202+ """
203+ if isinstance (uri , str ):
204+ uri = AnyUrl (uri ) # Ensure AnyUrl
205+ result = await self .session .read_resource (uri )
206+ return result
207+
141208 async def read_resource (
142209 self , uri : AnyUrl | str
143210 ) -> list [mcp .types .TextResourceContents | mcp .types .BlobResourceContents ]:
144- """Send a resources/read request."""
211+ """Read the contents of a resource or resolved template.
212+
213+ Args:
214+ uri (AnyUrl | str): The URI of the resource to read. Can be a string or an AnyUrl object.
215+
216+ Returns:
217+ list[mcp.types.TextResourceContents | mcp.types.BlobResourceContents]: A list of content
218+ objects, typically containing either text or binary data.
219+
220+ Raises:
221+ RuntimeError: If called while the client is not connected.
222+ """
145223 if isinstance (uri , str ):
146224 uri = AnyUrl (uri ) # Ensure AnyUrl
147- result = await self .session . read_resource (uri )
225+ result = await self .read_resource_mcp (uri )
148226 return result .contents
149227
150228 # async def subscribe_resource(self, uri: AnyUrl | str) -> None:
@@ -159,66 +237,190 @@ async def read_resource(
159237 # uri = AnyUrl(uri)
160238 # await self.session.unsubscribe_resource(uri)
161239
162- async def list_prompts (self ) -> list [mcp .types .Prompt ]:
163- """Send a prompts/list request."""
240+ # --- Prompts ---
241+
242+ async def list_prompts_mcp (self ) -> mcp .types .ListPromptsResult :
243+ """Send a prompts/list request and return the complete MCP protocol result.
244+
245+ Returns:
246+ mcp.types.ListPromptsResult: The complete response object from the protocol,
247+ containing the list of prompts and any additional metadata.
248+
249+ Raises:
250+ RuntimeError: If called while the client is not connected.
251+ """
164252 result = await self .session .list_prompts ()
253+ return result
254+
255+ async def list_prompts (self ) -> list [mcp .types .Prompt ]:
256+ """Retrieve a list of prompts available on the server.
257+
258+ Returns:
259+ list[mcp.types.Prompt]: A list of Prompt objects.
260+
261+ Raises:
262+ RuntimeError: If called while the client is not connected.
263+ """
264+ result = await self .list_prompts_mcp ()
165265 return result .prompts
166266
267+ # --- Prompt ---
268+ async def get_prompt_mcp (
269+ self , name : str , arguments : dict [str , str ] | None = None
270+ ) -> mcp .types .GetPromptResult :
271+ """Send a prompts/get request and return the complete MCP protocol result.
272+
273+ Args:
274+ name (str): The name of the prompt to retrieve.
275+ arguments (dict[str, str] | None, optional): Arguments to pass to the prompt. Defaults to None.
276+
277+ Returns:
278+ mcp.types.GetPromptResult: The complete response object from the protocol,
279+ containing the prompt messages and any additional metadata.
280+
281+ Raises:
282+ RuntimeError: If called while the client is not connected.
283+ """
284+ result = await self .session .get_prompt (name = name , arguments = arguments )
285+ return result
286+
167287 async def get_prompt (
168288 self , name : str , arguments : dict [str , str ] | None = None
169289 ) -> list [mcp .types .PromptMessage ]:
170- """Send a prompts/get request."""
171- result = await self .session .get_prompt (name , arguments )
290+ """Retrieve a rendered prompt message list from the server.
291+
292+ Args:
293+ name (str): The name of the prompt to retrieve.
294+ arguments (dict[str, str] | None, optional): Arguments to pass to the prompt. Defaults to None.
295+
296+ Returns:
297+ list[mcp.types.PromptMessage]: A list of prompt messages.
298+
299+ Raises:
300+ RuntimeError: If called while the client is not connected.
301+ """
302+ result = await self .get_prompt_mcp (name = name , arguments = arguments )
172303 return result .messages
173304
305+ # --- Completion ---
306+
307+ async def complete_mcp (
308+ self ,
309+ ref : mcp .types .ResourceReference | mcp .types .PromptReference ,
310+ argument : dict [str , str ],
311+ ) -> mcp .types .CompleteResult :
312+ """Send a completion request and return the complete MCP protocol result.
313+
314+ Args:
315+ ref (mcp.types.ResourceReference | mcp.types.PromptReference): The reference to complete.
316+ argument (dict[str, str]): Arguments to pass to the completion request.
317+
318+ Returns:
319+ mcp.types.CompleteResult: The complete response object from the protocol,
320+ containing the completion and any additional metadata.
321+
322+ Raises:
323+ RuntimeError: If called while the client is not connected.
324+ """
325+ result = await self .session .complete (ref = ref , argument = argument )
326+ return result
327+
174328 async def complete (
175329 self ,
176330 ref : mcp .types .ResourceReference | mcp .types .PromptReference ,
177331 argument : dict [str , str ],
178332 ) -> mcp .types .Completion :
179- """Send a completion request."""
180- result = await self .session .complete (ref , argument )
333+ """Send a completion request to the server.
334+
335+ Args:
336+ ref (mcp.types.ResourceReference | mcp.types.PromptReference): The reference to complete.
337+ argument (dict[str, str]): Arguments to pass to the completion request.
338+
339+ Returns:
340+ mcp.types.Completion: The completion object.
341+
342+ Raises:
343+ RuntimeError: If called while the client is not connected.
344+ """
345+ result = await self .complete_mcp (ref = ref , argument = argument )
181346 return result .completion
182347
183- async def list_tools (self ) -> list [mcp .types .Tool ]:
184- """Send a tools/list request."""
348+ # --- Tools ---
349+
350+ async def list_tools_mcp (self ) -> mcp .types .ListToolsResult :
351+ """Send a tools/list request and return the complete MCP protocol result.
352+
353+ Returns:
354+ mcp.types.ListToolsResult: The complete response object from the protocol,
355+ containing the list of tools and any additional metadata.
356+
357+ Raises:
358+ RuntimeError: If called while the client is not connected.
359+ """
185360 result = await self .session .list_tools ()
361+ return result
362+
363+ async def list_tools (self ) -> list [mcp .types .Tool ]:
364+ """Retrieve a list of tools available on the server.
365+
366+ Returns:
367+ list[mcp.types.Tool]: A list of Tool objects.
368+
369+ Raises:
370+ RuntimeError: If called while the client is not connected.
371+ """
372+ result = await self .list_tools_mcp ()
186373 return result .tools
187374
188- @overload
375+ # --- Call Tool ---
376+
377+ async def call_tool_mcp (
378+ self , name : str , arguments : dict [str , Any ]
379+ ) -> mcp .types .CallToolResult :
380+ """Send a tools/call request and return the complete MCP protocol result.
381+
382+ This method returns the raw CallToolResult object, which includes an isError flag
383+ and other metadata. It does not raise an exception if the tool call results in an error.
384+
385+ Args:
386+ name (str): The name of the tool to call.
387+ arguments (dict[str, Any]): Arguments to pass to the tool.
388+
389+ Returns:
390+ mcp.types.CallToolResult: The complete response object from the protocol,
391+ containing the tool result and any additional metadata.
392+
393+ Raises:
394+ RuntimeError: If called while the client is not connected.
395+ """
396+ result = await self .session .call_tool (name = name , arguments = arguments )
397+ return result
398+
189399 async def call_tool (
190400 self ,
191401 name : str ,
192402 arguments : dict [str , Any ] | None = None ,
193- _return_raw_result : Literal [False ] = False ,
194403 ) -> list [
195404 mcp .types .TextContent | mcp .types .ImageContent | mcp .types .EmbeddedResource
196- ]: ...
405+ ]:
406+ """Call a tool on the server.
197407
198- @overload
199- async def call_tool (
200- self ,
201- name : str ,
202- arguments : dict [str , Any ] | None = None ,
203- _return_raw_result : Literal [True ] = True ,
204- ) -> mcp .types .CallToolResult : ...
408+ Unlike call_tool_mcp, this method raises a ClientError if the tool call results in an error.
205409
206- async def call_tool (
207- self ,
208- name : str ,
209- arguments : dict [str , Any ] | None = None ,
210- _return_raw_result : bool = False ,
211- ) -> (
212- list [
213- mcp .types .TextContent | mcp .types .ImageContent | mcp .types .EmbeddedResource
214- ]
215- | mcp .types .CallToolResult
216- ):
217- """Send a tools/call request."""
218- result = await self .session .call_tool (name , arguments )
219- if _return_raw_result :
220- return result
221- elif result .isError :
410+ Args:
411+ name (str): The name of the tool to call.
412+ arguments (dict[str, Any] | None, optional): Arguments to pass to the tool. Defaults to None.
413+
414+ Returns:
415+ list[mcp.types.TextContent | mcp.types.ImageContent | mcp.types.EmbeddedResource]:
416+ The content returned by the tool.
417+
418+ Raises:
419+ ClientError: If the tool call results in an error.
420+ RuntimeError: If called while the client is not connected.
421+ """
422+ result = await self .call_tool_mcp (name = name , arguments = arguments or {})
423+ if result .isError :
222424 msg = cast (mcp .types .TextContent , result .content [0 ]).text
223425 raise ClientError (msg )
224426 return result .content
0 commit comments