PTENES
MODULE 4.3

📁 File Assistant

Build an MCP Server that reads, summarizes, and organizes local files—a personal organization assistant.

6
Topics
40
Minutes
Intermediate
Level
Practical
Type
1

📁 Planning the Tools

The File Assistant is a project that combines the power of MCP with file system operations. Let's create 4 tools that let Claude interact with local files and folders: read content, search text, generate statistics, and organize files automatically. All using the modules pathlib e os from Python’s standard library.

💎 Core Concept

The 4 tools in the File Assistant: ler_arquivo(caminho) — reads the contents of a text file and returns them with metadata (size, modification date); search_in_files(folder, text) — searches for a string in all files in a folder recursively, returning the file, line, and context; estatisticas_pasta(caminho) — counts files by extension, total size, largest/smallest file; organizar_por_tipo(pasta) — moves files into subfolders organized by extension (.pdf to PDFs/, .jpg to Images/, etc.). All use pathlib.Path for safe path manipulation.

💡 Practical Tip

Use pathlib.Path instead of os.path for all path operations. pathlib provides a more intuitive, object-oriented API: Path("pasta").iterdir() to list, path.suffix for the extension, path.stat().st_size for size. In addition, it works correctly on Windows, Linux, and macOS without manual slash adjustments.

2

📖 Tool: Read and Summarize

The tool ler_arquivo is the most basic and most powerful tool in our assistant. It reads the contents of a text file and returns them along with useful metadata such as size and modification date. The most interesting part is that Claude naturally summarizes the content when presenting it to the user—you don’t need to implement summarization logic; the model does that on its own.

💎 Core Concept

The tool ler_arquivo(caminho: str) uses Path(caminho) to open the file, read its contents with path.read_text(encoding="utf-8") and collects metadata via path.stat(): size in bytes/KB, formatted last-modified date. The return value combines the metadata and content in an organized string. Claude receives all of this and can summarize, analyze, or answer questions about the content — without any extra AI code on your part.

❌ Avoid
  • •Read binary files (.exe, .zip, images) as text
  • •Read huge files (>1MB) all at once
  • •Don't check whether the file exists before reading it
  • •Ignore encoding errors (UnicodeDecodeError)
✅ Do
  • •Limit reading to known text extensions
  • •Truncate large files (e.g., first 10KB)
  • •Check path.exists() and path.is_file() first
  • •Use try/except to handle encoding errors
🚨 Alert

Limit the read size! If the user asks to read a 500MB file, the server will try to load everything into memory and send it as a tool response—which could freeze the server or exceed the model’s limits. Set a safe limit (e.g., 10,000 characters) and, if the file is larger, return only the beginning with a warning: "File truncated — showing the first 10KB of 500MB."

3

🔍 Tool: Search Files

The tool search_in_files works like a smart "grep": it takes a folder and text to search for, scans all files recursively, and returns where the text was found with context. Imagine asking Claude: "Search for 'TODO' in all the files in my project" — this tool makes that possible.

💎 Core Concept

The tool buscar_em_arquivos(pasta: str, texto: str) uses Path(pasta).rglob("*") to recursively iterate over all files. For each text file, it reads the lines and checks whether the searched text appears (case-insensitive with .lower()). The return value includes: file name, line number e a line with context (the matching line plus one line before and after). Limit the number of results (e.g., a maximum of 50) so you don't overload the response.

💡 Practical Tip

Use rglob("*") for recursive search (including subfolders) and filter only files with path.is_file(). Ignore binary files by checking the extension or using a try/except when reading. A good list of text extensions: .txt, .py, .js, .md, .html, .css, .json, .yml, .toml, .cfg, .ini, .log. Ignore folders such as .git, __pycache__ e node_modules greatly speeds up the search.

📋 Search Flow
Step 1: Validate the folder

Check that the path exists and is a directory with Path(pasta).is_dir(). Return a clear error if it isn't.

Step 2: Iterate and search

Use rglob("*") to traverse files, read each one with try/except, and check whether the text appears on each line.

Step 3: Format results

Build a string with file:line:content for each match found. Include the total count: "Found X occurrences in Y files."

4

📊 Tool: Folder Statistics

The tool estatisticas_pasta analyzes a folder and returns a complete overview: how many files there are, how they’re distributed by extension, the total size, the largest and smallest files, and when the most recent file was modified. It’s like an "X-ray" of the directory.

💎 Core Concept

