@icarusmx/creta 1.5.13 → 1.5.15

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/bin/creta.js CHANGED
@@ -10,6 +10,7 @@ import { PullRequestTutorial } from '../lib/pr-tutorial.js'
10
10
  import { VimSetupTutorial } from '../lib/vim-setup-tutorial.js'
11
11
  import { AWSGuideViewer } from '../lib/aws-guide-viewer.js'
12
12
  import { CommandHelpExecutor } from '../lib/executors/CommandHelpExecutor.js'
13
+ import { readExercise, listExercises } from '../lib/readers/exercise-reader.js'
13
14
  import { PapersExecutor } from '../lib/papers/PapersExecutor.js'
14
15
  import { ExercisesExecutor } from '../lib/executors/ExercisesExecutor.js'
15
16
  import { executeSintaxis } from '../lib/executors/sintaxis-executor.js'
@@ -185,6 +186,13 @@ if (command.startsWith('portafolio')) {
185
186
  } else if (command === 'privacy' || command === 'privacidad') {
186
187
  // Show privacy information
187
188
  showPrivacyInfo()
189
+ } else if (command === 'read' || command === 'leer') {
190
+ // Read exercise/lesson
191
+ const query = args.slice(1).join(' ')
192
+ await readExercise(query)
193
+ } else if (command === 'exercises' || command === 'ejercicios') {
194
+ // List all exercises
195
+ await listExercises()
188
196
  } else if (command === 'help' || command === 'ayuda') {
189
197
  // Show available commands
190
198
  showHelp()
@@ -681,6 +689,7 @@ function showHelp() {
681
689
  console.log("📖 Documentación de comandos:")
682
690
  console.log(" creta ls - Documentación en español del comando ls")
683
691
  console.log(" creta grep - Documentación en español del comando grep")
692
+ console.log(" creta lz - Localiza recursos (alias de curl)")
684
693
  console.log(" creta cd - Documentación en español del comando cd")
685
694
  console.log(" creta curl - Documentación en español del comando curl")
686
695
  console.log(" creta git status - Documentación en español de git status")
@@ -690,7 +699,9 @@ function showHelp() {
690
699
  console.log(" creta - Menú principal interactivo")
691
700
  console.log(" creta sintaxis - Aprende comandos de terminal y Git")
692
701
  console.log(" creta enunciados - Explora los 7 enunciados fundamentales de OOP")
693
- console.log(" creta papers - Recrea papers clásicos de Computer Science\n")
702
+ console.log(" creta papers - Recrea papers clásicos de Computer Science")
703
+ console.log(" creta exercises - Lista todos los ejercicios disponibles")
704
+ console.log(" creta read <nombre> - Lee un ejercicio específico (ej: creta read 14)\n")
694
705
 
695
706
  console.log("🛠️ Proyectos:")
696
707
  console.log(" creta portafolio - Crea tu portafolio personal")
@@ -1904,7 +1915,7 @@ async function startVimSetupTutorial() {
1904
1915
  // Helper function to detect command help requests
1905
1916
  function isCommandHelpRequest(args) {
1906
1917
  // List of supported commands for help
1907
- const basicCommands = ['ls', 'cd', 'mkdir', 'touch', 'wc', 'curl', 'grep']
1918
+ const basicCommands = ['ls', 'cd', 'mkdir', 'touch', 'wc', 'curl', 'grep', 'lz']
1908
1919
  const gitCommands = ['git status', 'git add', 'git commit', 'git push', 'git log']
1909
1920
 
1910
1921
  const commandString = args.join(' ')
@@ -23,6 +23,10 @@ export const grep = {
23
23
  flag: '-c',
24
24
  description: 'Cuenta líneas que coinciden'
25
25
  },
26
+ {
27
+ flag: '-q',
28
+ description: 'Modo silencioso (no imprime nada, solo devuelve código de salida)'
29
+ },
26
30
  {
27
31
  flag: '-l',
28
32
  description: 'Solo muestra nombres de archivos con coincidencias'
@@ -6,6 +6,7 @@ export { touch } from './touch.js'
6
6
  export { wc } from './wc.js'
7
7
  export { curl } from './curl.js'
8
8
  export { grep } from './grep.js'
9
+ export { lz } from './lz.js'
9
10
 
10
11
  // Git commands
11
12
  export { gitStatus } from './git-status.js'
@@ -27,6 +28,7 @@ export const commandMap = {
27
28
  'wc': 'wc',
28
29
  'curl': 'curl',
29
30
  'grep': 'grep',
31
+ 'lz': 'lz',
30
32
 
31
33
  // Git
32
34
  'git status': 'gitStatus',
@@ -0,0 +1,67 @@
1
+ export const lz = {
2
+ command: 'lz',
3
+ description: 'Localiza recursos web con manejo automático de API keys',
4
+ usage: 'lz [url]',
5
+ setup: [
6
+ '1. Agrega la función lz a tu ~/.zshrc (ver lección Shell Functions)',
7
+ '2. Crea ~/.api_keys con permisos 600 para guardar tus keys',
8
+ '3. Exporta tu API key: export key="tu_api_key"',
9
+ '4. Usa lz normalmente - incluye la key automáticamente'
10
+ ],
11
+ commonPatterns: [
12
+ {
13
+ pattern: 'lz icarus.mx/api/endpoint',
14
+ description: 'Request GET con autenticación automática (si $key está definida)'
15
+ },
16
+ {
17
+ pattern: 'export key="sk_test_123"',
18
+ description: 'Define tu API key para la sesión actual'
19
+ },
20
+ {
21
+ pattern: 'unset key',
22
+ description: 'Elimina la API key de la sesión (seguridad)'
23
+ },
24
+ {
25
+ pattern: 'headers icarus.mx/api',
26
+ description: 'Ver headers de un endpoint (función helper)'
27
+ },
28
+ {
29
+ pattern: 'post icarus.mx/api \'{"name":"Memo"}\'',
30
+ description: 'POST request con JSON (función helper)'
31
+ }
32
+ ],
33
+ examples: [
34
+ {
35
+ command: 'lz icarus.mx',
36
+ description: 'Request normal (sin autenticación)'
37
+ },
38
+ {
39
+ command: 'export key="sk_test_4eC39HqLyjWDarjtT1zdp7dc" && lz icarus.mx/api/creta',
40
+ description: 'Request con API key (header automático)'
41
+ },
42
+ {
43
+ command: 'switch_key dev && lz icarus.mx/api/users',
44
+ description: 'Cambiar a key de desarrollo y hacer request'
45
+ },
46
+ {
47
+ command: 'lz icarus.mx/api/data | jq \'.results\'',
48
+ description: 'Request autenticado + parsear JSON con jq'
49
+ }
50
+ ],
51
+ relatedLesson: 'Shell Functions: API Querying Simplificado',
52
+ tips: [
53
+ '🔑 lz detecta automáticamente si $key está definida y agrega el header',
54
+ '⚡ Combina lz con jq para parsear JSON: lz api.com | jq',
55
+ '🔒 Usa chmod 600 ~/.api_keys para proteger tus keys',
56
+ '🔄 switch_key te permite cambiar entre dev/prod fácilmente',
57
+ '🧹 Siempre usa unset key cuando termines con APIs sensibles',
58
+ '📖 lz = "localiza recurso" - wrapper inteligente de curl'
59
+ ],
60
+ securityNotes: [
61
+ '❌ NUNCA pongas API keys directamente en ~/.zshrc',
62
+ '✅ Usa ~/.api_keys con permisos 600 (solo tú puedes leer)',
63
+ '✅ Agrega ~/.api_keys a tu .gitignore',
64
+ '✅ Usa unset key después de trabajar con APIs sensibles',
65
+ '✅ Considera usar direnv para keys por proyecto'
66
+ ]
67
+ }
@@ -0,0 +1,279 @@
1
+ # Shell Functions: API Querying Simplificado
2
+
3
+ ## Objetivo
4
+
5
+ Aprende a crear funciones de shell para hacer peticiones a APIs más fáciles. Crearemos `lz` (localiza recurso) - una función que maneja API keys automáticamente.
6
+
7
+ ## ¿Por qué una Función y no un Alias?
8
+
9
+ **Alias**: Atajo simple para un comando
10
+ - `alias lz='curl'` → reemplaza lz con curl
11
+
12
+ **Función**: Lógica programable con argumentos
13
+ - Puede verificar variables (`$key`)
14
+ - Puede construir requests dinámicamente
15
+ - Puede manejar errores
16
+
17
+ ## El Problema que Resuelve `lz`
18
+
19
+ Sin `lz`:
20
+ ```bash
21
+ curl -H "Authorization: Bearer tu_api_key_super_larga_aqui" https://icarus.mx/api/creta
22
+ ```
23
+
24
+ Con `lz`:
25
+ ```bash
26
+ export key="tu_api_key_super_larga_aqui"
27
+ lz icarus.mx/api/creta
28
+ ```
29
+
30
+ ## Por qué `lz`
31
+
32
+ **curl** = Client URL (Cliente de URL)
33
+ - **Cliente**: localiza recursos para ti
34
+ - **Universal**: usa HTTP (HyperText Transfer Protocol)
35
+ - **lz**: "localiza recurso" - wrapper inteligente de curl
36
+
37
+ ## Paso 1: Identificar tu Shell
38
+
39
+ En macOS Catalina+ se usa `zsh` por defecto:
40
+
41
+ ```bash
42
+ echo $SHELL
43
+ ```
44
+
45
+ Si ves `/bin/zsh` → usas zsh (archivo: `~/.zshrc`)
46
+ Si ves `/bin/bash` → usas bash (archivo: `~/.bashrc`)
47
+
48
+ ## Paso 2: Abrir el Archivo de Configuración
49
+
50
+ Para zsh (más común en Mac):
51
+
52
+ ```bash
53
+ nvim ~/.zshrc
54
+ ```
55
+
56
+ O si prefieres VS Code:
57
+
58
+ ```bash
59
+ code ~/.zshrc
60
+ ```
61
+
62
+ ## Paso 3: Agregar la Función `lz`
63
+
64
+ Al final del archivo, agrega esta función:
65
+
66
+ ```bash
67
+ # Función lz - API querying con API key automático
68
+ lz() {
69
+ local url="$1"
70
+
71
+ # Si la URL no tiene protocolo, agregar https://
72
+ if [[ ! "$url" =~ ^https?:// ]]; then
73
+ url="https://$url"
74
+ fi
75
+
76
+ # Si hay API key exportada, incluirla en el header
77
+ if [ -n "$key" ]; then
78
+ curl -H "Authorization: Bearer $key" "$url"
79
+ else
80
+ curl "$url"
81
+ fi
82
+ }
83
+ ```
84
+
85
+ **¿Qué hace esta función?**
86
+ 1. Toma la URL como argumento (`$1`)
87
+ 2. Agrega `https://` si no tiene protocolo
88
+ 3. Verifica si existe la variable `$key`
89
+ 4. Si existe, incluye el header de autorización
90
+ 5. Si no, hace un curl normal
91
+
92
+ Guarda el archivo:
93
+ - En nvim: presiona `ESC`, luego escribe `:wq` y `ENTER`
94
+ - En VS Code: `Cmd + S`
95
+
96
+ ## Paso 4: Recargar la Configuración
97
+
98
+ Tienes dos opciones:
99
+
100
+ **Opción 1: Recargar el archivo**
101
+ ```bash
102
+ source ~/.zshrc
103
+ ```
104
+
105
+ **Opción 2: Cerrar y abrir una nueva terminal**
106
+
107
+ ## Paso 5: Probar la Función
108
+
109
+ **Sin API key (request normal):**
110
+ ```bash
111
+ lz icarus.mx
112
+ ```
113
+
114
+ Deberías ver el HTML del sitio de Icarus.
115
+
116
+ **Con API key (request autenticado):**
117
+ ```bash
118
+ # Exportar tu API key (poético, ¿no?)
119
+ export key="es un secreto"
120
+
121
+ # Hacer request con autenticación automática
122
+ lz icarus.mx/api/creta/testeo
123
+
124
+ # La función automáticamente incluye:
125
+ # -H "Authorization: Bearer es un secreto"
126
+
127
+ # El API responde:
128
+ # "que a tu mirada y la mía la separa el abismo"
129
+ ```
130
+
131
+ **Ventajas:**
132
+ - No tener que escribir headers largos cada vez
133
+ - Cambiar de API key con un solo `export`
134
+ - Código más limpio y legible
135
+
136
+ ## Paso 6: Guardar el API Key de Forma Segura
137
+
138
+ **❌ Nunca hagas esto:**
139
+ ```bash
140
+ # NO pongas tu key directo en ~/.zshrc
141
+ export key="sk_live_SUPER_SECRETA" # ¡MAL!
142
+ ```
143
+
144
+ **✅ Mejor práctica:**
145
+ ```bash
146
+ # En ~/.zshrc agrega:
147
+ if [ -f ~/.api_keys ]; then
148
+ source ~/.api_keys
149
+ fi
150
+ ```
151
+
152
+ ```bash
153
+ # Crea ~/.api_keys con permisos restrictivos
154
+ touch ~/.api_keys
155
+ chmod 600 ~/.api_keys
156
+
157
+ # Edita ~/.api_keys y agrega:
158
+ export key="tu_api_key_aqui"
159
+ ```
160
+
161
+ Ahora tu key está separada y con permisos seguros (solo tú puedes leerla).
162
+
163
+ ## Funciones Adicionales Útiles
164
+
165
+ Mientras estás editando `~/.zshrc`, considera agregar:
166
+
167
+ ```bash
168
+ # Función para cambiar entre diferentes API keys
169
+ switch_key() {
170
+ case "$1" in
171
+ dev)
172
+ export key="sk_test_desarrollo"
173
+ echo "✅ API key: desarrollo"
174
+ ;;
175
+ prod)
176
+ export key="sk_live_produccion"
177
+ echo "✅ API key: producción"
178
+ ;;
179
+ *)
180
+ echo "Uso: switch_key [dev|prod]"
181
+ ;;
182
+ esac
183
+ }
184
+
185
+ # Ver headers de una API
186
+ headers() {
187
+ lz "$1" -I
188
+ }
189
+
190
+ # POST request con lz
191
+ post() {
192
+ local url="$1"
193
+ local data="$2"
194
+
195
+ if [ -n "$key" ]; then
196
+ curl -X POST -H "Authorization: Bearer $key" \
197
+ -H "Content-Type: application/json" \
198
+ -d "$data" "https://$url"
199
+ else
200
+ curl -X POST -H "Content-Type: application/json" \
201
+ -d "$data" "https://$url"
202
+ fi
203
+ }
204
+ ```
205
+
206
+ ## Verificar que Funciona
207
+
208
+ ```bash
209
+ # Request normal
210
+ lz icarus.mx
211
+
212
+ # Request con autenticación poética
213
+ export key="es un secreto"
214
+ lz icarus.mx/api/creta/testeo
215
+ # Responde: "que a tu mirada y la mía la separa el abismo"
216
+
217
+ # Ver headers
218
+ headers icarus.mx
219
+
220
+ # POST con data
221
+ post icarus.mx/api/users '{"name":"Guillermo"}'
222
+
223
+ # Cambiar entre keys
224
+ switch_key dev
225
+ switch_key prod
226
+ ```
227
+
228
+ ## Troubleshooting
229
+
230
+ **Problema: "command not found: lz"**
231
+ - Solución: Verifica que ejecutaste `source ~/.zshrc`
232
+ - Verifica que la función está correctamente definida (sin errores de sintaxis)
233
+
234
+ **Problema: "No such file or directory: ~/.zshrc"**
235
+ - Solución: Crea el archivo primero: `touch ~/.zshrc`
236
+
237
+ **Problema: Sigo usando bash en vez de zsh**
238
+ - Solución: Edita `~/.bashrc` en vez de `~/.zshrc`
239
+
240
+ **Problema: La API responde 401 Unauthorized**
241
+ - Verifica que exportaste la key: `echo $key`
242
+ - Verifica que la key es válida
243
+ - Prueba el request completo con curl para debug
244
+
245
+ **Problema: ~/.api_keys no se carga**
246
+ - Verifica que agregaste el `source` en ~/.zshrc
247
+ - Recarga la configuración: `source ~/.zshrc`
248
+
249
+ ## Seguridad: ¿Por qué `chmod 600`?
250
+
251
+ ```bash
252
+ chmod 600 ~/.api_keys
253
+ ```
254
+
255
+ Permisos en formato numérico:
256
+ - **6** (rw-): El dueño puede leer y escribir
257
+ - **0** (---): El grupo no tiene permisos
258
+ - **0** (---): Otros no tienen permisos
259
+
260
+ Resultado: Solo TÚ puedes leer tus API keys.
261
+
262
+ ## Siguiente Nivel
263
+
264
+ Una vez que domines funciones básicas, aprende sobre:
265
+ - **jq**: parsear JSON en la terminal
266
+ - **Scripts de shell**: automatizar workflows completos
267
+ - **Dotfiles**: versionar tu configuración con Git
268
+ - **Environment managers**: direnv para keys por proyecto
269
+
270
+ ## Recursos
271
+
272
+ - `man zsh` - Manual de zsh
273
+ - `man curl` - Manual de curl
274
+ - `printenv` - Ver todas tus variables de entorno
275
+ - `unset key` - Eliminar variable temporal
276
+
277
+ ---
278
+
279
+ **Pro tip**: Usa `unset key` cuando termines de trabajar con APIs sensibles. Las variables exportadas persisten en toda la sesión de la terminal.