balejosg/mcp-file-management-ra1
If you are the rightful owner of mcp-file-management-ra1 and would like to certify it and/or have it hosted online, please leave a comment on the right or send an email to dayong@mcphub.com.
The Model Context Protocol (MCP) server is an educational tool designed to help students develop applications that manage information stored in files, leveraging the MCP to interact with external tools.
MCP Server - RA1: Gestión de Ficheros DAM
Esqueleto educativo para el Resultado de Aprendizaje 1 del módulo "Acceso a Datos"
CFGS Desarrollo de Aplicaciones Multiplataforma (DAM)
📋 Descripción del Proyecto
Este proyecto es un servidor MCP (Model Context Protocol) educativo diseñado para que los estudiantes implementen el RA1: Desarrolla aplicaciones que gestionan información almacenada en ficheros.
¿Qué es MCP?
MCP es un protocolo que permite a las aplicaciones de IA interactuar con herramientas externas. En este caso, los estudiantes crearán herramientas que permiten a una IA gestionar archivos de usuarios en diferentes formatos.
🎯 Objetivos de Aprendizaje (RA1)
Al completar este proyecto, demostrarás:
- CE1.a: Análisis de clases relacionadas con el tratamiento de ficheros
- CE1.b: Utilización de flujos para el acceso a información en ficheros
- CE1.c: Utilización de clases para gestión de ficheros y directorios
- CE1.d: Escritura y lectura de información en formato XML
- CE1.e: Escritura y lectura de información en formato JSON
- CE1.f: Escritura y lectura de información en otros formatos estándar (CSV)
🏗️ Estructura del Proyecto
src/
├── main/java/com/dam/accesodatos/
│ ├── McpAccesoDatosApplication.java # Aplicación principal
│ ├── model/
│ │ ├── User.java # ✅ Modelo de datos (COMPLETO)
│ │ ├── UserCreateDto.java # ✅ DTO para creación (COMPLETO)
│ │ └── UserQueryDto.java # ✅ DTO para consultas (COMPLETO)
│ └── ra1/
│ ├── FileUserService.java # ✅ Interfaz con herramientas MCP (COMPLETO)
│ └── FileUserServiceImpl.java # ❌ PARA IMPLEMENTAR POR ESTUDIANTES
└── test/
├── java/com/dam/accesodatos/ra1/
│ └── FileUserServiceTest.java # ✅ Tests TDD (COMPLETOS)
└── resources/examples/
├── sample_users.csv # ✅ Ejemplo CSV
├── sample_users.json # ✅ Ejemplo JSON
└── sample_users.xml # ✅ Ejemplo XML
🚀 Cómo Empezar
1. Prerrequisitos
- Java 17+
- IntelliJ IDEA (con Gradle integrado)
2. Clonar e Importar en IntelliJ
git clone https://github.com/balejosg/mcp-file-management-ra1
cd mcp-server-ra1-ficheros
En IntelliJ IDEA:
File→Open→ Seleccionar la carpeta del proyecto- IntelliJ detectará automáticamente
build.gradley configurará el proyecto - Esperar a que Gradle sincronice las dependencias
3. Compilar el Proyecto
Opción A - Desde IntelliJ:
Build→Build Project(Ctrl+F9)
Opción B - Desde terminal:
gradle clean compileJava
4. Ejecutar Tests (Fallarán inicialmente)
Opción A - Desde IntelliJ:
- Botón derecho en
src/test/java→Run 'All Tests' - O usar panel Gradle:
Tasks→verification→test
Opción B - Desde terminal:
gradle test
⚠️ Esperado: Todos los tests fallan porque necesitas implementar los métodos
📝 Tu Tarea: Implementar FileUserServiceImpl
Abre el archivo src/main/java/com/dam/accesodatos/ra1/FileUserServiceImpl.java y completa todos los métodos marcados con TODO.
Métodos a Implementar: 13 ESENCIALES + 5 OPCIONALES
Total: 18 métodos (1 ejemplo implementado = getFileInfo())
- ✅ 12 ESENCIALES restantes - Obligatorios para demostrar dominio del RA1
- ⚠️ 5 OPCIONALES - Para estudiantes avanzados que quieran profundizar
Recomendación: Implementa primero los 13 métodos esenciales. Los opcionales son conceptos avanzados.
CE1.a: Análisis de clases relacionadas con tratamiento de ficheros
| Prioridad | Método | Tecnología | Descripción |
|---|---|---|---|
| ✅ EJEMPLO | getFileInfo() | File.length(), canRead(), SimpleDateFormat | EJEMPLO IMPLEMENTADO - Información detallada de archivos (actividad 1 de la presentación vista en clase) |
| ✅ ESENCIAL | compareIOPerformance() | System.currentTimeMillis(), FileReader vs BufferedReader | Comparación de rendimiento I/O con y sin buffering |
| ⚠️ OPCIONAL | compareNIOvsIO() | Files.readAllLines() vs BufferedReader | [OPCIONAL - Concepto avanzado NIO] Análisis comparativo java.nio vs java.io tradicional |
CE1.b: Utilización de flujos para acceso a información en ficheros
| Prioridad | Método | Tecnología | Descripción |
|---|---|---|---|
| ✅ ESENCIAL | searchTextInFile() | BufferedReader + String.contains() | Búsqueda de texto en archivos (actividad 4 de la presentación vista en clase) |
| ✅ ESENCIAL | randomAccessRead() | RandomAccessFile + seek() | Lectura desde posición específica |
| ✅ ESENCIAL | randomAccessWrite() | RandomAccessFile + seek() | Escritura en posición específica |
| ✅ ESENCIAL | convertFileEncoding() | InputStreamReader/OutputStreamWriter | Conversión entre codificaciones (UTF-8, ISO-8859-1) |
CE1.c: Utilización de clases para gestión de ficheros y directorios
| Prioridad | Método | Tecnología | Descripción |
|---|---|---|---|
| ✅ ESENCIAL | listUserFiles() | Files.list() | Lista archivos de usuario en directorio |
| ⚠️ OPCIONAL | validateDirectoryStructure() | Files API | [OPCIONAL - Muy utilitario] Valida y crea estructura de directorios |
| ⚠️ OPCIONAL | createTempFile() | File.createTempFile() | [OPCIONAL - Poco valor sobre flujos] Creación y gestión de archivos temporales |
| ⚠️ OPCIONAL | formatTextFile() | Character processing | [OPCIONAL - Más String que I/O] Procesamiento de texto avanzado (basado en ejemplo ArreglarFichero de la presentación vista en clase) |
CE1.d: Escritura y lectura de información en formato XML
| Prioridad | Método | Tecnología | Descripción |
|---|---|---|---|
| ✅ ESENCIAL | readUsersFromXML() | DOM Parser | Lee usuarios desde XML usando DOM |
| ✅ ESENCIAL | writeUsersToXML() | DOM + Transformer | Escribe usuarios a XML usando DOM |
| ⚠️ OPCIONAL | readUsersFromXMLSAX() | SAX Parser | [OPCIONAL - Concepto avanzado] Lee usuarios desde XML usando SAX (alternativa eficiente) |
CE1.e: Escritura y lectura de información en formato JSON
| Prioridad | Método | Tecnología | Descripción |
|---|---|---|---|
| ✅ ESENCIAL | readUsersFromJSON() | Jackson ObjectMapper | Lee usuarios desde JSON |
| ✅ ESENCIAL | writeUsersToJSON() | Jackson ObjectMapper | Escribe usuarios a JSON con formato pretty-print |
CE1.f: Escritura y lectura de información en otros formatos estándar
| Prioridad | Método | Tecnología | Descripción |
|---|---|---|---|
| ✅ ESENCIAL | readUsersFromCSV() | BufferedReader, FileReader | Lee usuarios desde CSV con parsing manual |
| ✅ ESENCIAL | writeUsersToCSV() | PrintWriter, FileWriter | Escribe usuarios a CSV con formateo manual |
📋 Orden de Implementación Sugerido
Fase 1: Fundamentos (Métodos ESENCIALES - CE1.f)
readUsersFromCSV()- Aprende parsing manual y BufferedReaderwriteUsersToCSV()- Aprende PrintWriter y formateo
Fase 2: Formatos Estructurados (Métodos ESENCIALES - CE1.e, CE1.d)
3. readUsersFromJSON() - Aprende Jackson ObjectMapper
4. writeUsersToJSON() - Aprende serialización JSON
5. readUsersFromXML() - Aprende DOM parser
6. writeUsersToXML() - Aprende DOM + Transformer
Fase 3: Flujos y Búsqueda (Métodos ESENCIALES - CE1.b, CE1.a, CE1.c)
7. searchTextInFile() - Practica BufferedReader línea por línea
8. compareIOPerformance() - Compara FileReader vs BufferedReader
9. listUserFiles() - Aprende navegación de directorios
Fase 4: Acceso Avanzado (Métodos ESENCIALES - CE1.b)
10. randomAccessRead() - Aprende RandomAccessFile
11. randomAccessWrite() - Practica seek() y escritura posicional
12. convertFileEncoding() - Aprende InputStreamReader/OutputStreamWriter
Fase 5 (OPCIONAL): Conceptos Avanzados
Solo si dominas los 13 métodos esenciales:
- ⚠️
readUsersFromXMLSAX()- SAX parser (alternativa avanzada a DOM) - ⚠️
compareNIOvsIO()- NIO vs IO (conceptos java.nio.file) - ⚠️
validateDirectoryStructure()- Utilidad de infraestructura - ⚠️
createTempFile()- Creación de archivos temporales - ⚠️
formatTextFile()- Procesamiento avanzado de texto
🎯 Ejemplo de Implementación Completada: get_file_info
¡Ya tienes un ejemplo funcional! El método getFileInfo() está completamente implementado como referencia educativa.
Cómo Probar el Ejemplo
Opción A - Desde IntelliJ:
- Ejecutar servidor: Botón derecho en
McpAccesoDatosApplication.java→Run- O usar panel Gradle:
Tasks→application→bootRun
- O usar panel Gradle:
- Probar con cliente MCP (ver sección "Uso del Servidor MCP" más abajo)
Opción B - Desde terminal:
# 1. Ejecutar servidor MCP
gradle bootRun
# 2. En otra terminal, probar con el cliente MCP
chmod +x mcp-client.sh
./mcp-client.sh get_file_info "/ruta/a/tu/archivo.txt"
# 3. O usar curl directamente
curl -X POST http://localhost:8081/test/get_file_info \
-H "Content-Type: application/json" \
-d '{"filePath": "/ruta/a/tu/archivo.txt"}'
Qué Estudiar en el Ejemplo
- Validación de entrada: Comprobar que el archivo existe
- Uso de File:
file.length(),file.canRead(),file.canWrite(),file.canExecute() - Formateo de fechas:
SimpleDateFormatcon patrón"dd/MM/yyyy HH:mm:ss" - Construcción de respuesta: String.format() para salida estructurada
- Manejo de excepciones: try-catch apropiado
Técnicas Java I/O Demostradas
// Análisis de archivo usando java.io.File
File file = new File(filePath);
if (!file.exists()) return "Error: archivo no existe";
// Información de permisos
String permisos = "";
permisos += file.canRead() ? "r" : "-";
permisos += file.canWrite() ? "w" : "-";
permisos += file.canExecute() ? "x" : "-";
// Formateo de fecha usando SimpleDateFormat
SimpleDateFormat formatter = new SimpleDateFormat("dd/MM/yyyy HH:mm:ss");
Date fechaModificacion = new Date(file.lastModified());
String fechaFormateada = formatter.format(fechaModificacion);
💡 Consejo: Estudia esta implementación antes de abordar los otros 17 métodos. Sigue el mismo patrón de validación, procesamiento y construcción de respuesta.
🧪 Metodología TDD (Test-Driven Development)
- 🔴 ROJO: Ejecuta tests → Fallan (estado inicial)
- 🟢 VERDE: Implementa código mínimo → Tests pasan
- 🔵 REFACTOR: Mejora código → Tests siguen pasando
Desde IntelliJ:
- Botón derecho en un test específico →
Run 'testReadUsersFromCSV_ReadsValidFile()'
Desde terminal:
# Ejecutar tests específicos
gradle test --tests FileUserServiceTest.testReadUsersFromCSV_ReadsValidFile
💡 Ejemplos de Implementación
CE1.f: Lectura CSV con BufferedReader
@Override
public List<User> readUsersFromCSV(String filePath) {
List<User> users = new ArrayList<>();
// 1. Validar archivo existe
if (!Files.exists(Paths.get(filePath))) {
throw new RuntimeException("Archivo no encontrado: " + filePath);
}
// 2. Usar try-with-resources
try (BufferedReader reader = new BufferedReader(new FileReader(filePath))) {
String line = reader.readLine(); // Saltear cabeceras
// 3. Leer línea por línea
while ((line = reader.readLine()) != null) {
String[] fields = line.split(",");
// 4. Convertir a User
User user = parseUserFromCSV(fields);
users.add(user);
}
} catch (IOException e) {
throw new RuntimeException("Error leyendo CSV: " + e.getMessage(), e);
}
return users;
}
CE1.d: Escritura XML con DOM
@Override
public boolean writeUsersToXML(List<User> users, String filePath) {
try {
// 1. Crear documento
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
DocumentBuilder builder = factory.newDocumentBuilder();
Document doc = builder.newDocument();
// 2. Crear elemento raíz
Element root = doc.createElement("users");
doc.appendChild(root);
// 3. Agregar usuarios
for (User user : users) {
Element userElement = doc.createElement("user");
Element id = doc.createElement("id");
id.setTextContent(user.getId().toString());
userElement.appendChild(id);
// ... más campos
root.appendChild(userElement);
}
// 4. Escribir a archivo
TransformerFactory transformerFactory = TransformerFactory.newInstance();
Transformer transformer = transformerFactory.newTransformer();
transformer.setOutputProperty(OutputKeys.INDENT, "yes");
DOMSource source = new DOMSource(doc);
StreamResult result = new StreamResult(new File(filePath));
transformer.transform(source, result);
return true;
} catch (Exception e) {
throw new RuntimeException("Error escribiendo XML: " + e.getMessage(), e);
}
}
📚 Clases Java I/O Requeridas
Análisis de Clases (CE1.a)
java.io.File- Operaciones clásicas, información de archivosjava.text.SimpleDateFormat- Formateo de fechasjava.util.Date- Representación de fechas y timestampsjava.lang.System- Medición de tiempo (currentTimeMillis)
Flujos de Datos (CE1.b)
java.io.FileInputStream/FileOutputStream- Flujos de bytesjava.io.FileReader/FileWriter- Flujos de caracteres básicosjava.io.BufferedReader/BufferedWriter- Lectura/escritura con bufferingjava.io.InputStreamReader/OutputStreamWriter- Conversión con codificaciónjava.io.RandomAccessFile- Acceso aleatorio a archivosjava.lang.String- Métodos contains(), indexOf() para búsqueda
Gestión de Archivos y Directorios (CE1.c)
java.nio.file.Files- Operaciones modernas (readAllLines, list, exists)java.nio.file.Paths- Construcción de rutasjava.io.File- Operaciones clásicas (createTempFile, listFiles)java.lang.Character- Análisis de caracteres (isWhitespace, isAlphabetic, toUpperCase)
Procesamiento XML (CE1.d)
javax.xml.parsers.DocumentBuilder- DOM parsingjavax.xml.parsers.DocumentBuilderFactory- Creación de parsers DOMjavax.xml.parsers.SAXParser- SAX parsing por eventosjavax.xml.parsers.SAXParserFactory- Creación de parsers SAXjavax.xml.transform.Transformer- Escritura XML con formatoorg.xml.sax.helpers.DefaultHandler- Handler personalizado para SAX
Procesamiento JSON (CE1.e)
com.fasterxml.jackson.databind.ObjectMapper- Serialización/deserialización JSONcom.fasterxml.jackson.core.type.TypeReference- Tipos genéricos para deserialización
Formatos Estándar (CE1.f)
java.io.PrintWriter- Escritura formateada de textojava.io.BufferedReader- Lectura eficiente línea por líneajava.lang.String- Métodos split(), trim() para parsing CSV
✅ Criterios de Evaluación
Para aprobar este RA1, debes:
- Todos los tests pasan en verde
- Usar únicamente las clases Java I/O especificadas
- Implementar manejo robusto de excepciones con try-with-resources
- Crear directorios padre automáticamente cuando sea necesario
- Documentar decisiones técnicas en comentarios
- Código limpio y bien estructurado
- Explica el código a tu profesor en horario de clase
🔧 Uso del Servidor MCP
Una vez implementadas, puedes probar las 18 herramientas MCP disponibles:
🎯 Herramienta de Ejemplo (Ya Implementada)
# Probar get_file_info (ejemplo completado)
./mcp-client.sh get_file_info "/ruta/a/archivo.txt"
# Ejecutar servidor MCP
# Opción 1 (IntelliJ): Run → McpAccesoDatosApplication
# Opción 2 (Terminal): gradle bootRun
# Herramientas disponibles organizadas por criterios de evaluación:
# CE1.a: Análisis de clases
# - get_file_info ✅ (EJEMPLO IMPLEMENTADO)
# - compare_io_performance
# - compare_nio_vs_io
# CE1.b: Flujos de datos
# - search_text_in_file
# - random_access_read
# - random_access_write
# - convert_file_encoding
# CE1.c: Gestión de archivos/directorios
# - list_user_files
# - validate_directory_structure
# - create_temp_file
# - format_text_file
# CE1.d: Procesamiento XML
# - read_users_xml_dom
# - write_users_xml
# - read_users_xml_sax
# CE1.e: Procesamiento JSON
# - read_users_json
# - write_users_json
# CE1.f: Formatos estándar
# - read_users_csv
# - write_users_csv
🔧 Guía Completa del Sistema MCP
¿Por Qué MCP en este Proyecto?
🎯 Objetivo Principal: Aprender Java I/O, no MCP
El protocolo MCP sirve como "envoltorio" que permite:
- Probar tus implementaciones de forma interactiva
- Validar funcionamiento sin escribir main() manuales
- Experiencia con tecnología moderna usada en aplicaciones de IA
⚠️ Importante: El valor educativo está en las clases Java I/O (File, BufferedReader, SimpleDateFormat, etc.), no en el protocolo MCP.
Flujo de Trabajo Recomendado
- Estudiar el ejemplo:
getFileInfo()ya implementado - Implementar método: Siguiendo patrones del ejemplo
- Ejecutar tests:
- IntelliJ: Botón derecho en test →
Run - Terminal:
gradle test --tests FileUserServiceTest.testTuMetodo
- IntelliJ: Botón derecho en test →
- Probar con MCP: Usar
mcp-client.shpara validación interactiva - Repetir: Para los 17 métodos restantes
Scripts de Ayuda Incluidos
# Cliente MCP simplificado
./mcp-client.sh get_file_info "/ruta/archivo" # Probar herramienta
./mcp-client.sh list # Ver todas las herramientas
./mcp-client.sh health # Estado del servidor
# Servidor MCP (ejecutar en terminal separada)
gradle bootRun # Puerto 8081
# O desde IntelliJ: Run → McpAccesoDatosApplication
Estructura de Respuesta MCP
Cada herramienta MCP devuelve:
{
"tool": "get_file_info",
"input": "/ruta/archivo.txt",
"result": "Tipo: archivo, Tamaño: 1024 bytes, Permisos: rw-, Fecha: 28/09/2025 10:30:15",
"status": "success"
}
📚 Para Estudiantes: Concéntrate en que tu método Java devuelva el result correcto. El resto es infraestructura.
🆘 Ayuda y Recursos
Documentación Oficial
Archivos de Ejemplo
Revisa los archivos en src/test/resources/examples/ para practicar todos los conceptos:
Archivos para formatos básicos (RA1):
sample_users.csv- Datos de usuarios en formato CSVsample_users.json- Datos de usuarios en formato JSONsample_users.xml- Datos de usuarios en formato XML
Archivos para conceptos de la presentación vista en clase:
texto_para_buscar.txt- Para practicar búsqueda de texto (actividad 4)texto_con_espacios.txt- Para procesamiento de texto con espacios irregularesarchivo_iso8859.txt- Para conversión de codificacionesarchivo_grande_performance.txt- Para pruebas de rendimiento I/OREADME_ejemplos.md- Guía detallada de uso de todos los archivos
Debugging
Desde IntelliJ:
- Tests con breakpoints: Click en margen izquierdo → Debug test
- Ver logs: Panel "Run" muestra salida completa
Desde terminal:
# Tests con logs detallados
gradle test --debug
# Test individual
gradle test --tests FileUserServiceTest.testWriteUsersToCSV_CreatesValidFile
📞 Soporte
- Profesor: bruno.ag@educa.madrid.org
- Documentación adicional: Ver
package-info.javaen el paquetera1 - Issues: Crear issue en el repositorio del curso
¡Éxito en tu implementación del RA1! 🚀
Recuerda: Este proyecto no solo te enseña acceso a datos, sino que también te da experiencia con tecnologías modernas como MCP que se usan en aplicaciones de IA profesionales.