shakers-cli 0.14.2 → 0.16.0
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/README.md +51 -1203
- package/bin/ai-usage.js +11 -56
- package/bin/login.js +10 -10
- package/bin/mcp.js +13 -9
- package/bin/mcpb.js +1 -1
- package/bin/onboarding.js +3 -2
- package/bin/register.js +17 -4
- package/bin/report-html.js +2 -2
- package/bin/shakers-cli.js +352 -0
- package/bin/shakers.js +20 -344
- package/bin/share.js +1 -1
- package/bin/superadmin.js +5 -5
- package/bin/version.js +3 -0
- package/package.json +12 -3
- package/src/agent-category.js +1 -1
- package/src/agent-evaluation.js +3 -3
- package/src/agent-org-chart.js +5 -5
- package/src/agent-synthesis.js +3 -3
- package/src/agent-usage.js +1 -1
- package/src/agents-client.js +4 -4
- package/src/ai.js +1 -1
- package/src/ansi.js +1 -1
- package/src/auth-client.js +18 -4
- package/src/auth-method-picker.js +1 -1
- package/src/auth-methods.js +1 -1
- package/src/auth-session-store.js +11 -8
- package/src/authorship-mismatch.js +1 -1
- package/src/authorship.js +2 -2
- package/src/automations-detector.js +1 -1
- package/src/backend-request.js +20 -3
- package/src/brand-ansi.js +1 -1
- package/src/browser-tools-detector.js +1 -1
- package/src/certify-disclaimer.js +1 -1
- package/src/certify-remediation-prompt.js +1 -1
- package/src/cli-args.js +2 -2
- package/src/command-audit.js +8 -5
- package/src/config-dir.js +1 -1
- package/src/config.js +112 -48
- package/src/consent-flow.js +4 -4
- package/src/consent-skip.js +1 -1
- package/src/detection-evidence.js +2 -2
- package/src/detection-noise.js +1 -1
- package/src/detectors.js +1 -1
- package/src/device-login.js +12 -1
- package/src/email-verification.js +3 -3
- package/src/env-paths.js +1 -1
- package/src/find-projects-client.js +12 -0
- package/src/find-projects-flow.js +1 -13
- package/src/git-activity.js +1 -1
- package/src/graph-certs.js +3 -3
- package/src/graph-scan.js +9 -9
- package/src/i18n.js +124 -124
- package/src/interactive-select.js +1 -1
- package/src/interview-client.js +6 -1
- package/src/interview-transcript.js +1 -1
- package/src/legal-notice.js +1 -1
- package/src/maturity.js +6 -6
- package/src/mcp-ai-usage-tool.js +1 -1
- package/src/mcp-auth-form.js +1 -1
- package/src/mcp-detector.js +3 -3
- package/src/mcp-device-login-tools.js +2 -1
- package/src/mcp-find-projects-tools.js +1 -2
- package/src/mcp-onboarding-tools.js +4 -4
- package/src/mcp-prompts.js +2 -2
- package/src/mcp-register-tools.js +1 -0
- package/src/mcp-server.js +5 -1
- package/src/mcp-signup-client.js +2 -2
- package/src/mcp-signup-tools.js +26 -2
- package/src/memory-structure-detector.js +1 -1
- package/src/model-call-record.js +2 -2
- package/src/onboarding-flow.js +16 -16
- package/src/onboarding-funnel.js +110 -17
- package/src/open-file.js +1 -1
- package/src/osc-link.js +1 -1
- package/src/portfolio-client.js +11 -1
- package/src/portfolio-git-info.js +1 -1
- package/src/profile-flow.js +1 -1
- package/src/profile-switch.js +5 -12
- package/src/render-certification.js +10 -10
- package/src/render-html.js +6 -6
- package/src/render-sheet.js +10 -10
- package/src/render-terminal.js +6 -6
- package/src/repo-scope.js +132 -0
- package/src/report-gating.js +1 -1
- package/src/report-store.js +6 -6
- package/src/roadmap-content.js +5 -5
- package/src/roadmap-personalization.js +3 -3
- package/src/roadmap-prompt.js +2 -2
- package/src/scan-exclusions.js +1 -1
- package/src/scanner.js +14 -14
- package/src/secret-prompt.js +1 -1
- package/src/session-gate.js +1 -1
- package/src/session-refresh.js +33 -3
- package/src/session-scan.js +1 -1
- package/src/shakers-wordmark.js +1 -1
- package/src/share-card.js +2 -2
- package/src/share-certification.js +4 -4
- package/src/share-consent-state.js +7 -7
- package/src/share-payload.js +7 -7
- package/src/share.js +7 -7
- package/src/signup-client.js +1 -1
- package/src/signup-copy.js +1 -1
- package/src/skills-client.js +1 -1
- package/src/start-add-agents.js +2 -2
- package/src/start-add-portfolio.js +3 -13
- package/src/start-add-skills.js +2 -2
- package/src/stdin-ask.js +3 -3
- package/src/strip-internal-comments.js +1 -1
- package/src/tech-detector.js +2 -2
- package/src/templates/report-sheet.html +11 -13
- package/src/terminal-agents.js +8 -8
- package/src/terminal-format.js +3 -3
- package/src/terminal-sections.js +11 -11
- package/src/tier-engine.js +3 -3
- package/src/tier-projection.js +2 -2
- package/src/transcript-turns.js +1 -1
- package/src/typewriter.js +1 -1
- package/src/usage-model-calls.js +6 -6
- package/src/usage-oneshot-commands.js +5 -5
- package/src/usage-repo-scope.js +11 -129
- package/src/usage-run-steps.js +32 -184
- package/src/usage-scan.js +235 -0
- package/src/work-streams.js +1 -1
package/src/i18n.js
CHANGED
|
@@ -227,7 +227,7 @@ const catalogs = {
|
|
|
227
227
|
},
|
|
228
228
|
ladder: {
|
|
229
229
|
levelsHeading: 'Niveles de madurez (0-4)',
|
|
230
|
-
//
|
|
230
|
+
// The ladder now groups tiers by SETUP LEVEL, not the 0-4 band.
|
|
231
231
|
setupHeading: 'Nivel de setup',
|
|
232
232
|
setupIntro:
|
|
233
233
|
'Tu nivel de setup (S1–S3) resume tu uso de IA de un vistazo; el tier (T0-T7) es el eje '
|
|
@@ -262,7 +262,7 @@ const catalogs = {
|
|
|
262
262
|
T7: 'Taller orquestado: hooks automatizan el taller y los agentes se orquestan entre sí.',
|
|
263
263
|
},
|
|
264
264
|
},
|
|
265
|
-
// Agent classification against the AI-agent catalog
|
|
265
|
+
// Agent classification against the AI-agent catalog + the "how to improve" tips.
|
|
266
266
|
classification: {
|
|
267
267
|
label: 'Clasificación',
|
|
268
268
|
noCategory: 'Sin categoría',
|
|
@@ -273,14 +273,14 @@ const catalogs = {
|
|
|
273
273
|
agentsEvalPartial: (names, count = 2) => (count === 1
|
|
274
274
|
? `Este agente se quedó fuera de esta ejecución: ${names}. La respuesta del modelo no llegó a cubrirlo, así que no es que no tenga categoría: es que no se llegó a evaluarlo. Vuelve a ejecutar \`usage\` para completarlo.`
|
|
275
275
|
: `Estos agentes se quedaron fuera de esta ejecución: ${names}. La respuesta del modelo no llegó a cubrirlos, así que no es que no tengan categoría: es que no se llegó a evaluarlos. Vuelve a ejecutar \`usage\` para completarlos.`),
|
|
276
|
-
// LA EVALUACIÓN FALLÓ ENTERA
|
|
276
|
+
// LA EVALUACIÓN FALLÓ ENTERA.
|
|
277
277
|
agentsEvalMissing: 'La categoría de tus agentes no se pudo calcular en esta ejecución: la evaluación no llegó a responder. No es que no tengan categoría. Vuelve a ejecutar `usage` para intentarlo otra vez.',
|
|
278
|
-
//
|
|
278
|
+
// Se parte el aviso genérico en dos, y el motivo es que apuntan a sitios distintos.
|
|
279
279
|
agentsEvalUnreachable: 'No se pudo conectar con Shakers, así que tus agentes salen sin categoría. Comprueba tu conexión y vuelve a ejecutar `usage`.',
|
|
280
280
|
agentsEvalErrored: 'Shakers respondió con un error, así que tus agentes salen sin categoría. No es cosa de tu configuración; vuelve a intentarlo en un rato.',
|
|
281
281
|
agentsEvalTimedOut: (count) => `La evaluación de tus agentes no respondió dentro del plazo, así que esta vez salen sin categoría. Ese tiempo crece con el número de agentes y tienes ${count}, así que volver a ejecutarlo tal cual probablemente acabe igual.`,
|
|
282
282
|
improvementsHeading: 'Cómo mejorar este agente',
|
|
283
|
-
// LAS OCHO CATEGORÍAS DEL CATÁLOGO DEL SERVICIO: siete especialidades y el SUELO (
|
|
283
|
+
// LAS OCHO CATEGORÍAS DEL CATÁLOGO DEL SERVICIO: siete especialidades y el SUELO (el catálogo vive en el servicio).
|
|
284
284
|
categories: {
|
|
285
285
|
developer: 'Desarrollo',
|
|
286
286
|
product: 'Producto',
|
|
@@ -298,7 +298,7 @@ const catalogs = {
|
|
|
298
298
|
},
|
|
299
299
|
},
|
|
300
300
|
// LEGACY 0-4 band names — kept only for older persisted reports / the
|
|
301
|
-
// unchanged sent payload
|
|
301
|
+
// unchanged sent payload; the report shows `setupLevels` instead.
|
|
302
302
|
levelNames: {
|
|
303
303
|
none: 'Sin rastro de IA',
|
|
304
304
|
exploring: 'Explorando',
|
|
@@ -306,7 +306,7 @@ const catalogs = {
|
|
|
306
306
|
power: 'Power user',
|
|
307
307
|
orchestrator: 'Orquestador',
|
|
308
308
|
},
|
|
309
|
-
// Setup Level (Talent Certification Framework
|
|
309
|
+
// Setup Level (Talent Certification Framework): the 3-value rollup that REPLACES the 0-4 band on every surface.
|
|
310
310
|
setupLevels: {
|
|
311
311
|
none: {
|
|
312
312
|
label: 'Sin certificar',
|
|
@@ -343,7 +343,7 @@ const catalogs = {
|
|
|
343
343
|
brandSub: 'perfil de uso de IA',
|
|
344
344
|
toolsDetected: (n, total) => `${n}/${total} herramientas detectadas`,
|
|
345
345
|
level: (level, name) => `Nivel ${level} · ${name}`,
|
|
346
|
-
//
|
|
346
|
+
// Setup Level shown in the top bar (replaces the 0-4 level line).
|
|
347
347
|
setupLevel: (label) => `Setup · ${label}`,
|
|
348
348
|
// Current tier appended to the top bar, next to the level (report req 1 addendum).
|
|
349
349
|
tierInline: (key, name) => ` · Tier ${key} · ${name}`,
|
|
@@ -371,16 +371,16 @@ const catalogs = {
|
|
|
371
371
|
environment: 'Entorno',
|
|
372
372
|
editors: 'editores',
|
|
373
373
|
noEditorsDetected: 'ninguno detectado',
|
|
374
|
-
//
|
|
374
|
+
// Agent evaluation (terminal, one line per agent): compact usage
|
|
375
375
|
// signal derived from the local Claude Code history.
|
|
376
376
|
agentUsed: (n) => `usado ${n}×`,
|
|
377
377
|
agentUnused: 'sin uso local',
|
|
378
378
|
agentUsageUnavailable: '(sin historial local de Claude Code: uso no disponible)',
|
|
379
|
-
//
|
|
379
|
+
// Discoverability hint for the next-steps section (behind --roadmap).
|
|
380
380
|
roadmapHint: 'Ejecuta `usage --roadmap` para ver los pasos que te separan del siguiente nivel de uso de IA. No son pasos de esta herramienta: son cambios en tu forma de trabajar, para las próximas semanas.',
|
|
381
381
|
aiProfileGenerating: 'Generando tu perfil de IA (matriz, visión y cómo trabajas)…',
|
|
382
382
|
aiProfilePendingRetry: 'Tu perfil de IA (matriz, visión y cómo trabajas) se está generando; re-lanza `report` en un momento para verlo.',
|
|
383
|
-
//
|
|
383
|
+
// Se muestra cuando había una sesión y ha caducado, para que el talento entienda por qué vuelve a ver el informe completo.
|
|
384
384
|
sessionExpiredNotice: 'Tu sesión ha caducado. Estás viendo el informe completo como usuario general; ejecuta `login` para volver a entrar.',
|
|
385
385
|
nextStep: 'Siguiente paso para subir de nivel',
|
|
386
386
|
files: (n) => `${n} ${n === 1 ? 'fichero' : 'ficheros'}`,
|
|
@@ -393,7 +393,7 @@ const catalogs = {
|
|
|
393
393
|
h1: 'Tu perfil de uso de IA',
|
|
394
394
|
sub: 'Un vistazo local a qué herramientas de IA tienes y cuánto las has configurado.',
|
|
395
395
|
levelOf: (level) => `Nivel ${level} de 4`,
|
|
396
|
-
//
|
|
396
|
+
// Hero label for the Setup Level (replaces the 0-4 "Nivel X de 4").
|
|
397
397
|
setupLevelOf: 'Nivel de setup',
|
|
398
398
|
// Current tier shown in the hero bar next to the level (report req 1 addendum).
|
|
399
399
|
currentTier: (key, name) => `Tier ${key} · ${name}`,
|
|
@@ -402,7 +402,7 @@ const catalogs = {
|
|
|
402
402
|
detectedSuffix: (total) => `de ${total} herramientas detectadas`,
|
|
403
403
|
maturity: 'Madurez',
|
|
404
404
|
tools: 'Herramientas',
|
|
405
|
-
//
|
|
405
|
+
// Only DETECTED tools are listed now (undetected ones were pure noise — any relevant next step already lives in the tier roadmap section).
|
|
406
406
|
toolsEmpty: 'No se ha detectado ninguna herramienta de IA en tu entorno.',
|
|
407
407
|
configIntensity: 'intensidad de configuración',
|
|
408
408
|
files: (n) => `${n} ${n === 1 ? 'fichero' : 'ficheros'}`,
|
|
@@ -416,21 +416,21 @@ const catalogs = {
|
|
|
416
416
|
diagramHeading: 'Agentes',
|
|
417
417
|
agentsEmpty: 'No se han detectado agentes de IA configurados (p. ej. .claude/agents/).',
|
|
418
418
|
orchestratorLabel: 'Orchestrator',
|
|
419
|
-
// Last-resort description fallback (
|
|
419
|
+
// Last-resort description fallback (a card must NEVER show only name+model, no description at all).
|
|
420
420
|
agentDescriptionFromName: (name) => `Agente "${name}" (sin descripción declarada en su fichero).`,
|
|
421
421
|
// AI product an agent belongs to, derived from its source (proper nouns; same es/en).
|
|
422
422
|
aiProducts: { 'claude-code': 'Claude Code' },
|
|
423
|
-
//
|
|
423
|
+
// Agent evaluation (HTML per-agent detail): definition-quality score + LLM rationale + local usage signal.
|
|
424
424
|
agentScoreLabel: 'Calidad de la definición (0-100)',
|
|
425
425
|
agentQualityLabel: 'Por qué:',
|
|
426
426
|
agentUsageLabel: 'Uso local (historial de Claude Code)',
|
|
427
427
|
agentUsedTimes: (n) => `usado ${n}×`,
|
|
428
428
|
agentUnused: 'sin uso local',
|
|
429
|
-
// Project technologies
|
|
429
|
+
// Project technologies.
|
|
430
430
|
technologiesHeading: 'Tecnologías del proyecto',
|
|
431
431
|
technologiesEmpty: 'No se reconoció ningún framework o librería en los manifiestos de dependencias (package.json, requirements.txt, go.mod, pyproject.toml).',
|
|
432
|
-
// MCP servers by name
|
|
433
|
-
//
|
|
432
|
+
// MCP servers by name.
|
|
433
|
+
// Esta clave existía desde la 015 y NO la pintaba nadie — los servidores MCP se detectaban, contaban para el tier y no se nombraban en ninguna superficie.
|
|
434
434
|
mcpHeading: 'Servicios conectados por MCP',
|
|
435
435
|
mcpEmpty: 'No se ha detectado ningún servidor MCP. Conectar uno es el criterio que te sube a T3 (Banco conectado).',
|
|
436
436
|
mcpUnidentified: (n) => `${n} ${n === 1 ? 'servidor más, cuyo servicio no' : 'servidores más, cuyo servicio no'} hemos podido identificar por su nombre.`,
|
|
@@ -447,18 +447,18 @@ const catalogs = {
|
|
|
447
447
|
roadmapConsolidationLabel: 'Pasos de consolidación',
|
|
448
448
|
roadmapHonestyLabel: 'Nota de honestidad',
|
|
449
449
|
roadmapContentUnavailable: 'El contenido detallado de este nivel aún no está disponible en este idioma.',
|
|
450
|
-
//
|
|
450
|
+
// Shown only when the 4 prose gaps below were actually replaced by a validated, project-adapted response — never on fallback to the curated content.
|
|
451
451
|
roadmapPersonalizedNotice: 'Contenido adaptado a tu proyecto.',
|
|
452
|
-
//
|
|
452
|
+
// Los dos avisos que faltaban, hermanos del `agentsEvalMissing` que añadió la 106.
|
|
453
453
|
roadmapNotPersonalizedNotice: 'Este roadmap es el genérico de tu tier: esta vez no se ha podido adaptar a tu proyecto. Vuelve a ejecutar `usage` para intentarlo otra vez.',
|
|
454
|
-
//
|
|
454
|
+
// El antes y el después del roadmap.
|
|
455
455
|
roadmapNowLabel: 'De dónde partes',
|
|
456
456
|
roadmapProjectionLabel: 'Dónde te deja esta ruta',
|
|
457
457
|
roadmapProjectionTag: 'proyección',
|
|
458
458
|
roadmapProjectionNote: 'Calculado con el mismo motor que tu evaluación, aplicando el mínimo que piden estos pasos. Es una proyección, no una promesa: la evaluación mide uso real, así que darlos es condición necesaria y no suficiente.',
|
|
459
459
|
implementationPromptHeading: 'Prompt para implementar',
|
|
460
460
|
implementationPromptHint: 'Copia este prompt y pégalo en tu IA de confianza (Claude Code, Cursor, ChatGPT...) para que lo implemente en tu proyecto.',
|
|
461
|
-
// Copy-to-clipboard button (HTML report only
|
|
461
|
+
// Copy-to-clipboard button (HTML report only): navigator.clipboard with a document.execCommand fallback, both inline, zero-network.
|
|
462
462
|
implementationPromptCopyLabel: 'Copiar',
|
|
463
463
|
implementationPromptCopiedLabel: 'Copiado ✓',
|
|
464
464
|
privacyNote:
|
|
@@ -470,9 +470,9 @@ const catalogs = {
|
|
|
470
470
|
rawData: 'Ver los datos exactos de este informe (JSON)',
|
|
471
471
|
},
|
|
472
472
|
cli: {
|
|
473
|
-
// Reporting redesign
|
|
473
|
+
// Reporting redesign: el HTML ya NO es opt-in (se retira --html).
|
|
474
474
|
reportLink: (url) => `Abre tu informe en el navegador:\n ${url}`,
|
|
475
|
-
// `share` command
|
|
475
|
+
// `share` command: copy del CLI que envuelve a la tarjeta branded para LinkedIn.
|
|
476
476
|
share: {
|
|
477
477
|
help: 'share — crea una tarjeta branded con tu resultado de uso de IA (tier + nota) para compartir en LinkedIn.\n'
|
|
478
478
|
+ ' Usa `usage` primero; `share` toma el último uso de IA de este proyecto.\n'
|
|
@@ -522,7 +522,7 @@ const catalogs = {
|
|
|
522
522
|
available: (from, to) => `Hay una versión nueva del CLI de Shakers: ${from} → ${to}`,
|
|
523
523
|
howTo: 'Ejecuta `shakers update` para actualizar.',
|
|
524
524
|
},
|
|
525
|
-
// `report` command
|
|
525
|
+
// `report` command: genera y ABRE el informe HTML completo y compartible de este proyecto (uso de IA + Skills certificadas).
|
|
526
526
|
report: {
|
|
527
527
|
help: 'report — genera y abre el informe HTML completo de este proyecto (uso de IA + Skills certificadas) para compartir con tu equipo.\n'
|
|
528
528
|
+ ' Usa `usage` (y opcionalmente `certify`) primero; `report` reúne su resultado.\n'
|
|
@@ -534,7 +534,7 @@ const catalogs = {
|
|
|
534
534
|
},
|
|
535
535
|
frameworkIntroUsage:
|
|
536
536
|
'Esto mide tu fluidez con IA en dos ejes: Setup (madurez de tu tooling, T0–T7, determinista) y Usage (cómo lo usas, evaluado en entrevista + código). Te sitúa en el mapa 3×3 (Explorer → AI Native). Completarlo posiciona tu perfil agéntico para los proyectos que valoran cómo trabajas con IA. Por defecto leo el uso de IA de todo este equipo y asumo que es tuyo (un equipo = tú).',
|
|
537
|
-
// Terminal progress feedback
|
|
537
|
+
// Terminal progress feedback: stderr-only status
|
|
538
538
|
// during the two slow phases (see src/terminal-progress.js).
|
|
539
539
|
scanningLabel: 'Escaneando entorno y detectores…',
|
|
540
540
|
// Loader de la fase de agregación por repo seleccionado (git + sesiones + steering/decisiones + evidencia + org-chart de agentes).
|
|
@@ -555,14 +555,14 @@ const catalogs = {
|
|
|
555
555
|
`Evaluación de toda la máquina limitada a ${shown} de ${total} repos detectados (los más activos primero).`,
|
|
556
556
|
reposScopeAll: 'Evaluando todo el uso de IA de la máquina.',
|
|
557
557
|
synthesizingLabel: 'Sintetizando agentes con IA…',
|
|
558
|
-
// Roadmap personalization
|
|
558
|
+
// Roadmap personalization: reuses the
|
|
559
559
|
// same spinner mechanism as synthesizingLabel above.
|
|
560
560
|
personalizingRoadmapLabel: 'Personalizando roadmap…',
|
|
561
|
-
//
|
|
561
|
+
// Agent definition-quality evaluation (ephemeral LLM call).
|
|
562
562
|
evaluatingAgentsLabel: 'Evaluando la calidad de tus agentes…',
|
|
563
|
-
// "Construir el siguiente nivel ahora"
|
|
563
|
+
// "Construir el siguiente nivel ahora": now a SECONDARY, opt-in alternative — the copyable implementation prompt (below) is the PRIMARY "how do I implement this" path.
|
|
564
564
|
buildNextLevelHint: 'Alternativamente, ejecuta `usage --build-next-level` para generar el fichero de partida directamente en tu proyecto.',
|
|
565
|
-
// Ayuda localizada
|
|
565
|
+
// Ayuda localizada: antes estaba hardcodeada en español en bin/report.js; ahora pasa por i18n y respeta la locale de la máquina.
|
|
566
566
|
help:
|
|
567
567
|
'\nShakers — perfil local de uso de herramientas de IA\n\n'
|
|
568
568
|
+ 'Uso:\n usage [opciones]\n\n'
|
|
@@ -616,7 +616,7 @@ const catalogs = {
|
|
|
616
616
|
label: 'AVISO LEGAL',
|
|
617
617
|
},
|
|
618
618
|
consent: {
|
|
619
|
-
//
|
|
619
|
+
// The disclosure wall (what's sent / never sent, itemized) is RETIRED from the CLI — that content now lives in the repo's README.
|
|
620
620
|
persistIntro:
|
|
621
621
|
'Este informe se ha generado y mostrado en tu equipo, siempre. '
|
|
622
622
|
+ 'Guardarlo en Shakers es opcional y revocable en cualquier momento '
|
|
@@ -644,11 +644,11 @@ const catalogs = {
|
|
|
644
644
|
savedUnderEmail: (email) => `El informe se guardará a nombre de: ${email}`,
|
|
645
645
|
invalidEmail: 'Correo no válido, inténtalo de nuevo.',
|
|
646
646
|
notObtained: 'No se ha podido registrar tu respuesta; se te volverá a preguntar la próxima vez.',
|
|
647
|
-
//
|
|
647
|
+
// Esta pregunta se pide ahora ANTES de cualquier llamada de IA/egress (agent-synthesis, agent-evaluation, personalización de roadmap), no después.
|
|
648
648
|
noReportWithoutConsent: 'Sin tu consentimiento, este informe no incluirá síntesis, evaluación ni roadmap generados por IA esta vez (el resto del informe se muestra igual). Vuelve a ejecutar `usage` y acepta para incluirlos, o usa --consent-reset si quieres que se te pregunte de nuevo.',
|
|
649
649
|
deniedSaved: 'Entendido, no se guardará nada. Puedes cambiar de opinión más adelante volviendo a ejecutar el comando.',
|
|
650
650
|
grantedSaved: (email) => `Gracias. A partir de ahora este informe se guardará automáticamente en Shakers (correo: ${email}, máx. 1 vez por hora).`,
|
|
651
|
-
//
|
|
651
|
+
// Un talento logueado NUNCA ve el prompt de email (su cuenta ya prueba su identidad).
|
|
652
652
|
noSessionEmail: 'No hay un correo asociado a tu sesión todavía, así que no se puede guardar el informe esta vez. Se te preguntará de nuevo la próxima ejecución.',
|
|
653
653
|
skipAlreadyDecided: (decision, path) =>
|
|
654
654
|
`Consentimiento ya respondido (${decision === 'granted' ? 'concedido' : 'rechazado'}) — guardado en ${path}. `
|
|
@@ -681,8 +681,8 @@ const catalogs = {
|
|
|
681
681
|
showConfigFile: (url, path) => `Endpoint de ingesta efectivo: ${url}\n Origen: fichero de config (${path}).`,
|
|
682
682
|
showConfigInvalid: (path) => `El fichero de config (${path}) tiene un endpoint no válido o inseguro; se ignora. Corrígelo con usage --set-endpoint <url>.`,
|
|
683
683
|
showNone: 'No hay endpoint de ingesta configurado. Define SHAKERS_CLI_INGEST_ENDPOINT o usa usage --set-endpoint <url>. Sin él, el informe se sigue mostrando pero no se envía a Shakers.',
|
|
684
|
-
//
|
|
685
|
-
//
|
|
684
|
+
// El CLI habla con una CADENA de dos backends — PRIMARIO (servicio de certificaciones, arriba) y FALLBACK (hub-backend, aquí).
|
|
685
|
+
// The second backend was retired, so the five `showFallback*`/ `setFallbackOk` strings that explained the chain are gone with it.
|
|
686
686
|
showFallbackRetired: 'Nota: tu config.json todavía tiene `ingestEndpointFallback`. Ya no se usa: el CLI habla con un solo backend. Puedes borrar esa línea a mano; dejarla no afecta a nada.',
|
|
687
687
|
confirmHostPrompt: (host) => `El host "${host}" no es localhost ni un dominio conocido de Shakers. Si continúas, tu código muestreado y tus señales de IA se enviarán ahí.\n Escribe el hostname exacto para confirmar (déjalo en blanco para cancelar):`,
|
|
688
688
|
confirmHostMismatch: 'No coincide con el hostname mostrado. Cancelado: no se ha guardado nada.',
|
|
@@ -716,7 +716,7 @@ const catalogs = {
|
|
|
716
716
|
}
|
|
717
717
|
},
|
|
718
718
|
},
|
|
719
|
-
// Email-ownership verification
|
|
719
|
+
// Email-ownership verification: the OTP "modo espera" copy, shared by both binaries.
|
|
720
720
|
verify: {
|
|
721
721
|
sent: (email) => `Te enviamos un código de verificación a ${email}.`,
|
|
722
722
|
waitHint: 'Pega aquí el código. Pulsa "r" y Enter para reenviarlo, o Enter en blanco para cancelar.',
|
|
@@ -732,7 +732,7 @@ const catalogs = {
|
|
|
732
732
|
cancelled: 'Verificación cancelada. No se guardará el informe (el reporte ya se te ha mostrado).',
|
|
733
733
|
unavailable: 'La verificación de correo no está disponible ahora mismo; no se guardará el informe (el reporte ya se te ha mostrado).',
|
|
734
734
|
},
|
|
735
|
-
// Skill Code Certification
|
|
735
|
+
// Skill Code Certification.
|
|
736
736
|
// Copy for the SECOND binary `ai-certify` (resolve phase V1). Localized
|
|
737
737
|
// like the consent flow — legal/disclaimer copy must not default to a
|
|
738
738
|
// language the Talent may not read. Vocabulario CONTEXT: Talent, Skill.
|
|
@@ -1117,7 +1117,7 @@ const catalogs = {
|
|
|
1117
1117
|
failed: (reason) => `No se pudo hablar con Alma (${reason}). Inténtalo de nuevo en un momento.`,
|
|
1118
1118
|
},
|
|
1119
1119
|
certify: {
|
|
1120
|
-
// Aviso legal
|
|
1120
|
+
// Aviso legal: asume el proyecto propiedad del Talent y le
|
|
1121
1121
|
// atribuye la responsabilidad. Aceptación explícita obligatoria.
|
|
1122
1122
|
disclaimer:
|
|
1123
1123
|
'AVISO LEGAL — léelo antes de continuar:\n'
|
|
@@ -1140,7 +1140,7 @@ const catalogs = {
|
|
|
1140
1140
|
disclaimerDeclined: 'No has aceptado el aviso legal. No se ha enviado nada.',
|
|
1141
1141
|
disclaimerInvalidAnswer: 'Respuesta no reconocida. Responde "s" (sí) o "n" (no).',
|
|
1142
1142
|
disclaimerNoAnswer: 'No se ha obtenido respuesta. No se ha enviado nada.',
|
|
1143
|
-
// Certify report (terminal + HTML). Rúbrica anclada + agregación determinista
|
|
1143
|
+
// Certify report (terminal + HTML). Rúbrica anclada + agregación determinista.
|
|
1144
1144
|
report: {
|
|
1145
1145
|
heading: 'Resultado de certificación de Skills TÉCNICAS',
|
|
1146
1146
|
noInterviewNote: 'Preliminar, sin entrevista: la certificación combinada de esta Skill requiere completar su entrevista.',
|
|
@@ -1152,7 +1152,7 @@ const catalogs = {
|
|
|
1152
1152
|
partialSampleWarning:
|
|
1153
1153
|
'Muestra parcial: por los límites de tamaño la valoración se basa en una muestra del '
|
|
1154
1154
|
+ 'código, no en todo el proyecto.',
|
|
1155
|
-
//
|
|
1155
|
+
// Skill levels (by decision power, NOT points) — replace the
|
|
1156
1156
|
// numeric grade in the skill output. `key` from skillLevelForScore.
|
|
1157
1157
|
levelLine: (label) => `Nivel: ${label}`,
|
|
1158
1158
|
skillLevels: {
|
|
@@ -1161,7 +1161,7 @@ const catalogs = {
|
|
|
1161
1161
|
expert: 'Expert',
|
|
1162
1162
|
na: '—',
|
|
1163
1163
|
},
|
|
1164
|
-
//
|
|
1164
|
+
// Rubric dimensions.
|
|
1165
1165
|
dimensionsLabel: 'Dimensiones',
|
|
1166
1166
|
dimensionNA: 'N/A',
|
|
1167
1167
|
dimensionLabels: {
|
|
@@ -1173,7 +1173,7 @@ const catalogs = {
|
|
|
1173
1173
|
},
|
|
1174
1174
|
rationaleLabel: 'Por qué',
|
|
1175
1175
|
improvementsLabel: 'Mejoras sugeridas',
|
|
1176
|
-
//
|
|
1176
|
+
// Authorship receipt (atribución, NO prueba criptográfica).
|
|
1177
1177
|
receipt: {
|
|
1178
1178
|
label: 'Autoría',
|
|
1179
1179
|
repoLabel: 'Repo',
|
|
@@ -1196,11 +1196,11 @@ const catalogs = {
|
|
|
1196
1196
|
`No hay muestreo definido para la tecnología "${technology}": todavía no se puede certificar por código.`,
|
|
1197
1197
|
htmlTitle: 'Certificación de Skills técnicas · Shakers',
|
|
1198
1198
|
noItems: 'No hay resultados de certificación que mostrar.',
|
|
1199
|
-
// Coste
|
|
1199
|
+
// Coste: input mayor = más € por run.
|
|
1200
1200
|
costNote:
|
|
1201
1201
|
'Nota de coste: se analiza bastante código por Skill (hasta ~150k tokens/Skill), '
|
|
1202
1202
|
+ 'lo que tiene un coste por ejecución.',
|
|
1203
|
-
// Prompt de remediación
|
|
1203
|
+
// Prompt de remediación: generado en local desde las mejoras.
|
|
1204
1204
|
remediationHeading: 'Prompt para aplicar las mejoras',
|
|
1205
1205
|
remediationHint: 'Copia este prompt y pégalo en tu herramienta de IA (Claude Code, Cursor…) para aplicar las mejoras.',
|
|
1206
1206
|
remediationIntro: (skillName, technology) =>
|
|
@@ -1213,7 +1213,7 @@ const catalogs = {
|
|
|
1213
1213
|
remediationCopiedLabel: 'Copiado ✓',
|
|
1214
1214
|
},
|
|
1215
1215
|
},
|
|
1216
|
-
// Branded mini-shell chrome
|
|
1216
|
+
// Branded mini-shell chrome.
|
|
1217
1217
|
login: {
|
|
1218
1218
|
intro: 'Inicia sesión con tu email y contraseña de Shakers.',
|
|
1219
1219
|
sessionExpiredIntro: 'Tu sesión anterior caducó. Vuelve a iniciar sesión.',
|
|
@@ -1234,7 +1234,7 @@ const catalogs = {
|
|
|
1234
1234
|
errorNoEndpoint: 'No hay endpoint configurado. login usa la misma base que usage: define SHAKERS_CLI_INGEST_ENDPOINT o usa `usage --set-endpoint <url>`.',
|
|
1235
1235
|
errorPersist: 'El inicio de sesión funcionó, pero no se pudo guardar la sesión en disco. Revisa los permisos de ~/.config/shakers y vuelve a intentarlo.',
|
|
1236
1236
|
errorGeneric: 'No se pudo iniciar sesión. Inténtalo de nuevo.',
|
|
1237
|
-
//
|
|
1237
|
+
// Login con Google por loopback (`login --google`).
|
|
1238
1238
|
googleIntro: 'Inicia sesión con Google. Se abrirá tu navegador para autorizar; al terminar, vuelve aquí.',
|
|
1239
1239
|
googleOpening: 'Abriendo el navegador para iniciar sesión con Google…',
|
|
1240
1240
|
googlePasteUrl: 'Si el navegador no se abre solo, pega esta URL en él:',
|
|
@@ -1264,7 +1264,7 @@ const catalogs = {
|
|
|
1264
1264
|
selectHint: 'Flechas ↑/↓ para moverte · enter para elegir · esc para cancelar',
|
|
1265
1265
|
chooseMethodPrompt: (max) => `Número (1-${max}), vacío para cancelar: `,
|
|
1266
1266
|
},
|
|
1267
|
-
// `start
|
|
1267
|
+
// `start`: la herramienta para un talento YA registrado en Shakers que quiere completar su perfil agéntico.
|
|
1268
1268
|
start: {
|
|
1269
1269
|
help:
|
|
1270
1270
|
'start — completa tu perfil de talento agéntico en Shakers: inicia sesión, evalúa tu uso de IA\n'
|
|
@@ -1288,10 +1288,10 @@ const catalogs = {
|
|
|
1288
1288
|
menuHint: 'Flechas ↑/↓ para moverte · enter para elegir · esc para cancelar',
|
|
1289
1289
|
menuPrompt: (max) => `Número (1-${max}), vacío para cancelar: `,
|
|
1290
1290
|
menuRerun: 'Volver a lanzar la evaluación de uso de IA',
|
|
1291
|
-
//
|
|
1291
|
+
// Renombrado — el label decía "Añadir" pero la acción es declarar/subir lo detectado al PERFIL de Shakers, no crear algo nuevo desde cero.
|
|
1292
1292
|
menuAddSkills: 'Subir skills a tu perfil',
|
|
1293
1293
|
menuAddAgents: 'Subir agentes a tu perfil',
|
|
1294
|
-
//
|
|
1294
|
+
// "Añadir proyecto al portfolio" — junto a las de skills/agentes, antes de certificar (declarar cosas de tu perfil, luego certificarlas).
|
|
1295
1295
|
menuAddPortfolio: 'Añadir proyecto al portfolio',
|
|
1296
1296
|
menuCertifySkills: 'Certificar skills',
|
|
1297
1297
|
menuCertifyAgents: 'Certificar agentes',
|
|
@@ -1310,7 +1310,7 @@ const catalogs = {
|
|
|
1310
1310
|
menuCertifyAgentsDesc:
|
|
1311
1311
|
'Un reto valida que el agente es real, es tuyo y lo operas con criterio. Obtienes el agente Certified con su tracción → la señal más fuerte de tu perfil agéntico.',
|
|
1312
1312
|
menuCancelled: 'Cancelado. No se ha hecho nada.',
|
|
1313
|
-
//
|
|
1313
|
+
// Cierre del BUCLE del menú — usado tanto al elegir "Salir" explícitamente como al cancelar (esc / respuesta vacía) DESDE DENTRO del bucle.
|
|
1314
1314
|
menuGoodbye: 'Sesión de `start` terminada. Ejecuta `start` de nuevo cuando quieras seguir completando tu perfil.',
|
|
1315
1315
|
addAgentsComingSoon:
|
|
1316
1316
|
'Añadir agentes: próximamente. Tus agentes serán activos de tu perfil agéntico — todavía no existe esa ficha en Shakers, así que de momento no hay dónde guardarlos.',
|
|
@@ -1329,7 +1329,7 @@ const catalogs = {
|
|
|
1329
1329
|
addSkillsNoneChosen: 'No has elegido ninguna skill. No se ha añadido nada a tu perfil.',
|
|
1330
1330
|
addSkillsDeclaredOne: (skillName) => `✓ Añadida a tu perfil: ${skillName} (sin verificar).`,
|
|
1331
1331
|
addSkillsDeclareFailed: (skillName, reason) => `✗ No se pudo añadir ${skillName}: ${reason}`,
|
|
1332
|
-
// Cierre de la visión
|
|
1332
|
+
// Cierre de la visión: UNA vez, después del lote — no repetido por cada skill (repetir la misma frase por ítem es ruido, no refuerzo).
|
|
1333
1333
|
addSkillsProfileBoost: 'Cada skill que añades suma a tu perfil: apareces en más búsquedas.',
|
|
1334
1334
|
addSkillsHubSessionExpired: 'Tu sesión de Shakers ha caducado mientras añadíamos tus skills.',
|
|
1335
1335
|
addSkillsOfferRelogin: '¿Quieres volver a iniciar sesión ahora para seguir? (s/n):',
|
|
@@ -1344,7 +1344,7 @@ const catalogs = {
|
|
|
1344
1344
|
addSkillsRelateSkipped: (skillName) => `"${skillName}" añadida sin relacionar.`,
|
|
1345
1345
|
addSkillsRelated: (skillName, portfolioName) => ` ✓ "${skillName}" relacionada con "${portfolioName}".`,
|
|
1346
1346
|
addSkillsRelateFailed: (skillName, portfolioName, reason) => ` ✗ No se pudo relacionar "${skillName}" con "${portfolioName}": ${reason}`,
|
|
1347
|
-
//
|
|
1347
|
+
// "Añadir proyecto al portfolio".
|
|
1348
1348
|
portfolioIntro:
|
|
1349
1349
|
'Vamos a añadir este proyecto a tu portfolio de Shakers. La mayoría de los datos vienen pre-rellenados desde tu código y tu git: confirma o edita cada uno.',
|
|
1350
1350
|
portfolioErrorNoEndpoint:
|
|
@@ -1356,7 +1356,7 @@ const catalogs = {
|
|
|
1356
1356
|
portfolioDuplicateName: (name) => `Ya tienes un proyecto llamado "${name}" en tu portfolio. No se ha creado uno duplicado — vuelve a ejecutar esta opción con otro título si quieres añadir uno distinto.`,
|
|
1357
1357
|
// (1) Título ← nombre del directorio, editable.
|
|
1358
1358
|
portfolioTitlePrompt: (def) => `Título del proyecto [${def}]:`,
|
|
1359
|
-
// (2) Tipo ← PORTFOLIO/EXPERIENCE, obligatorio. Copy de visión
|
|
1359
|
+
// (2) Tipo ← PORTFOLIO/EXPERIENCE, obligatorio. Copy de visión:
|
|
1360
1360
|
// qué significa cada tipo para tu perfil, mostrado SOLO al resaltar.
|
|
1361
1361
|
portfolioTypeHeading: '¿Qué tipo de entrada es?',
|
|
1362
1362
|
portfolioTypeHint: 'Flechas ↑/↓ para moverte · enter para elegir · esc para cancelar',
|
|
@@ -1367,7 +1367,7 @@ const catalogs = {
|
|
|
1367
1367
|
portfolioTypeExperience: 'Experiencia',
|
|
1368
1368
|
portfolioTypeExperienceDesc:
|
|
1369
1369
|
'Lo añade a tu perfil como experiencia profesional (freelance o de plantilla): cuenta en tu trayectoria, no como una pieza para mostrar.',
|
|
1370
|
-
// (3) Descripción ← IA pre-redacta tras consentimiento
|
|
1370
|
+
// (3) Descripción ← IA pre-redacta tras consentimiento.
|
|
1371
1371
|
portfolioDescriptionConsentDisclaimer:
|
|
1372
1372
|
'Para redactar un borrador de la descripción con IA, se enviarán a Shakers: el nombre del proyecto, las tecnologías detectadas y, si existen, el contenido del README y la descripción del package.json.',
|
|
1373
1373
|
portfolioDescriptionDraftLabel: 'Borrador generado por IA:',
|
|
@@ -1395,7 +1395,7 @@ const catalogs = {
|
|
|
1395
1395
|
portfolioRelaunchAfterRelogin: 'Sesión renovada. Reintentamos añadir el proyecto a tu portfolio.',
|
|
1396
1396
|
portfolioRelaunchDeclined: 'Vale. Ejecuta `login` y vuelve a elegir "Añadir proyecto al portfolio" cuando quieras.',
|
|
1397
1397
|
portfolioReloginFailed: 'No se pudo volver a iniciar sesión. El proyecto no se ha añadido a tu portfolio.',
|
|
1398
|
-
//
|
|
1398
|
+
// "Añadir agente al perfil".
|
|
1399
1399
|
agentErrorNoEndpoint:
|
|
1400
1400
|
'No hay endpoint configurado. `start` usa la misma base que `usage`: define el endpoint con `usage --set-endpoint <url>` (o SHAKERS_CLI_INGEST_ENDPOINT).',
|
|
1401
1401
|
agentNoHubToken:
|
|
@@ -1416,7 +1416,7 @@ const catalogs = {
|
|
|
1416
1416
|
agentCancelled: 'Cancelado. No se ha añadido ningún agente a tu perfil.',
|
|
1417
1417
|
// (3) Nombre ← detectado, editable.
|
|
1418
1418
|
agentNamePrompt: (def) => `Nombre del agente [${def}]:`,
|
|
1419
|
-
// (4) whatItDoes + humanDecides ← IA pre-redacta tras consentimiento
|
|
1419
|
+
// (4) whatItDoes + humanDecides ← IA pre-redacta tras consentimiento.
|
|
1420
1420
|
agentFieldsConsentDisclaimer:
|
|
1421
1421
|
'Para redactar un borrador con IA de qué hace tu agente y qué decides tú, se enviarán a Shakers: el nombre del agente, sus herramientas/modelo/agente padre detectados y un resumen de su definición (sus propias instrucciones).',
|
|
1422
1422
|
agentDraftingLabel: 'Redactando un borrador con IA…',
|
|
@@ -1459,7 +1459,7 @@ const catalogs = {
|
|
|
1459
1459
|
errorReasonHttp: (status) => `el servidor respondió con un error (HTTP ${status}).`,
|
|
1460
1460
|
},
|
|
1461
1461
|
superadmin: {
|
|
1462
|
-
//
|
|
1462
|
+
// Sesión de superadmin autenticada por contraseña (no-prod).
|
|
1463
1463
|
sessionIntro:
|
|
1464
1464
|
'Abre una sesión de superadmin (solo entornos no productivos): certify funcionará con CUALQUIER email en CUALQUIER repo, saltándose los gates de identidad y autoría.',
|
|
1465
1465
|
passwordPrompt: 'Contraseña de superadmin:',
|
|
@@ -1472,7 +1472,7 @@ const catalogs = {
|
|
|
1472
1472
|
sessionHint:
|
|
1473
1473
|
'Ejecuta: certify --email <cualquiera> --accept-disclaimer --skill <nombre> · Para cerrarla: superadmin --logout',
|
|
1474
1474
|
loggedOut: 'Sesión de superadmin olvidada (token local eliminado).',
|
|
1475
|
-
//
|
|
1475
|
+
// Conmutador de perfil vía superadmin: conveniencia de dev/testing — cambia entre perfil talent/external sin reinstalar.
|
|
1476
1476
|
profileMenuHeading: '¿Qué quieres hacer?',
|
|
1477
1477
|
profileMenuHint: 'Flechas ↑/↓ para moverte · enter para elegir · esc para cancelar',
|
|
1478
1478
|
profileMenuPrompt: (max) => `Número (1-${max}), vacío para cancelar: `,
|
|
@@ -1487,7 +1487,7 @@ const catalogs = {
|
|
|
1487
1487
|
profileMenuCancelled: 'Cancelado. No se ha cambiado nada.',
|
|
1488
1488
|
profileAlreadyOn: (profile) => `Ya estás en el perfil ${profile === 'talent' ? 'Talent' : 'External'}. No se ha cambiado ni purgado nada.`,
|
|
1489
1489
|
profileSwitched: (profile) => `Perfil cambiado a ${profile === 'talent' ? 'Talent' : 'External'} · historial limpiado (informe, consentimiento, sesión de talento) · efecto inmediato, sin reiniciar.`,
|
|
1490
|
-
//
|
|
1490
|
+
// Superadmin es DELIBERADAMENTE single-hop, SOLO PRIMARIO (servicio de certificaciones) — nunca hub.
|
|
1491
1491
|
queryingPrimary: (endpoint) => `Consultando Shakers: ${endpoint}`,
|
|
1492
1492
|
errorNoEndpoint:
|
|
1493
1493
|
'No hay endpoint configurado. Configura el backend (SHAKERS_CLI_INGEST_ENDPOINT o usage --set-endpoint) y reinténtalo.',
|
|
@@ -1495,7 +1495,7 @@ const catalogs = {
|
|
|
1495
1495
|
errorDisabled:
|
|
1496
1496
|
'Endpoint no disponible: la sesión de superadmin está deshabilitada fuera de entornos no productivos.',
|
|
1497
1497
|
errorGeneric: 'No se pudo abrir la sesión de superadmin. Inténtalo de nuevo.',
|
|
1498
|
-
// Inspect
|
|
1498
|
+
// Inspect — recibo de atribución de certificaciones YA guardadas.
|
|
1499
1499
|
inspectIntro:
|
|
1500
1500
|
'Audita la evidencia de autoría de las certificaciones ya guardadas (solo lectura, entornos no productivos).',
|
|
1501
1501
|
inspectEmailPrompt: 'Email cuya(s) certificación(es) quieres inspeccionar:',
|
|
@@ -1521,7 +1521,7 @@ const catalogs = {
|
|
|
1521
1521
|
// in-shell command help and messages — the commands keep their own copy.
|
|
1522
1522
|
repl: {
|
|
1523
1523
|
prompt: 'ϟ shakers ›',
|
|
1524
|
-
//
|
|
1524
|
+
// El BANNER de arranque (src/repl-shell.js) ahora es profile-aware y localizado.
|
|
1525
1525
|
bannerWelcome: 'Bienvenido a',
|
|
1526
1526
|
bannerTalentLine1: 'Completa o actualiza tu perfil de talento',
|
|
1527
1527
|
bannerTalentLine2: 'agéntico en Shakers: no solo qué sabes, sino',
|
|
@@ -1542,7 +1542,7 @@ const catalogs = {
|
|
|
1542
1542
|
bannerExternalMapDesc: 'informe LOCAL (grafo)',
|
|
1543
1543
|
bannerExternalReportDesc: 'informe HTML compartible',
|
|
1544
1544
|
bannerExternalShareDesc: 'tarjeta para LinkedIn',
|
|
1545
|
-
// FLUJO DE COMANDOS
|
|
1545
|
+
// FLUJO DE COMANDOS VOCABULARIO, y lo hereda la 083: aquí se habla de COMANDOS de la herramienta.
|
|
1546
1546
|
completeNeeds: (cmd) => `(necesita: ${cmd})`,
|
|
1547
1547
|
completeDone: '(ya ejecutado)',
|
|
1548
1548
|
completeDoneStale: (days) => `(ya ejecutado, hace ${days} días)`,
|
|
@@ -1575,7 +1575,7 @@ const catalogs = {
|
|
|
1575
1575
|
journeyDone: 'Has completado el recorrido de la herramienta: no queda ningún comando por ejecutar. Los siguientes pasos para subir tu nivel de uso de IA son otra cosa y están en `usage --roadmap`.',
|
|
1576
1576
|
goodbye: 'Hasta pronto.',
|
|
1577
1577
|
unknown: (cmd) => `Comando no reconocido: "${cmd}". Escribe "help" para ver los comandos disponibles.`,
|
|
1578
|
-
// ORDEN: lo declara src/command-graph.js
|
|
1578
|
+
// ORDEN: lo declara src/command-graph.js.
|
|
1579
1579
|
help:
|
|
1580
1580
|
'Shakers — comandos disponibles\n\n'
|
|
1581
1581
|
+ ' usage [opciones] Escanea este proyecto y tu equipo; puntúa tu setup de IA (T0-T7)\n'
|
|
@@ -1618,7 +1618,7 @@ const catalogs = {
|
|
|
1618
1618
|
toolsS: 'Clientes de IA presentes en tu entorno.',
|
|
1619
1619
|
techT: 'Tecnologías del proyecto',
|
|
1620
1620
|
techS: 'Stack reconocido en el repositorio.',
|
|
1621
|
-
//
|
|
1621
|
+
// Los SERVICIOS detrás de los MCP.
|
|
1622
1622
|
mcpT: 'Servicios conectados por MCP',
|
|
1623
1623
|
mcpS: 'Productos a los que tu IA tiene acceso.',
|
|
1624
1624
|
mcpEmpty: 'No se ha detectado ningún servidor MCP. Conectar uno es el criterio que te sube a T3 (Banco conectado).',
|
|
@@ -1626,7 +1626,7 @@ const catalogs = {
|
|
|
1626
1626
|
// 085: la pestaña decía "Skills" a secas junto a una de "Agentes", que es
|
|
1627
1627
|
// la colisión exacta que la issue nombra.
|
|
1628
1628
|
skills: 'Skills técnicas',
|
|
1629
|
-
// ---- Agentes DETECTADOS, columna izquierda
|
|
1629
|
+
// ---- Agentes DETECTADOS, columna izquierda --------------
|
|
1630
1630
|
agentsT: 'Agentes detectados',
|
|
1631
1631
|
agentsS: 'Todos los agentes que hay configurados en tu entorno. Certificar es otra cosa y está en la columna de la derecha.',
|
|
1632
1632
|
agentsEmpty: 'No se ha detectado ningún agente configurado (p. ej. en .claude/agents/). Si tienes agentes y no salen aquí, es que la herramienta no los ha encontrado, no que no cuenten.',
|
|
@@ -1642,7 +1642,7 @@ const catalogs = {
|
|
|
1642
1642
|
hereYouAre: 'Estás aquí',
|
|
1643
1643
|
noFoot: 'Aún no hay uso de IA. Ejecuta usage en este proyecto.',
|
|
1644
1644
|
noSkills: 'Aún no hay Skills técnicas certificadas. Ejecuta certify skills.',
|
|
1645
|
-
// Agent certifications were removed from the report
|
|
1645
|
+
// Agent certifications were removed from the report; the sheet's agent-cert tab, its empty state and its detected-vs-certified copy went with it.
|
|
1646
1646
|
footer: 'Informe generado localmente · Shakers',
|
|
1647
1647
|
// Template chrome that used to be hardcoded Spanish in report-sheet.html (including inside its inline <script>), so an English report shipped Spanish controls.
|
|
1648
1648
|
themeToggle: 'Cambiar tema',
|
|
@@ -1869,10 +1869,10 @@ const catalogs = {
|
|
|
1869
1869
|
t7Blocking: (n) => `To reach T7 (Orchestrated workshop) you need at least one automation hook configured — you have ${n} now.`,
|
|
1870
1870
|
},
|
|
1871
1871
|
},
|
|
1872
|
-
// Progression ladder
|
|
1872
|
+
// Progression ladder — see the es block.
|
|
1873
1873
|
ladder: {
|
|
1874
1874
|
levelsHeading: 'Maturity levels (0-4)',
|
|
1875
|
-
//
|
|
1875
|
+
// The ladder now groups tiers by SETUP LEVEL, not the 0-4 band.
|
|
1876
1876
|
setupHeading: 'Setup Level',
|
|
1877
1877
|
setupIntro:
|
|
1878
1878
|
'Your setup level (S1–S3) sums up your AI usage at a glance; the tier (T0-T7) is the '
|
|
@@ -1909,7 +1909,7 @@ const catalogs = {
|
|
|
1909
1909
|
T7: 'Orchestrated workshop: hooks automate the workshop and agents orchestrate each other.',
|
|
1910
1910
|
},
|
|
1911
1911
|
},
|
|
1912
|
-
// Agent classification + improvement tips
|
|
1912
|
+
// Agent classification + improvement tips — see the es block.
|
|
1913
1913
|
classification: {
|
|
1914
1914
|
label: 'Classification',
|
|
1915
1915
|
noCategory: 'No category',
|
|
@@ -1946,7 +1946,7 @@ const catalogs = {
|
|
|
1946
1946
|
},
|
|
1947
1947
|
},
|
|
1948
1948
|
// LEGACY 0-4 band names — kept only for older persisted reports / the
|
|
1949
|
-
// unchanged sent payload
|
|
1949
|
+
// unchanged sent payload; the report shows `setupLevels` instead.
|
|
1950
1950
|
levelNames: {
|
|
1951
1951
|
none: 'No AI usage',
|
|
1952
1952
|
exploring: 'Exploring',
|
|
@@ -1954,7 +1954,7 @@ const catalogs = {
|
|
|
1954
1954
|
power: 'Power user',
|
|
1955
1955
|
orchestrator: 'Orchestrator',
|
|
1956
1956
|
},
|
|
1957
|
-
// Setup Level (Talent Certification Framework
|
|
1957
|
+
// Setup Level (Talent Certification Framework): the 3-value rollup that REPLACES the 0-4 band on every surface.
|
|
1958
1958
|
setupLevels: {
|
|
1959
1959
|
none: {
|
|
1960
1960
|
label: 'Not certified',
|
|
@@ -1991,7 +1991,7 @@ const catalogs = {
|
|
|
1991
1991
|
brandSub: 'AI usage profile',
|
|
1992
1992
|
toolsDetected: (n, total) => `${n}/${total} tools detected`,
|
|
1993
1993
|
level: (level, name) => `Level ${level} · ${name}`,
|
|
1994
|
-
//
|
|
1994
|
+
// Setup Level shown in the top bar (replaces the 0-4 level line).
|
|
1995
1995
|
setupLevel: (label) => `Setup · ${label}`,
|
|
1996
1996
|
// Current tier appended to the top bar, next to the level (report req 1 addendum).
|
|
1997
1997
|
tierInline: (key, name) => ` · Tier ${key} · ${name}`,
|
|
@@ -2019,22 +2019,22 @@ const catalogs = {
|
|
|
2019
2019
|
environment: 'Environment',
|
|
2020
2020
|
editors: 'editors',
|
|
2021
2021
|
noEditorsDetected: 'none detected',
|
|
2022
|
-
//
|
|
2022
|
+
// Agent evaluation (terminal, one line per agent): compact usage
|
|
2023
2023
|
// signal derived from the local Claude Code history.
|
|
2024
2024
|
agentUsed: (n) => `used ${n}×`,
|
|
2025
2025
|
agentUnused: 'no local use',
|
|
2026
2026
|
agentUsageUnavailable: '(no local Claude Code history: usage unavailable)',
|
|
2027
|
-
//
|
|
2027
|
+
// Discoverability hint for the next-steps section (behind --roadmap).
|
|
2028
2028
|
roadmapHint: 'Run `usage --roadmap` to see the steps between you and the next AI-usage level. These are not steps in this tool: they are changes to how you work, over the coming weeks.',
|
|
2029
2029
|
aiProfileGenerating: 'Generating your AI profile (matrix, vision and how you work)…',
|
|
2030
2030
|
aiProfilePendingRetry: 'Your AI profile (matrix, vision and how you work) is still being generated; re-run `report` in a moment to see it.',
|
|
2031
|
-
//
|
|
2031
|
+
// Shown when a session existed and has expired. Opens
|
|
2032
2032
|
// with "Your session has expired" — see the Spanish catalog.
|
|
2033
2033
|
sessionExpiredNotice: 'Your session has expired. You are seeing the full report as a general user; run `login` to sign in again.',
|
|
2034
2034
|
nextStep: 'Next step to level up',
|
|
2035
2035
|
files: (n) => `${n} ${n === 1 ? 'file' : 'files'}`,
|
|
2036
2036
|
lastModified: (label) => `last modified: ${label}`,
|
|
2037
|
-
//
|
|
2037
|
+
// "Project technologies" is renamed "Skills" for the TALENT profile only (naming unicity with the rest of the talent surface).
|
|
2038
2038
|
skillsHeading: 'Skills',
|
|
2039
2039
|
},
|
|
2040
2040
|
html: {
|
|
@@ -2043,7 +2043,7 @@ const catalogs = {
|
|
|
2043
2043
|
h1: 'Your AI usage profile',
|
|
2044
2044
|
sub: 'A local snapshot of which AI tools you have and how deeply you have configured them.',
|
|
2045
2045
|
levelOf: (level) => `Level ${level} of 4`,
|
|
2046
|
-
//
|
|
2046
|
+
// Hero label for the Setup Level (replaces the 0-4 "Level X of 4").
|
|
2047
2047
|
setupLevelOf: 'Setup Level',
|
|
2048
2048
|
// Current tier shown in the hero bar next to the level (report req 1 addendum).
|
|
2049
2049
|
currentTier: (key, name) => `Tier ${key} · ${name}`,
|
|
@@ -2066,17 +2066,17 @@ const catalogs = {
|
|
|
2066
2066
|
agentDescriptionFromName: (name) => `"${name}" agent (no description declared in its file).`,
|
|
2067
2067
|
// AI product an agent belongs to, derived from its source (proper nouns; same es/en).
|
|
2068
2068
|
aiProducts: { 'claude-code': 'Claude Code' },
|
|
2069
|
-
//
|
|
2069
|
+
// Agent evaluation (HTML per-agent detail): definition-quality score + LLM rationale + local usage signal.
|
|
2070
2070
|
agentScoreLabel: 'Definition quality (0-100)',
|
|
2071
2071
|
agentQualityLabel: 'Why:',
|
|
2072
2072
|
agentUsageLabel: 'Local usage (Claude Code history)',
|
|
2073
2073
|
agentUsedTimes: (n) => `used ${n}×`,
|
|
2074
2074
|
agentUnused: 'no local use',
|
|
2075
|
-
// Project technologies
|
|
2075
|
+
// Project technologies. Refined: shows
|
|
2076
2076
|
// recognized FRAMEWORKS/LIBRARIES only, not a raw dependency dump.
|
|
2077
2077
|
technologiesHeading: 'Project technologies',
|
|
2078
2078
|
technologiesEmpty: 'No recognized framework or library was found in the dependency manifests (package.json, requirements.txt, go.mod, pyproject.toml).',
|
|
2079
|
-
// MCP servers by name
|
|
2079
|
+
// MCP servers by name.
|
|
2080
2080
|
mcpHeading: 'Services connected over MCP',
|
|
2081
2081
|
mcpEmpty: 'No MCP server detected. Connecting one is the criterion that takes you to T3 (Connected bench).',
|
|
2082
2082
|
mcpUnidentified: (n) => `${n} more server${n === 1 ? '' : 's'} whose service we could not identify from its name.`,
|
|
@@ -2092,10 +2092,10 @@ const catalogs = {
|
|
|
2092
2092
|
roadmapHonestyLabel: 'Honesty note',
|
|
2093
2093
|
roadmapContentUnavailable: "This level's detailed content isn't available in this language yet.",
|
|
2094
2094
|
roadmapPersonalizedNotice: 'Content adapted to your project.',
|
|
2095
|
-
//
|
|
2095
|
+
// See the Spanish catalog for why these say what was lost
|
|
2096
2096
|
// rather than what went wrong, and when they are allowed to show.
|
|
2097
2097
|
roadmapNotPersonalizedNotice: 'This roadmap is the generic one for your tier: it could not be adapted to your project this run. Run `usage` again to retry.',
|
|
2098
|
-
//
|
|
2098
|
+
// See the Spanish catalog for why the tag sits next to the
|
|
2099
2099
|
// heading instead of in a footnote.
|
|
2100
2100
|
roadmapNowLabel: 'Where you start from',
|
|
2101
2101
|
roadmapProjectionLabel: 'Where this path leaves you',
|
|
@@ -2114,9 +2114,9 @@ const catalogs = {
|
|
|
2114
2114
|
rawData: "View this report's exact data (JSON)",
|
|
2115
2115
|
},
|
|
2116
2116
|
cli: {
|
|
2117
|
-
// Reporting redesign
|
|
2117
|
+
// Reporting redesign: HTML is no longer opt-in (--html retired).
|
|
2118
2118
|
reportLink: (url) => `Open your report in your browser:\n ${url}`,
|
|
2119
|
-
// `share` command
|
|
2119
|
+
// `share` command: CLI copy wrapping the branded LinkedIn card.
|
|
2120
2120
|
share: {
|
|
2121
2121
|
help: 'share — build a branded card with your AI usage result (tier + score) to post on LinkedIn.\n'
|
|
2122
2122
|
+ ' Run `usage` first; `share` uses this project\'s latest AI usage.\n'
|
|
@@ -2166,7 +2166,7 @@ const catalogs = {
|
|
|
2166
2166
|
available: (from, to) => `A newer Shakers CLI is available: ${from} → ${to}`,
|
|
2167
2167
|
howTo: 'Run `shakers update` to upgrade.',
|
|
2168
2168
|
},
|
|
2169
|
-
// `report` command
|
|
2169
|
+
// `report` command: builds and OPENS the full, shareable HTML report for this project (AI usage + certified Skills).
|
|
2170
2170
|
report: {
|
|
2171
2171
|
help: 'report — build and open the full HTML report for this project (AI usage + certified Skills) to share with your team.\n'
|
|
2172
2172
|
+ ' Run `usage` (and optionally `certify`) first; `report` gathers their result.\n'
|
|
@@ -2198,10 +2198,10 @@ const catalogs = {
|
|
|
2198
2198
|
reposScopeAll: 'Evaluating all AI usage on this machine.',
|
|
2199
2199
|
synthesizingLabel: 'Synthesizing agents with AI…',
|
|
2200
2200
|
personalizingRoadmapLabel: 'Personalizing roadmap…',
|
|
2201
|
-
//
|
|
2201
|
+
// Agent definition-quality evaluation (ephemeral LLM call).
|
|
2202
2202
|
evaluatingAgentsLabel: 'Evaluating your agents’ quality…',
|
|
2203
2203
|
buildNextLevelHint: 'Alternatively, run `usage --build-next-level` to generate the starter file directly in your project.',
|
|
2204
|
-
// Localized help
|
|
2204
|
+
// Localized help: previously hardcoded Spanish in bin/report.js; now routed through i18n so it respects the machine locale.
|
|
2205
2205
|
help:
|
|
2206
2206
|
'\nShakers — local profile of your AI-tool usage\n\n'
|
|
2207
2207
|
+ 'Usage:\n usage [options]\n\n'
|
|
@@ -2236,7 +2236,7 @@ const catalogs = {
|
|
|
2236
2236
|
+ 'file (--set-endpoint) > none. Without an endpoint, the report is shown but not sent\n'
|
|
2237
2237
|
+ 'to Shakers.\n',
|
|
2238
2238
|
},
|
|
2239
|
-
// Cumulative report
|
|
2239
|
+
// Cumulative report — English mirror.
|
|
2240
2240
|
cumulative: {
|
|
2241
2241
|
title: 'Your Shakers report',
|
|
2242
2242
|
privacyNote: 'This report is generated and stored only on your machine. Nothing is sent to Shakers unless you give explicit consent.',
|
|
@@ -2252,12 +2252,12 @@ const catalogs = {
|
|
|
2252
2252
|
noFileTarget: "The next step isn't a file this command can create — check the roadmap snippet in the report.",
|
|
2253
2253
|
unrecognizedTier: "Couldn't determine your current tier.",
|
|
2254
2254
|
},
|
|
2255
|
-
//
|
|
2255
|
+
// Mirrors the es catalog's `legalNotice` — see its comment.
|
|
2256
2256
|
legalNotice: {
|
|
2257
2257
|
label: 'LEGAL NOTICE',
|
|
2258
2258
|
},
|
|
2259
2259
|
consent: {
|
|
2260
|
-
//
|
|
2260
|
+
// The disclosure wall (itemized sends / never sends) is RETIRED from the CLI — that content now lives in the repo's README.
|
|
2261
2261
|
persistIntro:
|
|
2262
2262
|
'This report has already been generated and shown on your machine, '
|
|
2263
2263
|
+ 'always. Saving it in Shakers is optional and revocable at any '
|
|
@@ -2284,11 +2284,11 @@ const catalogs = {
|
|
|
2284
2284
|
savedUnderEmail: (email) => `The report will be saved under: ${email}`,
|
|
2285
2285
|
invalidEmail: 'Invalid email, try again.',
|
|
2286
2286
|
notObtained: "Couldn't record your answer; you'll be asked again next time.",
|
|
2287
|
-
//
|
|
2287
|
+
// This question is now asked BEFORE any AI/egress call (agent-synthesis, agent-evaluation, roadmap personalization), not after.
|
|
2288
2288
|
noReportWithoutConsent: 'Without your consent, this report will not include AI-generated synthesis, evaluation, or roadmap this time (the rest of the report is shown as usual). Run `usage` again and accept to include them, or use --consent-reset if you want to be asked again.',
|
|
2289
2289
|
deniedSaved: 'Understood, nothing will be saved. You can change your mind later by running the command again.',
|
|
2290
2290
|
grantedSaved: (email) => `Thanks. From now on this report will be saved in Shakers automatically (email: ${email}, max. once per hour).`,
|
|
2291
|
-
//
|
|
2291
|
+
// A logged-in Talent is NEVER asked for an email (their account already proves identity).
|
|
2292
2292
|
noSessionEmail: "There's no email on file for your session yet, so this report can't be saved this time. You'll be asked again next run.",
|
|
2293
2293
|
skipAlreadyDecided: (decision, path) =>
|
|
2294
2294
|
`Consent already answered (${decision}) — stored at ${path}. `
|
|
@@ -2321,7 +2321,7 @@ const catalogs = {
|
|
|
2321
2321
|
showConfigFile: (url, path) => `Effective ingest endpoint: ${url}\n Source: config file (${path}).`,
|
|
2322
2322
|
showConfigInvalid: (path) => `The config file (${path}) has an invalid or insecure endpoint; it is ignored. Fix it with usage --set-endpoint <url>.`,
|
|
2323
2323
|
showNone: 'No ingest endpoint configured. Set SHAKERS_CLI_INGEST_ENDPOINT or use usage --set-endpoint <url>. Without it, the report is still shown but not sent to Shakers.',
|
|
2324
|
-
//
|
|
2324
|
+
// The CLI now talks to a CHAIN of two backends — PRIMARY (certifications service, above) and FALLBACK (hub-backend, here).
|
|
2325
2325
|
showFallbackRetired: 'Note: your config.json still has `ingestEndpointFallback`. It is no longer used: the CLI talks to a single backend. You can delete that line by hand; leaving it changes nothing.',
|
|
2326
2326
|
confirmHostPrompt: (host) => `The host "${host}" is not localhost or a known Shakers domain. If you continue, your sampled code and AI signals will be sent there.\n Type the exact hostname to confirm (leave blank to cancel):`,
|
|
2327
2327
|
confirmHostMismatch: "That didn't match the hostname shown. Cancelled: nothing was saved.",
|
|
@@ -2355,7 +2355,7 @@ const catalogs = {
|
|
|
2355
2355
|
}
|
|
2356
2356
|
},
|
|
2357
2357
|
},
|
|
2358
|
-
// Email-ownership verification
|
|
2358
|
+
// Email-ownership verification: the OTP "wait mode" copy, shared by both binaries.
|
|
2359
2359
|
verify: {
|
|
2360
2360
|
sent: (email) => `We sent a verification code to ${email}.`,
|
|
2361
2361
|
waitHint: 'Paste the code here. Press "r" then Enter to resend it, or Enter on a blank line to cancel.',
|
|
@@ -2371,7 +2371,7 @@ const catalogs = {
|
|
|
2371
2371
|
cancelled: 'Verification cancelled. The report will not be saved (it has already been shown to you).',
|
|
2372
2372
|
unavailable: 'Email verification is not available right now; the report will not be saved (it has already been shown to you).',
|
|
2373
2373
|
},
|
|
2374
|
-
// Skill Code Certification
|
|
2374
|
+
// Skill Code Certification —
|
|
2375
2375
|
// English mirror of the `certify` catalog. Same content/invariants.
|
|
2376
2376
|
certifyDimension: {
|
|
2377
2377
|
help:
|
|
@@ -2787,7 +2787,7 @@ const catalogs = {
|
|
|
2787
2787
|
partialSampleWarning:
|
|
2788
2788
|
'Partial sample: due to size limits the assessment is based on a sample of the code, '
|
|
2789
2789
|
+ 'not the whole project.',
|
|
2790
|
-
//
|
|
2790
|
+
// Skill levels (by decision power, NOT points) — replace the
|
|
2791
2791
|
// numeric grade in the skill output. `key` from skillLevelForScore.
|
|
2792
2792
|
levelLine: (label) => `Level: ${label}`,
|
|
2793
2793
|
skillLevels: {
|
|
@@ -2796,7 +2796,7 @@ const catalogs = {
|
|
|
2796
2796
|
expert: 'Expert',
|
|
2797
2797
|
na: '—',
|
|
2798
2798
|
},
|
|
2799
|
-
//
|
|
2799
|
+
// Rubric dimensions.
|
|
2800
2800
|
dimensionsLabel: 'Dimensions',
|
|
2801
2801
|
dimensionNA: 'N/A',
|
|
2802
2802
|
dimensionLabels: {
|
|
@@ -2808,7 +2808,7 @@ const catalogs = {
|
|
|
2808
2808
|
},
|
|
2809
2809
|
rationaleLabel: 'Why',
|
|
2810
2810
|
improvementsLabel: 'Suggested improvements',
|
|
2811
|
-
//
|
|
2811
|
+
// Authorship receipt (attribution, NOT cryptographic proof).
|
|
2812
2812
|
receipt: {
|
|
2813
2813
|
label: 'Authorship',
|
|
2814
2814
|
repoLabel: 'Repo',
|
|
@@ -2846,7 +2846,7 @@ const catalogs = {
|
|
|
2846
2846
|
remediationCopiedLabel: 'Copied ✓',
|
|
2847
2847
|
},
|
|
2848
2848
|
},
|
|
2849
|
-
// Branded mini-shell chrome
|
|
2849
|
+
// Branded mini-shell chrome.
|
|
2850
2850
|
login: {
|
|
2851
2851
|
intro: 'Log in with your Shakers email and password.',
|
|
2852
2852
|
sessionExpiredIntro: 'Your previous session expired. Log in again.',
|
|
@@ -2867,7 +2867,7 @@ const catalogs = {
|
|
|
2867
2867
|
errorNoEndpoint: 'No endpoint configured. login uses the same base as usage: set SHAKERS_CLI_INGEST_ENDPOINT or use `usage --set-endpoint <url>`.',
|
|
2868
2868
|
errorPersist: 'Login succeeded, but the session could not be saved to disk. Check the permissions of ~/.config/shakers and try again.',
|
|
2869
2869
|
errorGeneric: 'Could not log in. Try again.',
|
|
2870
|
-
//
|
|
2870
|
+
// Google login by loopback (`login --google`).
|
|
2871
2871
|
googleIntro: 'Log in with Google. Your browser will open to authorize; when you are done, come back here.',
|
|
2872
2872
|
googleOpening: 'Opening your browser to log in with Google…',
|
|
2873
2873
|
googlePasteUrl: 'If your browser does not open on its own, paste this URL into it:',
|
|
@@ -2898,7 +2898,7 @@ const catalogs = {
|
|
|
2898
2898
|
selectHint: 'Arrows ↑/↓ to move · enter to pick · esc to cancel',
|
|
2899
2899
|
chooseMethodPrompt: (max) => `Number (1-${max}), empty to cancel: `,
|
|
2900
2900
|
},
|
|
2901
|
-
// `start
|
|
2901
|
+
// `start`: the tool for a talent ALREADY registered in Shakers who wants to complete their agentic profile.
|
|
2902
2902
|
start: {
|
|
2903
2903
|
help:
|
|
2904
2904
|
'start — complete your agentic talent profile in Shakers: log in, run the AI-usage\n'
|
|
@@ -2922,16 +2922,16 @@ const catalogs = {
|
|
|
2922
2922
|
menuHint: 'Arrows ↑/↓ to move · enter to pick · esc to cancel',
|
|
2923
2923
|
menuPrompt: (max) => `Number (1-${max}), empty to cancel: `,
|
|
2924
2924
|
menuRerun: 'Run the AI-usage evaluation again',
|
|
2925
|
-
//
|
|
2925
|
+
// Renamed — the label said "Add" but the action is declaring/uploading what was DETECTED to the Shakers profile, not creating something new from scratch.
|
|
2926
2926
|
menuAddSkills: 'Upload skills to profile',
|
|
2927
2927
|
menuAddAgents: 'Upload agents to profile',
|
|
2928
|
-
//
|
|
2928
|
+
// "Add project to portfolio" — grouped with skills/agents, before certifying (declare things on your profile, then certify them).
|
|
2929
2929
|
menuAddPortfolio: 'Add project to portfolio',
|
|
2930
2930
|
menuCertifySkills: 'Certify skills',
|
|
2931
2931
|
menuCertifyAgents: 'Certify agents',
|
|
2932
2932
|
menuExit: 'Exit',
|
|
2933
2933
|
menuExitDesc: 'Ends this `start` session. Run it again whenever you want to keep completing your profile.',
|
|
2934
|
-
// Per-option descriptions
|
|
2934
|
+
// Per-option descriptions: shown ONLY for the HIGHLIGHTED item in the interactive picker (or compactly in the numbered fallback) — never all at once.
|
|
2935
2935
|
menuRerunDesc:
|
|
2936
2936
|
'Re-scans your AI setup and recomputes your AI fluency. You get your updated position on the map (Explorer → AI Native) on your profile.',
|
|
2937
2937
|
menuAddSkillsDesc:
|
|
@@ -2945,7 +2945,7 @@ const catalogs = {
|
|
|
2945
2945
|
menuCertifyAgentsDesc:
|
|
2946
2946
|
'A challenge validates the agent is real, is yours, and you run it with judgment. You get the agent Certified with its traction → the strongest signal of your agentic profile.',
|
|
2947
2947
|
menuCancelled: 'Cancelled. Nothing was done.',
|
|
2948
|
-
//
|
|
2948
|
+
// Closes the menu LOOP — used both when "Exit" is explicitly chosen and when cancelling (esc / empty answer) FROM INSIDE the loop.
|
|
2949
2949
|
menuGoodbye: '`start` session ended. Run `start` again whenever you want to keep completing your profile.',
|
|
2950
2950
|
addAgentsComingSoon:
|
|
2951
2951
|
"Add agents: coming soon. Your agents will become assets of your agentic profile — that record doesn't exist in Shakers yet, so there's nowhere to save them for now.",
|
|
@@ -2964,7 +2964,7 @@ const catalogs = {
|
|
|
2964
2964
|
addSkillsNoneChosen: 'No skill was chosen. Nothing was added to your profile.',
|
|
2965
2965
|
addSkillsDeclaredOne: (skillName) => `✓ Added to your profile: ${skillName} (unverified).`,
|
|
2966
2966
|
addSkillsDeclareFailed: (skillName, reason) => `✗ Could not add ${skillName}: ${reason}`,
|
|
2967
|
-
// Vision close
|
|
2967
|
+
// Vision close: ONCE, after the batch — not repeated per skill (the same line repeated per item is noise, not reinforcement).
|
|
2968
2968
|
addSkillsProfileBoost: 'Every skill you add counts toward your profile: you show up in more searches.',
|
|
2969
2969
|
addSkillsHubSessionExpired: 'Your Shakers session expired while we were adding your skills.',
|
|
2970
2970
|
addSkillsOfferRelogin: 'Do you want to log in again now to continue? (y/n):',
|
|
@@ -2979,7 +2979,7 @@ const catalogs = {
|
|
|
2979
2979
|
addSkillsRelateSkipped: (skillName) => `"${skillName}" added without a relation.`,
|
|
2980
2980
|
addSkillsRelated: (skillName, portfolioName) => ` ✓ "${skillName}" related to "${portfolioName}".`,
|
|
2981
2981
|
addSkillsRelateFailed: (skillName, portfolioName, reason) => ` ✗ Could not relate "${skillName}" to "${portfolioName}": ${reason}`,
|
|
2982
|
-
//
|
|
2982
|
+
// "Add project to portfolio".
|
|
2983
2983
|
portfolioIntro:
|
|
2984
2984
|
"Let's add this project to your Shakers portfolio. Most of the data is pre-filled from your code and your git history: confirm or edit each one.",
|
|
2985
2985
|
portfolioErrorNoEndpoint:
|
|
@@ -2991,7 +2991,7 @@ const catalogs = {
|
|
|
2991
2991
|
portfolioDuplicateName: (name) => `You already have a project named "${name}" in your portfolio. No duplicate was created — run this option again with a different title if you want to add a distinct one.`,
|
|
2992
2992
|
// (1) Title ← directory name, editable.
|
|
2993
2993
|
portfolioTitlePrompt: (def) => `Project title [${def}]:`,
|
|
2994
|
-
// (2) Type ← PORTFOLIO/EXPERIENCE, obligatorio. Vision copy
|
|
2994
|
+
// (2) Type ← PORTFOLIO/EXPERIENCE, obligatorio. Vision copy:
|
|
2995
2995
|
// what each type means for your profile, shown ONLY on highlight.
|
|
2996
2996
|
portfolioTypeHeading: 'What type of entry is this?',
|
|
2997
2997
|
portfolioTypeHint: 'Arrows ↑/↓ to move · enter to pick · esc to cancel',
|
|
@@ -3002,7 +3002,7 @@ const catalogs = {
|
|
|
3002
3002
|
portfolioTypeExperience: 'Experience',
|
|
3003
3003
|
portfolioTypeExperienceDesc:
|
|
3004
3004
|
"Adds it to your profile as professional experience (freelance or in-house): counts toward your track record, not as a piece to show.",
|
|
3005
|
-
// (3) Description ← AI pre-drafts after consent
|
|
3005
|
+
// (3) Description ← AI pre-drafts after consent.
|
|
3006
3006
|
portfolioDescriptionConsentDisclaimer:
|
|
3007
3007
|
'To draft a description with AI, this will send to Shakers: the project name, the detected technologies, and — if present — the README content and the package.json description.',
|
|
3008
3008
|
portfolioDescriptionDraftLabel: 'AI-drafted description:',
|
|
@@ -3031,8 +3031,8 @@ const catalogs = {
|
|
|
3031
3031
|
portfolioRelaunchAfterRelogin: 'Session renewed. Retrying adding the project to your portfolio.',
|
|
3032
3032
|
portfolioRelaunchDeclined: 'OK. Run `login` and pick "Add project to portfolio" again whenever you want.',
|
|
3033
3033
|
portfolioReloginFailed: 'Could not log in again. The project was not added to your portfolio.',
|
|
3034
|
-
//
|
|
3035
|
-
// portfolio
|
|
3034
|
+
// "Add agent to profile". Same model as the
|
|
3035
|
+
// portfolio: AI pre-drafts, the talent edits.
|
|
3036
3036
|
agentErrorNoEndpoint:
|
|
3037
3037
|
'No endpoint configured. `start` uses the same base as `usage`: set the endpoint with `usage --set-endpoint <url>` (or SHAKERS_CLI_INGEST_ENDPOINT).',
|
|
3038
3038
|
agentNoHubToken:
|
|
@@ -3053,7 +3053,7 @@ const catalogs = {
|
|
|
3053
3053
|
agentCancelled: 'Cancelled. No agent was added to your profile.',
|
|
3054
3054
|
// (3) Name ← detected, editable.
|
|
3055
3055
|
agentNamePrompt: (def) => `Agent name [${def}]:`,
|
|
3056
|
-
// (4) whatItDoes + humanDecides ← AI pre-drafts after consent
|
|
3056
|
+
// (4) whatItDoes + humanDecides ← AI pre-drafts after consent.
|
|
3057
3057
|
agentFieldsConsentDisclaimer:
|
|
3058
3058
|
"To draft what your agent does and what you decide with AI, this will send to Shakers: the agent name, its detected tools/model/parent, and a summary of its definition (its own instructions).",
|
|
3059
3059
|
agentDraftingLabel: 'Drafting with AI…',
|
|
@@ -3069,7 +3069,7 @@ const catalogs = {
|
|
|
3069
3069
|
agentDeclaredSuccess: (name) => `✓ "${name}" added to your profile.`,
|
|
3070
3070
|
agentDeclareFailed: (reason) => `✗ Could not add the agent to your profile: ${reason}`,
|
|
3071
3071
|
agentHubSessionExpired: 'Your Shakers session expired while we were adding the agent to your profile.',
|
|
3072
|
-
//
|
|
3072
|
+
// AFTER the agent is declared, offer to relate it to the experiences/projects the talent already declared (portfolioId only).
|
|
3073
3073
|
agentRelateNoPortfolios: "You don't have any experiences in your profile yet, so the agent was added without a relation. Add one with \"Add project to portfolio\" and relate it later.",
|
|
3074
3074
|
agentRelateAsk: (agentName) => `Do you want to relate "${agentName}" to any of your experiences? (y/n):`,
|
|
3075
3075
|
agentRelateSelectHeading: (agentName) => `Relate "${agentName}" to one or more experiences:`,
|
|
@@ -3096,7 +3096,7 @@ const catalogs = {
|
|
|
3096
3096
|
},
|
|
3097
3097
|
errorReasonHttp: (status) => `the server answered with an error (HTTP ${status}).`,
|
|
3098
3098
|
},
|
|
3099
|
-
//
|
|
3099
|
+
// Password-authenticated superadmin SESSION (NON-PROD only).
|
|
3100
3100
|
superadmin: {
|
|
3101
3101
|
sessionIntro:
|
|
3102
3102
|
'Open a superadmin session (non-production environments only): certify will run against ANY email on ANY repo, bypassing the identity and authorship gates.',
|
|
@@ -3110,7 +3110,7 @@ const catalogs = {
|
|
|
3110
3110
|
sessionHint:
|
|
3111
3111
|
'Run: certify --email <anyone> --accept-disclaimer --skill <name> · To end it: superadmin --logout',
|
|
3112
3112
|
loggedOut: 'Superadmin session forgotten (local token removed).',
|
|
3113
|
-
//
|
|
3113
|
+
// Profile switch via superadmin: a dev/testing convenience — flips between the talent/ external profile without reinstalling.
|
|
3114
3114
|
profileMenuHeading: 'What do you want to do?',
|
|
3115
3115
|
profileMenuHint: 'Arrows ↑/↓ to move · enter to pick · esc to cancel',
|
|
3116
3116
|
profileMenuPrompt: (max) => `Number (1-${max}), empty to cancel: `,
|
|
@@ -3125,7 +3125,7 @@ const catalogs = {
|
|
|
3125
3125
|
profileMenuCancelled: 'Cancelled. Nothing was changed.',
|
|
3126
3126
|
profileAlreadyOn: (profile) => `You are already on the ${profile === 'talent' ? 'Talent' : 'External'} profile. Nothing was changed or purged.`,
|
|
3127
3127
|
profileSwitched: (profile) => `Profile switched to ${profile === 'talent' ? 'Talent' : 'External'} · history cleared (report, consent, talent session) · takes effect immediately, no restart needed.`,
|
|
3128
|
-
//
|
|
3128
|
+
// Superadmin is DELIBERATELY single-hop, PRIMARY (certifications service) ONLY — never hub.
|
|
3129
3129
|
queryingPrimary: (endpoint) => `Querying Shakers: ${endpoint}`,
|
|
3130
3130
|
errorNoEndpoint:
|
|
3131
3131
|
'No endpoint configured. Set the backend (SHAKERS_CLI_INGEST_ENDPOINT or usage --set-endpoint) and retry.',
|
|
@@ -3133,7 +3133,7 @@ const catalogs = {
|
|
|
3133
3133
|
errorDisabled:
|
|
3134
3134
|
'Endpoint unavailable: the superadmin session is disabled outside non-production environments.',
|
|
3135
3135
|
errorGeneric: 'Could not open the superadmin session. Try again.',
|
|
3136
|
-
// Inspect
|
|
3136
|
+
// Inspect — attribution receipt for ALREADY-stored certifications.
|
|
3137
3137
|
inspectIntro:
|
|
3138
3138
|
'Audit the authorship evidence of already-stored certifications (read-only, non-production).',
|
|
3139
3139
|
inspectEmailPrompt: 'Email whose certification(s) to inspect:',
|
|
@@ -3158,7 +3158,7 @@ const catalogs = {
|
|
|
3158
3158
|
// `shakers` REPL is the single entrypoint; this covers the prompt, the in-shell command help and messages — the commands keep their own copy.
|
|
3159
3159
|
repl: {
|
|
3160
3160
|
prompt: 'ϟ shakers ›',
|
|
3161
|
-
//
|
|
3161
|
+
// The startup BANNER (src/repl-shell.js) is now profile-aware and localized.
|
|
3162
3162
|
bannerWelcome: 'Welcome to',
|
|
3163
3163
|
bannerTalentLine1: 'Complete or update your agentic talent',
|
|
3164
3164
|
bannerTalentLine2: "profile on Shakers: it's not just what you know,",
|
|
@@ -3178,7 +3178,7 @@ const catalogs = {
|
|
|
3178
3178
|
bannerExternalMapDesc: 'LOCAL report (graph)',
|
|
3179
3179
|
bannerExternalReportDesc: 'shareable HTML report',
|
|
3180
3180
|
bannerExternalShareDesc: 'card for LinkedIn',
|
|
3181
|
-
// COMMAND FLOW
|
|
3181
|
+
// COMMAND FLOW VOCABULARY: this is about the tool's COMMANDS.
|
|
3182
3182
|
completeNeeds: (cmd) => `(needs: ${cmd})`,
|
|
3183
3183
|
completeDone: '(already run)',
|
|
3184
3184
|
completeDoneStale: (days) => `(already run, ${days} days ago)`,
|
|
@@ -3207,7 +3207,7 @@ const catalogs = {
|
|
|
3207
3207
|
journeyDone: 'You have completed the tool\u2019s flow: there is no command left to run. The next steps for raising your AI-usage level are a different thing, and they live in `usage --roadmap`.',
|
|
3208
3208
|
goodbye: 'See you soon.',
|
|
3209
3209
|
unknown: (cmd) => `Unknown command: "${cmd}". Type "help" to list the available commands.`,
|
|
3210
|
-
// ORDER: declared by src/command-graph.js
|
|
3210
|
+
// ORDER: declared by src/command-graph.js.
|
|
3211
3211
|
help:
|
|
3212
3212
|
'Shakers — available commands\n\n'
|
|
3213
3213
|
+ ' usage [options] Scan this project + your machine; score your AI setup (T0-T7)\n'
|
|
@@ -3250,7 +3250,7 @@ const catalogs = {
|
|
|
3250
3250
|
toolsS: 'AI clients present in your environment.',
|
|
3251
3251
|
techT: 'Project technologies',
|
|
3252
3252
|
techS: 'Stack recognized in the repository.',
|
|
3253
|
-
//
|
|
3253
|
+
// See the Spanish catalog for why the service is shown and the
|
|
3254
3254
|
// server name never is, and why the empty state carries the T3 criterion.
|
|
3255
3255
|
mcpT: 'Services connected over MCP',
|
|
3256
3256
|
mcpS: 'Products your AI has access to.',
|
|
@@ -3259,7 +3259,7 @@ const catalogs = {
|
|
|
3259
3259
|
// 085: the tab said a bare "Skills" next to an "Agents" one, which is the
|
|
3260
3260
|
// exact collision the issue names.
|
|
3261
3261
|
skills: 'Technical Skills',
|
|
3262
|
-
// ---- DETECTED agents, left column
|
|
3262
|
+
// ---- DETECTED agents, left column -----------------------
|
|
3263
3263
|
agentsT: 'Detected agents',
|
|
3264
3264
|
agentsS: 'Every agent configured in your environment. Certifying is a different thing, and it lives in the right-hand column.',
|
|
3265
3265
|
agentsEmpty: 'No configured agent detected (e.g. under .claude/agents/). If you have agents and they are not here, the tool did not find them — it is not that they do not count.',
|
|
@@ -3275,7 +3275,7 @@ const catalogs = {
|
|
|
3275
3275
|
hereYouAre: 'You are here',
|
|
3276
3276
|
noFoot: 'No AI usage yet. Run usage in this project.',
|
|
3277
3277
|
noSkills: 'No certified technical Skills yet. Run certify skills.',
|
|
3278
|
-
// Agent certifications were removed from the report
|
|
3278
|
+
// Agent certifications were removed from the report; the sheet's agent-cert tab, its empty state and its detected-vs-certified copy went with it.
|
|
3279
3279
|
footer: 'Report generated locally · Shakers',
|
|
3280
3280
|
themeToggle: 'Toggle theme',
|
|
3281
3281
|
themeDark: 'Dark',
|
|
@@ -3333,7 +3333,7 @@ function tierName(tierKey, lang) {
|
|
|
3333
3333
|
return (names && names[tierKey]) || tierKey;
|
|
3334
3334
|
}
|
|
3335
3335
|
|
|
3336
|
-
// Defensive i18n lookup
|
|
3336
|
+
// Defensive i18n lookup.
|
|
3337
3337
|
function label(value, fallback) {
|
|
3338
3338
|
return typeof value === 'string' && value ? value : fallback;
|
|
3339
3339
|
}
|