17 Ejercicios de la asignatura
17.1 Introducción a Redes
Investigación del Modelo TCP/IP
Investiga y compara el modelo de capas TCP/IP con tu propia experiencia navegando por Internet.
Tareas:
- Traza la ruta de una petición web:
- Ejecuta el comando
traceroute www.google.com(Linux/Mac) otracert www.google.com(Windows) - Documenta cuántos saltos (hops) hay hasta llegar al destino
- Identifica si alguno de los routers intermedios pertenece a tu ISP
- Ejecuta el comando
- Análisis por capas: Para acceder a una página web (ej: https://www.google.com), describe qué ocurre en cada capa del modelo TCP/IP:
- Capa de Aplicación: ¿Qué protocolo se utiliza?
- Capa de Transporte: ¿TCP o UDP? ¿Por qué?
- Capa de Red: ¿Qué información contienen los paquetes IP?
- Capa de Acceso a la Red: ¿Qué tecnología física usas (WiFi, Ethernet, 4G)?
- Encapsulación:
- Dibuja un diagrama mostrando cómo se encapsulan los datos en cada capa
- Indica qué información añade cada capa (cabeceras)
- Reflexión:
- ¿Por qué crees que el modelo está organizado en capas?
- ¿Qué ventajas tiene esta separación?
- Da un ejemplo de cómo puedes cambiar una capa sin afectar a las demás
17.2 Capa de Acceso
Análisis de Direcciones MAC y ARP
Investiga las direcciones MAC en tu red local y el protocolo ARP.
Tareas:
- Descubre tu dirección MAC:
- En Linux/Mac:
ip link showoifconfig - En Windows:
ipconfig /all - Anota la dirección MAC de tu interfaz de red principal
- En Linux/Mac:
- Analiza la tabla ARP:
- En Linux/Mac:
arp -aoip neigh show - En Windows:
arp -a - Documenta:
- ¿Cuántas entradas tiene tu tabla ARP?
- ¿Reconoces alguna de las IPs? (router, otros dispositivos)
- ¿Hay entradas incompletas o que fallan?
- En Linux/Mac:
- Experimento con ARP:
- Haz ping a tu router/gateway:
ping 192.168.1.1 - Vuelve a consultar la tabla ARP
- ¿Qué ha cambiado?
- Haz ping a tu router/gateway:
- Investigación:
- ¿Qué pasaría si dos dispositivos en la misma red tuvieran la misma dirección MAC?
- ¿Por qué las direcciones MAC no se usan para enrutamiento en Internet?
- ¿Cuál es la diferencia entre una dirección MAC y una dirección IP en términos de alcance?
- Analiza la estructura de la dirección MAC:
- Tu MAC tiene formato:
XX:XX:XX:YY:YY:YY - Los primeros 3 bytes (XX:XX:XX) son el OUI (Organizationally Unique Identifier)
- Busca el fabricante de tu tarjeta de red en: https://maclookup.app/
- Tu MAC tiene formato:
17.3 Capa de Red
Análisis de Direccionamiento IP y Subredes
Dada la siguiente salida del comando ip addr en un sistema Linux, analiza la configuración de red y responde las preguntas:
$ ip addr show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
inet6 ::1/128 scope host
valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc fq_codel state UP
link/ether 52:54:00:12:34:56 brd ff:ff:ff:ff:ff:ff
inet 192.168.1.100/24 brd 192.168.1.255 scope global eth0
valid_lft forever preferred_lft forever
inet6 fe80::5054:ff:fe12:3456/64 scope link
valid_lft forever preferred_lft forever
3: wlan0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq state UP
link/ether a4:5e:60:ab:cd:ef brd ff:ff:ff:ff:ff:ff
inet 10.0.5.42/22 brd 10.0.7.255 scope global wlan0
valid_lft forever preferred_lft foreverPreguntas:
- Direcciones de red: Para cada interfaz con IPv4, calcula:
- La dirección de red
- La dirección de broadcast
- El rango de IPs válidas para hosts
- El número total de hosts disponibles
- Clasificación:
- ¿Qué interfaces tienen direcciones IP privadas? ¿Por qué?
- ¿La dirección de loopback es pública o privada? ¿Para qué se utiliza?
- Máscara de subred:
- Convierte las máscaras CIDR (/8, /24, /22) a formato decimal (ej: 255.255.255.0)
- ¿Cuál es la diferencia entre /24 y /22 en términos de número de hosts?
- Escenario práctico:
- Si quieres enviar un paquete desde esta máquina (192.168.1.100) a un servidor web en Internet (8.8.8.8), ¿qué interfaz se utilizaría?
- ¿Necesitarías NAT? ¿Por qué?
- MTU:
- ¿Qué significa MTU 1500?
- Si envías un datagrama IP de 2000 bytes por eth0, ¿qué ocurrirá?
17.4 Capa de Transporte
Análisis de Conexiones TCP y UDP
Investiga las conexiones activas en tu sistema y analiza el comportamiento de TCP y UDP.
Tareas:
Visualiza conexiones activas:
- En Linux/Mac:
netstat -tunaposs -tunap - En Windows:
netstat -ano - Identifica:
- ¿Cuántas conexiones TCP tienes activas?
- ¿Hay conexiones UDP? ¿A qué puertos?
- ¿Reconoces algún servicio por su puerto? (80=HTTP, 443=HTTPS, 53=DNS, etc.)
- En Linux/Mac:
Analiza estados TCP:
- Busca conexiones en estado ESTABLISHED, LISTEN, TIME_WAIT
- ¿Qué significa cada estado?
- ¿Por qué hay puertos en estado LISTEN?
Compara TCP vs UDP: Completa la tabla:
Característica TCP UDP Orientado a conexión ? ? Garantiza entrega ? ? Garantiza orden ? ? Control de flujo ? ? Overhead ? ? Velocidad ? ? Ejemplo de uso ? ? Investiga el handshake de TCP:
- Dibuja el proceso de establecimiento de conexión (3-way handshake)
- ¿Qué flags se utilizan? (SYN, ACK)
- ¿Qué ocurre si se pierde uno de los paquetes?
Caso práctico: Para un videojuego multijugador, ¿usarías TCP o UDP para los siguientes casos?
- Chat de texto entre jugadores
- Posición de los jugadores en tiempo real
- Transferencia de archivos (mapas, texturas)
- Sistema de login/autenticación
Justifica cada respuesta.
17.5 Capa de Aplicación
Análisis de Petición HTTP
Investiga cómo funciona el protocolo HTTP usando herramientas de línea de comandos.
Tareas:
Realiza una petición HTTP simple:
curl -v http://example.com- Analiza la salida
- Identifica las cabeceras de petición (Request headers)
- Identifica las cabeceras de respuesta (Response headers)
- ¿Qué código de estado se recibe?
Compara HTTP vs HTTPS:
curl -v http://google.com curl -v https://google.com- ¿Qué diferencias observas?
- ¿Hay una redirección en la versión HTTP?
- ¿Qué información adicional aparece en HTTPS?
Investiga los métodos HTTP: Para cada método, describe:
- GET
- POST
- PUT
- DELETE
- ¿Cuándo usarías cada uno en un videojuego?
Analiza códigos de estado HTTP: Agrupa estos códigos por categoría (1xx, 2xx, 3xx, 4xx, 5xx):
- 200, 201, 301, 302, 400, 401, 403, 404, 500, 502, 503
- ¿Qué significa cada categoría?
- Da un ejemplo de cuándo podrías recibir cada código en un juego
Investiga DNS:
nslookup google.com- ¿Qué IP(s) se resuelven?
- ¿Por qué hay múltiples IPs?
- ¿Qué pasaría si el DNS no funcionara?
17.6 JavaScript
Sistema de Inventario de Videojuego
Crea un sistema de inventario para un videojuego utilizando JavaScript moderno (ES2015+). El sistema debe:
- Crear una clase
Inventarioque pueda almacenar items con las siguientes propiedades:nombre(string)cantidad(number)tipo(string): “arma”, “consumible”, o “quest”
- La clase
Inventariodebe tener los siguientes métodos:agregarItem(nombre, cantidad, tipo): Añade un item al inventario. Si el item ya existe, incrementa su cantidad.usarItem(nombre, cantidad): Reduce la cantidad del item especificado. Si llega a 0, elimina el item.obtenerItemsPorTipo(tipo): Retorna un array con todos los items de un tipo específico.get totalItems(): Getter que retorna el número total de items diferentes en el inventario.
- Implementa validaciones:
- La cantidad nunca puede ser negativa
- El tipo debe ser uno de los válidos (“arma”, “consumible”, “quest”)
- No se puede usar más cantidad de la disponible
- Guarda el inventario en
localStoragecada vez que se modifique y permite cargarlo cuando se crea una nueva instancia.
Requisitos técnicos:
- Utiliza la sintaxis de clases ES2015+
- Usa getters/setters cuando sea apropiado
- Emplea métodos de arrays modernos (map, filter, etc.)
- Implementa manejo de errores con try-catch
- Usa template literals para mensajes
Ejemplo de uso:
const inventario = new Inventario();
inventario.agregarItem("Espada de Fuego", 1, "arma");
inventario.agregarItem("Poción de Salud", 5, "consumible");
inventario.agregarItem("Llave Antigua", 1, "quest");
console.log(`Total de items: ${inventario.totalItems}`); // 3
inventario.usarItem("Poción de Salud", 2);
const consumibles = inventario.obtenerItemsPorTipo("consumible");
console.log(consumibles); // [{ nombre: "Poción de Salud", cantidad: 3, tipo: "consumible" }]17.7 Phaser
Sistema de Puntuación Persistente
Crea un sistema de puntuación para un juego Phaser que:
- Muestre la puntuación actual en pantalla durante el juego
- Guarde la puntuación más alta (high score) en
localStorage - Muestre el high score en la pantalla principal
- Permita resetear el high score
Requisitos:
- Crea una escena de Phaser con:
- Un texto que muestre “Score: X”
- Un texto que muestre “High Score: Y”
- Un botón o tecla para incrementar la puntuación (simular evento del juego)
- Un botón para resetear el high score
- Implementa la lógica para:
- Incrementar la puntuación cuando ocurra un evento (ej: presionar SPACE)
- Comparar la puntuación actual con el high score
- Actualizar el high score si se supera
- Persistir el high score en
localStorage - Cargar el high score guardado al iniciar
Pista: Utiliza localStorage.setItem() y localStorage.getItem() para la persistencia.
Estructura sugerida:
class GameScene extends Phaser.Scene {
constructor() {
super('GameScene');
this.score = 0;
this.highScore = 0;
}
create() {
// Cargar high score
// Crear textos
// Configurar controles
}
update() {
// Actualizar puntuación
}
}17.8 REST - Introducción
Diseño de API REST para Videojuego
Diseña una API RESTful para un sistema de gestión de jugadores y partidas de un videojuego.
Requisitos:
- Define los recursos principales:
- Jugadores (players)
- Partidas (games)
- Puntuaciones (scores)
- Diseña los endpoints siguiendo principios REST: Para cada operación, especifica:
- Método HTTP (GET, POST, PUT, DELETE)
- Ruta del endpoint
- Código de estado esperado
- Ejemplo de request/response
- Listar todos los jugadores
- Obtener un jugador específico
- Crear un nuevo jugador
- Actualizar información de un jugador
- Eliminar un jugador
- Obtener todas las partidas de un jugador
- Crear una nueva partida
- Obtener el top 10 de puntuaciones
- Aplica convenciones RESTful:
- Usa nombres en plural para recursos
- Usa IDs en la URL para recursos específicos
- Usa query parameters para filtros y paginación
- Diseña URLs jerárquicas para relaciones
- Diseña las estructuras de datos: Define el formato JSON para:
- Un jugador (Player)
- Una partida (Game)
- Una puntuación (Score)
Ejemplo de formato:
GET /api/players/123
Respuesta: 200 OK
{
"id": 123,
"username": "player1",
...
}
17.9 REST - Cliente
Cliente REST con Fetch API
Implementa un cliente JavaScript que consuma la API REST de un videojuego usando Fetch API.
Requisitos:
Crea funciones para consumir la API: Implementa las siguientes funciones usando
fetch():async function getPlayers() { ... } async function getPlayer(id) { ... } async function createPlayer(playerData) { ... } async function updatePlayer(id, updates) { ... } async function deletePlayer(id) { ... } async function getTopScores(limit = 10) { ... }Manejo de errores:
- Verifica el código de estado de la respuesta
- Lanza excepciones personalizadas para errores HTTP
- Maneja errores de red (ej: servidor no disponible)
Implementa una clase
GameAPI: Encapsula todas las funciones en una clase con:- Base URL configurable
- Métodos para cada operación
- Manejo centralizado de errores
- Headers comunes (Content-Type, Authorization si aplica)
Crea una interfaz de usuario simple:
- Botón para obtener el top 10 de puntuaciones
- Mostrar los resultados en una lista HTML
- Indicador de carga durante la petición
- Mensaje de error si falla
Estructura sugerida:
class GameAPI {
constructor(baseURL) {
this.baseURL = baseURL;
}
async request(endpoint, options = {}) {
// Método helper para hacer peticiones
}
async getPlayers() { ... }
async createPlayer(data) { ... }
// ... más métodos
}Uso esperado:
const api = new GameAPI('https://api.mygame.com');
// Obtener jugador
const player = await api.getPlayer(123);
console.log(player.username);
// Crear nuevo jugador
const newPlayer = await api.createPlayer({
username: 'newbie',
email: 'newbie@example.com'
});17.10 REST - Servidor
Implementar un Servidor REST con Express
Crea un servidor REST básico para gestionar jugadores de un videojuego usando Node.js y Express.
Requisitos:
Configura un proyecto Express:
npm init -y npm install expressImplementa los siguientes endpoints:
GET /api/players- Listar todos los jugadoresGET /api/players/:id- Obtener un jugador por IDPOST /api/players- Crear un nuevo jugadorPUT /api/players/:id- Actualizar un jugadorDELETE /api/players/:id- Eliminar un jugador
Almacenamiento en memoria:
- Usa un array para almacenar los jugadores temporalmente
- Cada jugador debe tener:
id,username,level,score
Validaciones:
- Verificar que
usernameno esté vacío - Verificar que
levelyscoresean números - Retornar error 400 si los datos son inválidos
- Retornar error 404 si el jugador no existe
- Verificar que
Middleware:
- Usa
express.json()para parsear JSON - Añade un middleware de logging que imprima cada petición
- Usa
Estructura sugerida:
const express = require('express');
const app = express();
// Datos en memoria
let players = [
{ id: 1, username: "player1", level: 5, score: 1000 },
{ id: 2, username: "player2", level: 3, score: 500 }
];
let nextId = 3;
// Middleware
app.use(express.json());
// TODO: Implementar endpoints
app.listen(3000, () => {
console.log('Server running on http://localhost:3000');
});Bonus:
- Añade un endpoint
GET /api/players?level=Xpara filtrar por nivel - Implementa paginación con
limityoffset
17.11 WebSockets - Introducción
Comparación REST vs WebSockets
Analiza las diferencias entre REST y WebSockets y determina cuándo usar cada uno.
Tareas:
Completa la tabla comparativa:
Aspecto REST (HTTP) WebSockets Protocolo base ? ? Conexión ? ? Comunicación ? (cliente→servidor) ? Overhead ? ? Tiempo real ? ? Escalabilidad ? ? Complejidad ? ? Casos de uso - ¿REST o WebSocket? Para cada escenario de videojuego, indica si usarías REST, WebSocket o ambos, y justifica:
- Chat entre jugadores en tiempo real
- Cargar lista de mapas disponibles
- Sincronizar posición de jugadores en un shooter multijugador
- Subir una puntuación al leaderboard
- Notificaciones de amigos que se conectan
- Descargar un mapa de 50MB
- Partida de ajedrez online por turnos
- Sistema de login/autenticación
Investigación:
- ¿Qué es el “handshake” de WebSocket?
- ¿Por qué WebSocket usa HTTP inicialmente?
- ¿Pueden atravesar WebSockets un firewall/proxy más fácilmente que un socket TCP puro?
Diseño arquitectónico: Para un juego multijugador tipo battle royale:
- ¿Qué información enviarías por REST?
- ¿Qué información enviarías por WebSocket?
- Dibuja un diagrama simple de la arquitectura
17.12 WebSockets - Cliente
Cliente WebSocket para Chat de Juego
Implementa un cliente WebSocket simple para un sistema de chat en tiempo real de un videojuego.
Requisitos:
Crea una clase
GameChat:- Constructor que reciba la URL del servidor WebSocket
- Método
connect()para establecer conexión - Método
sendMessage(message)para enviar mensajes - Método
disconnect()para cerrar la conexión - Callbacks para eventos:
onMessage,onConnect,onDisconnect,onError
Manejo de estados de conexión:
- Mostrar indicador cuando se está conectando
- Mostrar indicador cuando está conectado
- Mostrar error si falla la conexión
- Intentar reconectar automáticamente si se pierde la conexión
Interfaz de usuario HTML:
- Input para el nombre de usuario
- Botón para conectar
- Área de mensajes (mostrar historial)
- Input para escribir mensaje
- Botón para enviar mensaje
- Indicador de estado de conexión
Formato de mensajes JSON:
// Cliente → Servidor (enviar mensaje) { type: "message", username: "player1", text: "Hola a todos" } // Servidor → Cliente (mensaje broadcast) { type: "message", username: "player2", text: "Hola player1!", timestamp: "2025-11-06T10:30:00Z" } // Servidor → Cliente (usuario conectado) { type: "user_joined", username: "player3" }
Estructura sugerida:
class GameChat {
constructor(serverURL) {
this.serverURL = serverURL;
this.ws = null;
this.username = null;
// Callbacks
this.onMessage = null;
this.onConnect = null;
this.onDisconnect = null;
this.onError = null;
}
connect(username) {
// TODO: Establecer conexión WebSocket
}
sendMessage(text) {
// TODO: Enviar mensaje al servidor
}
disconnect() {
// TODO: Cerrar conexión
}
}Bonus:
- Mostrar quién está escribiendo (“player2 is typing…”)
- Soporte para comandos especiales (“/help”, “/users”)
- Emoticones o formato básico de texto
17.13 WebSockets - Servidor
Servidor WebSocket para Chat de Juego
Implementa un servidor WebSocket simple usando Node.js y la librería ws.
Requisitos:
Instala las dependencias:
npm init -y npm install wsImplementa el servidor WebSocket:
- Servidor escuchando en el puerto 8080
- Manejar conexiones de múltiples clientes simultáneamente
- Broadcast de mensajes a todos los clientes conectados
- Gestionar usuarios (username por cliente)
Tipos de mensajes:
register: Cliente envía su username al conectarmessage: Cliente envía mensaje de chatuser_joined: Servidor notifica cuando alguien se uneuser_left: Servidor notifica cuando alguien se va
Funcionalidades:
- Almacenar usuarios conectados con su websocket y username
- Broadcast a todos excepto al emisor
- Notificar a todos cuando un usuario se conecta/desconecta
- Manejo de errores y desconexiones
Estructura sugerida:
const WebSocket = require('ws');
const wss = new WebSocket.Server({ port: 8080 });
// Almacenar clientes conectados
const clients = new Map(); // ws -> {username, ws}
wss.on('connection', (ws) => {
console.log('New client connected');
ws.on('message', (message) => {
// TODO: Manejar mensajes
});
ws.on('close', () => {
// TODO: Manejar desconexión
});
});Bonus:
- Logging con timestamp de cada evento
- Comando “/users” para listar usuarios conectados
- Límite máximo de clientes simultáneos
- Heartbeat/ping para detectar conexiones muertas