The tool estatisticas_pasta(caminho: str) goes through all the files in the folder with Path(caminho).rglob("*"), collecting information with path.stat() for each file. It calculates: total number of files, distribution by extension (using a dictionary/Counter), total size in bytes/KB/MB, largest and smallest file with their names and sizes, and date of the most recent file. The return value is a formatted string that Claude presents as an organized report.

📊 Data and Research

Directory analysis tools are surprisingly useful in everyday work. Studies show that the average user has more than 100,000 files on the computer and takes about 2.5 hours per week looking for and organizing files. A tool that provides quick statistics makes it easy to identify folders that need cleaning, large files that take up space, and unexpected extensions that may indicate problems.

💡 Practical Tip

Use collections.Counter to count extensions elegantly: Counter(p.suffix.lower() for p in pasta.rglob("*") if p.is_file()). To format readable sizes, create a helper function that automatically converts bytes to KB/MB/GB. Sort extensions by count (most common first) so the report shows the most relevant information at the top.

5

📂 Tool: Organize by Type

The most impactful tool in our assistant: organizar_por_tipo analyzes a folder and moves each file into a subfolder matching its extension. .pdf files go into a "PDFs/" folder, .jpg and .png into "Imagens/", .py into "Python/", and so on. But be careful: this tool modifies the file system, so it needs to ask for confirmation before acting.

💎 Core Concept

The tool organizar_por_tipo(pasta: str, confirmar: bool = False) works in two modes. When confirmar=False (default), it only lists the planned changes: "Move relatorio.pdf to PDFs/relatorio.pdf", "Move foto.jpg to Imagens/foto.jpg", etc. When confirmar=True, it makes the changes using shutil.move(). The mapping of extensions to folders uses a dictionary: {".pdf": "PDFs", ".jpg": "Imagens", ".png": "Imagens", ".py": "Python", ...}. Unknown extensions go in "Outros/".

❌ Avoid
  • •Move files without showing the plan first
  • •Overwrite files with duplicate names
  • •Organize system or hidden folders
  • •Move files recursively into subfolders
✅ Do
  • •Always list changes before executing
  • •Rename it if a file with the same name already exists
  • •Ignore hidden files (those starting with ".")
  • •Organize only the root level of the target folder
🚨 Alert — Always Confirm Before Moving!

Never move files automatically without the user's confirmation. The tool pattern should be confirmar=False, returning only the list of planned changes. Claude will present this list to the user and ask whether they want to proceed. Only after the user confirms will Claude call the tool again with confirmar=True. This two-step approach prevents accidental movement of important files.

6

🧪 Testing with Claude

With all the tools implemented, let’s test the File Assistant in real-world scenarios. The goal is to validate that Claude can understand natural-language requests, choose the right tool, and present the results in a useful way. Each scenario tests a different combination of tools and capabilities.

💎 Core Concept

Configure the server in Claude Desktop and create a test folder with various files (text, PDFs, images, Python code). The more varied the test folder, the more scenarios you can validate. Observe how Claude decides which tool to use—sometimes it combines several in sequence, such as first calling estatisticas_pasta to see what's in the folder, then ler_arquivo to inspect a specific file.

📋 Suggested Test Scenarios
Test 1: Explore

"What's in my Downloads folder?" — Claude should call estatisticas_pasta and present an organized summary with counts by type, total size, etc.

Test 2: Search

"Search for 'TODO' in all the files in my project" — Claude should call buscar_em_arquivos and list each occurrence with its file, line, and context.

Test 3: Read

"Read the notas.txt file and summarize it for me" — Claude should call ler_arquivo and then summarize the content naturally in its response.

Test 4: Organize

"Organize the files in the Teste folder by type" — Claude should first show the plan (confirmar=False), ask, and only then execute (confirmar=True).

💡 Practical Tip

Create a dedicated test folder with sample files before testing—never test directly in important folders. Use mkdir pasta_teste && touch pasta_teste/doc.pdf pasta_teste/foto.jpg pasta_teste/notas.txt pasta_teste/script.py to quickly create a test structure. This lets you test all the tools without risking changes to real files, especially the organization tool that moves files.

📝 Module Summary

  • ✓ We planned 4 tools for the File Assistant: read, search, statistics, and organize.
  • ✓ We implemented ler_arquivo with metadata and a size limit — Claude summarizes the content naturally.
  • ✓ We created buscar_em_arquivos with recursive search via rglob, returning the file, line, and context.
  • ✓ We implemented estatisticas_pasta with counts by extension, total size, and identification of extremes.
  • ✓ We built organizar_por_tipo with two-step confirmation—list first, execute next.
  • ✓ We tested the complete assistant with real-world exploration, search, reading, and organization scenarios.

Next Module: 4.4 — REST API Integration