L51 - Módulos ES6
🧠 Concepto
Section titled “🧠 Concepto”Los módulos ES6 permiten dividir el código JavaScript en archivos independientes que pueden exportar e importar funcionalidades entre sí. Cada módulo tiene su propio scope aislado: las variables, funciones y clases definidas dentro de un módulo no son accesibles desde fuera a menos que se exporten explícitamente.
💻 Exportaciones
Section titled “💻 Exportaciones”Export nombrado (named)
Section titled “Export nombrado (named)”export const PI = 3.1416;export function sumar(a, b) { return a + b; }export class Calculadora { ... }También se pueden declarar primero y exportar después:
const PI = 3.1416;function sumar(a, b) { return a + b; }export { PI, sumar };Con alias:
export { PI as PI_VALUE, sumar as add };Export por defecto (default)
Section titled “Export por defecto (default)”Cada módulo puede tener un único export default. Se usa para lo que el módulo “exporta por defecto”:
export default function log(msg) { console.log(`[LOG] ${msg}`);}O una clase:
export default class Usuario { ... }💻 Importaciones
Section titled “💻 Importaciones”Import de export nombrados
Section titled “Import de export nombrados”import { PI, sumar } from './utils.js';import { PI as PI_VALUE, sumar as add } from './utils.js';import * as utilidades from './utils.js'; // Namespace// uso: utilidades.PI, utilidades.sumar()Import de export default
Section titled “Import de export default”import log from './logger.js';import miLog from './logger.js'; // cualquier nombre valeImport mixto
Section titled “Import mixto”import log, { PI, sumar } from './logger.js';⚠️ type=“module” en HTML
Section titled “⚠️ type=“module” en HTML”Para usar módulos en el navegador, el script debe cargarse con type="module":
<script type="module" src="app.js"></script>Diferencias clave con scripts clásicos
Section titled “Diferencias clave con scripts clásicos”| Script clásico | Módulo |
|---|---|
| Scope global | Scope propio del módulo |
var crea propiedad en window | var NO contamina window |
| Se ejecuta en el orden de carga | Se ejecuta en orden, pero se descargan en paralelo |
"use strict" opcional | Siempre en strict mode |
this en顶层 es window | this en顶层 es undefined |
| Se carga de forma síncrona por defecto | Se cargan con defer implícito |
🎯 Import dinámico: import()
Section titled “🎯 Import dinámico: import()”import() es una función que devuelve una Promise y permite cargar módulos bajo demanda:
btn.addEventListener('click', async () => { const modulo = await import('./editor.js'); modulo.iniciarEditor();});Casos de uso:
- Code splitting: dividir el código en chunks que se cargan cuando se necesitan.
- Carga condicional: importar según el navegador, usuario o característica.
- Rutas dinámicas en SPAs.
📝 Beneficios de los módulos
Section titled “📝 Beneficios de los módulos”- Scope aislado: no hay colisión de nombres entre archivos.
- Reutilización: el mismo módulo se puede importar en múltiples lugares.
- Tree-shaking: los bundlers (Webpack, Vite) eliminan el código no utilizado.
- Mantenibilidad: código organizado en archivos pequeños con responsabilidades claras.
- Carga diferida: con
import()se cargan solo los recursos necesarios.
🧠 Ejemplo completo
Section titled “🧠 Ejemplo completo”export const API_URL = 'https://api.ejemplo.com';export const TIMEOUT = 5000;
// api.jsimport { API_URL, TIMEOUT } from './config.js';
export async function fetchUsers() { const res = await fetch(`${API_URL}/users`, { signal: AbortSignal.timeout(TIMEOUT) }); return res.json();}
// app.jsimport { fetchUsers } from './api.js';
const users = await fetchUsers();console.log(users);⚠️ Notas importantes
Section titled “⚠️ Notas importantes”- La ruta en
importdebe ser relativa (./o../) o una URL absoluta — no se puede poner un nombre simple sin ruta (eso requiere bundler). - Los módulos se cargan una sola vez, aunque se importen en varios sitios (se cachean).
- En Node.js, para usar módulos ES6 hay que poner
"type": "module"en elpackage.jsono usar extensión.mjs.
🎯 Regla de oro: usa
exportpara exponer solo lo necesario. Mantén el resto privado dentro del módulo.