@prettifystudio/lyngo-cli 0.2.0 → 0.2.2

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.
Files changed (3) hide show
  1. package/README.md +6 -4
  2. package/bin/lyngo +20 -4
  3. package/package.json +1 -1
package/README.md CHANGED
@@ -65,12 +65,14 @@ Configuration: `LYNGO_HOST` (default `https://lyngo.app`), `LYNGO_TOKEN`
65
65
 
66
66
  ## The Claude Code plugin (optional)
67
67
 
68
- This repository is also a Claude Code plugin. It adds the `/lyngo:localize`
69
- command and the `lyngo-i18n` skill, which makes the agent check existing keys
70
- before it writes new text. It needs the `lyngo` command from npm.
68
+ This repository is also a Claude Code plugin. It adds the commands
69
+ `/lyngo:init`, `/lyngo:localize`, `/lyngo:status` and `/lyngo:login`, and the
70
+ `lyngo-i18n` skill, which makes the agent check existing keys before it writes
71
+ new text. It needs the `lyngo` command from npm; `lyngo init` prints these two
72
+ lines when the plugin is not installed yet.
71
73
 
72
74
  ```bash
73
- claude plugin marketplace add <owner>/lyngo-claude-plugin
75
+ claude plugin marketplace add prettifystudio/lyngo-claude-plugin
74
76
  claude plugin install lyngo@lyngo
75
77
  ```
76
78
 
package/bin/lyngo CHANGED
@@ -28,7 +28,10 @@ const TOKEN_DIR = path.join(os.homedir(), '.config', 'lyngo');
28
28
  const TOKEN_FILE = path.join(TOKEN_DIR, 'token');
29
29
  // Milliseconds per protocol second. Tests shrink it; people never set it.
30
30
  const TICK = Number(process.env.LYNGO_TICK_MS) > 0 ? Number(process.env.LYNGO_TICK_MS) : 1000;
31
- const HOOK_COMMAND = 'lyngo localize 2>&1 | tail -20';
31
+ // The Stop hook says so when the CLI is not on PATH, instead of a "command not
32
+ // found" that scrolls past unread (corp1 setup, 2026-10-18).
33
+ const HOOK_COMMAND = 'if command -v lyngo >/dev/null 2>&1; then lyngo localize 2>&1 | tail -20; else echo "lyngo: the CLI is not on PATH. Install it: npm i -g @prettifystudio/lyngo-cli"; fi';
34
+ const OLD_HOOK_COMMANDS = ['lyngo localize 2>&1 | tail -20'];
32
35
  const SRC = /\.(blade\.php|php|tsx|jsx|ts|js|vue|svelte)$/;
33
36
  const SKIP = /(^|\/)(vendor|node_modules|tests?|database|storage|bootstrap|public|config|\.git)\//;
34
37
 
@@ -340,9 +343,15 @@ function setUpClaudeCode(top, remote) {
340
343
  settings.hooks = settings.hooks || {};
341
344
  const stop = Array.isArray(settings.hooks.Stop) ? settings.hooks.Stop : [];
342
345
  const has = stop.some((group) => (group.hooks || []).some((h) => typeof h.command === 'string' && /\blyngo\b[^|]*\blocalize\b/.test(h.command)));
346
+ let upgraded = false;
347
+ for (const group of stop) for (const h of group.hooks || []) {
348
+ if (OLD_HOOK_COMMANDS.includes(h.command)) { h.command = HOOK_COMMAND; upgraded = true; }
349
+ }
343
350
  if (!has) {
344
351
  stop.push({ hooks: [{ type: 'command', command: HOOK_COMMAND }] });
345
352
  settings.hooks.Stop = stop;
353
+ }
354
+ if (!has || upgraded) {
346
355
  fs.mkdirSync(dir, { recursive: true });
347
356
  fs.writeFileSync(file, JSON.stringify(settings, null, 2) + '\n');
348
357
  }
@@ -358,6 +367,11 @@ function setUpClaudeCode(top, remote) {
358
367
  }
359
368
  }
360
369
  console.log(`Claude Code: the lyngo MCP server is registered for this repository, and the Stop hook ${has ? 'was already' : 'is'} in .claude/settings.local.json.`);
370
+ // The slash commands (/lyngo:localize, /lyngo:init, /lyngo:status) come
371
+ // from the plugin; say how to get it when it is not installed yet.
372
+ let installed = false;
373
+ try { installed = /\blyngo\b/.test(run(['plugin', 'list'])); } catch { /* no plugin support, or none installed */ }
374
+ if (!installed) console.log('Slash commands for Claude Code (/lyngo:localize, /lyngo:init, /lyngo:status): claude plugin marketplace add prettifystudio/lyngo-claude-plugin && claude plugin install lyngo@lyngo');
361
375
  }
362
376
 
363
377
  async function init(opts) {
@@ -384,9 +398,11 @@ async function init(opts) {
384
398
  console.log(`Detected: ${detected.summary || 'no i18n setup found'}`);
385
399
  if (detected.i18n) project = { ...project, i18n: detected.i18n };
386
400
 
401
+ // The agent setup comes before the language question: a run that stops
402
+ // there still leaves the hook and the MCP server in place (corp1, 2026-10-18).
403
+ setUpClaudeCode(top, remote);
387
404
  project = await chooseLanguages(project, opts);
388
405
  await scaffold(project);
389
- setUpClaudeCode(top, remote);
390
406
  await fillMissingCatalogs(project, opts);
391
407
  console.log('Done. Build as usual; lyngo localize runs when your agent finishes, or run it yourself before committing.');
392
408
  }
@@ -452,10 +468,10 @@ async function translateLanguage(code, project) {
452
468
  fs.writeFileSync(targetPath, out.content);
453
469
  const l = (r.report && r.report.languages && r.report.languages[code]) || {};
454
470
  translated += l.translated || 0; memory += l.from_memory || 0; flagged.push(...(l.flagged || []));
455
- process.stdout.write(`\r${code}: ${Math.min(i + 100, missing.length)}/${missing.length}`);
471
+ if (process.stdout.isTTY) process.stdout.write(`\r${code}: ${Math.min(i + 100, missing.length)}/${missing.length}`);
456
472
  }
457
473
  const flaggedText = flagged.length ? `; ${flagged.length} flagged for review: ${flagged.slice(0, 3).map((x) => JSON.stringify(x.key || x)).join(', ')}` : '';
458
- console.log(`\r${code}: ${translated} translated, ${memory} from memory${flaggedText} -> ${targetPath}`);
474
+ console.log(`${process.stdout.isTTY ? '\r' : ''}${code}: ${translated} translated, ${memory} from memory${flaggedText} -> ${targetPath}`);
459
475
  }
460
476
 
461
477
  // ── onboard: the "copy this into your agent" path ──────────────────────────
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@prettifystudio/lyngo-cli",
3
- "version": "0.2.0",
3
+ "version": "0.2.2",
4
4
  "description": "Localization for Laravel applications, from the terminal: Lyngo wraps user-facing text with your framework's i18n call, reuses your project's keys, translates and verifies the catalogs. Blade, Livewire, PHP, and Inertia with React, Vue or Svelte.",
5
5
  "bin": {
6
6
  "lyngo": "bin/lyngo"