Locked learning resources

Join us and get access to thousands of tutorials and a community of expert Pythonistas.

Unlock This Lesson

Locked learning resources

This lesson is for members only. Join us and get access to thousands of tutorials and a community of expert Pythonistas.

Unlock This Lesson

Exposing Resources

Resource mentioned in this lesson: MCP documentation on Resource URIs: https://modelcontextprotocol.io/specification/draft/server/resources

00:00 MCP servers can expose tools. As you’ve seen, these are functions, typically dynamic functions that interact with the environments to retrieve information that is not available statically, which is what a resource is for.

00:14 Resources in MCP servers are static, things like CSV files, images, or videos that the LLM might request access to. In the context of your MCP server, the resource you’re going to expose is the full sales data CSV.

00:32 In order to do that, go ahead and open your main.py file in your preferred editor. To expose a resource in an MCP server, you need to write a function that returns a sales resource. In this case, you’re going to write a function called get_sales() that takes no arguments and returns a string, which is going to be the contents of the file.

00:55 And again, the docstring is very important because it provides information to the LLM about what the function does. In here, you can say, """Retrieve the CSV with all sales""".

01:09 And then what you write, you can do something like open the file, that’s data/sales.csv, you open it for reading, and you just return f.read().

01:23 Now bear in mind that because the example file you’re using is small, returning the full file is a reasonable thing to do. If you’re dealing with large amounts of data, returning the full file might not be a good idea. You may want to provide a tool that paginates the file, for example, instead of returning the full contents of the file.

01:47 Now you only defined the function, you need to tell the MCP server that the function get_sales() is actually a resource. And you do that by using the decorator @mcp.resource().

01:58 So above the function, you’re going to write @mcp.resource, and you’re going to open and close parentheses.

02:07 @mcp comes from the instance that is your FastMCP server. So it’s not because the package is called mcp. In fact, for clarity, you might want to rename the variable mcp to something like mcp_server.

02:25 To make sure that there’s no confusion between the fact that there’s a package called mcp that you’re using and your MCP server instance. So the decorator comes from the MCP server, and then the .resource creates a resource.

02:39 Now, the decorator .resource needs an extra argument that is required, which is a URI, which stands for Uniform Resource Identifier, that will help the LLM know what’s what when it comes to different resources.

02:54 That’s going to be a string. And in here, because this is a file, you’re going to write file://data/sales.csv. Feel free to read the documentation on what the URIs are for and how to format them.

03:11 But for files, you can use this format, file://

03:16 and then a path to the file. If you want to learn more about these URIs, feel free to check the documentation of the Model Context Protocol. And now bear in mind that we’re talking about the documentation of the protocol itself, not of the package mcp, which is just the Python package that allows you to work with a protocol.

03:37 And note that, as a quick tangent, the file URI doesn’t have to be a real path in your system, but it helps you keep your thoughts organized if you do pick the real path to the real file when you’re exposing a file as a resource.

03:53 This defines your resource. Now you want to check that LLMs have access to it through the MCP server. So go ahead and open Cursor. And in case your MCP server was still running, you’ll want to toggle it off and on again. In this case, you can see that instead of showing a green circle, it shows a red circle because there was an error in the server. If you click the error, you can see the output of running your file.

04:22 And in this case, you can see that there was a mistake. When the variable mcp was renamed, you should also rename it at the bottom where it’s being used to run the MCP server.

04:34 So once you save that, you can open Cursor again. You turn it off and on again. Once it’s on, you can see that Cursor says that there’s one tool and one resource enabled.

04:48 You’re going to go to the menu, View, Command Palette. You’re going to type New Chat to open a new chat window. And you’re going to ask something like, how many sales in total have I made?

05:02 And the only way the LLM can get this answer is if it inspects the sales CSV. So hopefully, in a couple of seconds, you should see the thinking trace showing the usage of the MCP server and more specifically, the resource sales.csv.

05:21 After a couple of seconds, you can see in the thinking trace,

05:25 read sales.csv in a faint shade of gray and then the information that there were five total sales, which is information that was extracted from the sales.csv file that the LLM had access to through the MCP server. If you click the explored three files, one search, which might have slightly different numbers for you, you can see the thinking trace talking about the MCP resource.

05:49 So now that you have tools and resources in your MCP server, in the next lesson, you’re going to learn about prompts.

Become a Member to join the conversation.