natureco-cli 5.61.0 → 5.63.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.
@@ -1,5 +1,7 @@
1
1
  const chalk = require('chalk');
2
2
  const crypto = require('crypto');
3
+ const { getLang: _gl } = require('../utils/i18n');
4
+ const L = (tr, en) => (_gl() === 'en' ? en : tr);
3
5
  const qrcode = require('qrcode-terminal');
4
6
 
5
7
  function qr(args) {
@@ -48,8 +50,8 @@ function showQR(data) {
48
50
 
49
51
  function generateQR(text) {
50
52
  if (!text) {
51
- console.log(chalk.red('\n ❌ QR için veri gerekli\n'));
52
- console.log(chalk.gray(' Örnek: natureco qr generate "https://natureco.me/pair?code=ABC"\n'));
53
+ console.log(chalk.red(L('\n ❌ QR için veri gerekli\n', '\n ❌ Data required for QR\n')));
54
+ console.log(chalk.gray(L(' Örnek: natureco qr generate "https://natureco.me/pair?code=ABC"\n', ' Example: natureco qr generate "https://natureco.me/pair?code=ABC"\n')));
53
55
  process.exit(1);
54
56
  }
55
57
  console.log(chalk.cyan('\n 📱 QR: ') + chalk.white(text) + '\n');
@@ -46,8 +46,8 @@ function extractPreferenceFacts(content) {
46
46
  }
47
47
  return out;
48
48
  }
49
- const chalk = require('chalk');
50
- const { getLang: _getLang } = require('../utils/i18n');
49
+ const chalk = require('chalk');
50
+ const { getLang: _getLang } = require('../utils/i18n');
51
51
  const L = (tr, en) => (_getLang() === 'en' ? en : tr);
52
52
  const tui = require('../utils/tui');
53
53
  const { loadToolDefinitions, toOpenAIFormat, executeTool } = require('../utils/tools');
@@ -132,22 +132,22 @@ const guardrails = new ToolGuardrails();
132
132
 
133
133
  // CLI komutları (REPL içinden çalıştırılabilir)
134
134
  const CLI_COMMANDS = {
135
- '/doctor': { desc: 'Sistem sağlığı kontrolü', run: ['doctor'] },
136
- '/cost': { desc: 'Maliyet takibi (today|week|month|budget)', run: ['cost', 'today'] },
137
- '/audit': { desc: 'Audit log (today|stats|files)', run: ['audit', 'stats'] },
138
- '/team': { desc: 'Multi-agent (list|status)', run: ['team', 'list'] },
139
- '/xp': { desc: 'XP/Level durumu', run: ['xp'] },
140
- '/skills': { desc: 'Yüklü skill listesi', run: ['skills', 'list'] },
141
- '/status': { desc: 'Sistem durumu', run: ['status'] },
142
- '/mcp': { desc: 'MCP sunucuları', run: ['mcp', 'list'] },
143
- '/channels': { desc: 'Bağlı kanallar', run: ['channels'] },
144
- '/crons': { desc: 'Cron görevleri', run: ['cron', 'list'] },
145
- '/bots': { desc: 'Bot listesi', run: ['bots'] },
146
- '/models': { desc: 'Modeller', run: ['models', 'list'] },
147
- '/memory-ls': { desc: 'Memory dosyaları', run: ['memory', 'list'] },
148
- '/seo': { desc: 'SEO denetimi (URL gerek)', needsArg: true, run: ['seo', 'audit'] },
149
- '/naturehub': { desc: 'Bota mesaj gönder (text gerek)', needsArg: true, run: ['naturehub', 'post'] },
150
- '/dashboard': { desc: 'Web dashboard başlat (port 7421)', run: ['dashboard', 'start'] },
135
+ '/doctor': { desc: L('Sistem sağlığı kontrolü', 'System health check'), run: ['doctor'] },
136
+ '/cost': { desc: L('Maliyet takibi (today|week|month|budget)', 'Cost tracking (today|week|month|budget)'), run: ['cost', 'today'] },
137
+ '/audit': { desc: L('Denetim kaydı (today|stats|files)', 'Audit log (today|stats|files)'), run: ['audit', 'stats'] },
138
+ '/team': { desc: L('Çoklu ajan (list|status)', 'Multi-agent (list|status)'), run: ['team', 'list'] },
139
+ '/xp': { desc: L('XP/Seviye durumu', 'XP/level status'), run: ['xp'] },
140
+ '/skills': { desc: L('Yüklü beceri listesi', 'Installed skills'), run: ['skills', 'list'] },
141
+ '/status': { desc: L('Sistem durumu', 'System status'), run: ['status'] },
142
+ '/mcp': { desc: L('MCP sunucuları', 'MCP servers'), run: ['mcp', 'list'] },
143
+ '/channels': { desc: L('Bağlı kanallar', 'Connected channels'), run: ['channels'] },
144
+ '/crons': { desc: L('Zamanlanmış görevler', 'Scheduled tasks'), run: ['cron', 'list'] },
145
+ '/bots': { desc: L('Bot listesi', 'Bot list'), run: ['bots'] },
146
+ '/models': { desc: L('Modeller', 'Models'), run: ['models', 'list'] },
147
+ '/memory-ls': { desc: L('Hafıza dosyaları', 'Memory files'), run: ['memory', 'list'] },
148
+ '/seo': { desc: L('SEO denetimi (URL gerekli)', 'SEO audit (URL required)'), needsArg: true, run: ['seo', 'audit'] },
149
+ '/naturehub': { desc: L('Bota mesaj gönder (metin gerekli)', 'Send a message to a bot (text required)'), needsArg: true, run: ['naturehub', 'post'] },
150
+ '/dashboard': { desc: L('Web panelini başlat (port 7421)', 'Start web dashboard (port 7421)'), run: ['dashboard', 'start'] },
151
151
  };
152
152
 
153
153
  // Profil desteği: --profile <ad> ile ~/.natureco-<ad> kullanılır (config ile tutarlı)
@@ -174,7 +174,7 @@ const { isMiniMax, isGemini, buildChatEndpoint } = require('../utils/provider-de
174
174
 
175
175
  function loadMemory(username) {
176
176
  const uname = (username || 'default').toLowerCase();
177
- const base = { name: username || 'Kullanıcı', nickname: null, botName: null, facts: [], preferences: [], history: [] };
177
+ const base = { name: username || L('Kullanıcı', 'User'), nickname: null, botName: null, facts: [], preferences: [], history: [] };
178
178
  const readJson = (f) => { try { return fs.existsSync(f) ? JSON.parse(fs.readFileSync(f, 'utf8')) : null; } catch { return null; } };
179
179
 
180
180
  const userMem = readJson(path.join(MEMORY_DIR, `${uname}.json`));
@@ -201,7 +201,7 @@ function loadMemory(username) {
201
201
  }
202
202
  }
203
203
 
204
- if (!merged.botName) merged.botName = 'Asistan';
204
+ if (!merged.botName) merged.botName = L('Asistan', 'Assistant');
205
205
  return merged;
206
206
  }
207
207
 
@@ -241,7 +241,7 @@ function saveSession(messages, meta) {
241
241
  const idx = loadSessionsIndex();
242
242
  idx.sessions.unshift({
243
243
  id, file, createdAt: data.createdAt, messageCount: messages.length,
244
- firstUserMessage: messages.find(m => m.role === 'user')?.content?.slice(0, 60) || '(boş)',
244
+ firstUserMessage: messages.find(m => m.role === 'user')?.content?.slice(0, 60) || L('(boş)', '(empty)'),
245
245
  });
246
246
  // Son 50 session tut
247
247
  idx.sessions = idx.sessions.slice(0, 50);
@@ -732,7 +732,7 @@ async function sendStreaming(providerUrl, providerApiKey, messages, model, onChu
732
732
  // Fallback chain: try next model on error
733
733
  const fb = fallbackChain.recordError(body.model, err);
734
734
  if (fb.fallback) {
735
- console.log(tui.C.yellow(`\n ⚠ ${body.model} başarısız → ${fb.nextModel} deneniyor...\n`));
735
+ console.log(tui.C.yellow(`\n ⚠ ${body.model} ${L('başarısız', 'failed')} → ${fb.nextModel} ${L('deneniyor...', 'trying...')}\n`));
736
736
  continue; // Retry with next model
737
737
  }
738
738
  throw err;
@@ -757,12 +757,12 @@ async function sendStreaming(providerUrl, providerApiKey, messages, model, onChu
757
757
  // Plan mode review: plan submitted, wait for user approval
758
758
  if (planMode.inReview()) {
759
759
  const { plan } = planMode.planHistory[planMode.planHistory.length - 1] || {};
760
- console.log('\n' + tui.C.cyan(' 📋 Plan sunuldu — onay bekleniyor...'));
760
+ console.log('\n' + tui.C.cyan(L(' 📋 Plan sunuldu — onay bekleniyor...', ' 📋 Plan submitted — awaiting approval...')));
761
761
  console.log(tui.C.muted(' ' + '─'.repeat(56)));
762
762
  console.log(plan ? `\n ${plan.replace(/\n/g, '\n ')}` : '');
763
763
  console.log('\n' + tui.C.muted(' ─'.repeat(28)));
764
764
  const approved = await new Promise(resolve => {
765
- stdinPrompt(tui.C.yellow(' Planı onaylıyor musun? [Y=exec, n=reddet, e=düzenle]: '), answer => {
765
+ stdinPrompt(tui.C.yellow(L(' Planı onaylıyor musun? [Y=exec, n=reddet, e=düzenle]: ', ' Approve the plan? [Y=exec, n=reject, e=edit]: ')), answer => {
766
766
  const key = answer.trim().toLowerCase();
767
767
  if (key === 'n' || key === 'no') { planMode.reject(); resolve(false); }
768
768
  else if (key === 'e' || key === 'edit') { planMode.reject(); resolve('edit'); }
@@ -770,16 +770,16 @@ async function sendStreaming(providerUrl, providerApiKey, messages, model, onChu
770
770
  });
771
771
  });
772
772
  if (approved === true) {
773
- console.log(tui.C.green(' ✓ Plan onaylandı. Plan uygulanıyor...\n'));
773
+ console.log(tui.C.green(L(' ✓ Plan onaylandı. Plan uygulanıyor...\n', ' ✓ Plan approved. Applying...\n')));
774
774
  // Devam — model cevap versin
775
775
  } else if (approved === 'edit') {
776
- console.log(tui.C.yellow(' 📝 Planı düzenleyin ve /plan ile yeniden gönderin.\n'));
776
+ console.log(tui.C.yellow(L(' 📝 Planı düzenleyin ve /plan ile yeniden gönderin.\n', ' 📝 Edit the plan and resubmit with /plan.\n')));
777
777
  // Plan modunda kal, mesaj ekle
778
- currentMessages.push({ role: 'user', content: 'Planı düzenle ve yeniden sun.' });
778
+ currentMessages.push({ role: 'user', content: L('Planı düzenle ve yeniden sun.', 'Revise the plan and submit it again.') });
779
779
  continue;
780
780
  } else {
781
- console.log(tui.C.amber(' ⨯ Plan reddedildi. Yeniden plan yapılıyor...\n'));
782
- currentMessages.push({ role: 'user', content: 'Plan reddedildi. Lütfen farklı bir yaklaşım dene.' });
781
+ console.log(tui.C.amber(L(' ⨯ Plan reddedildi. Yeniden plan yapılıyor...\n', ' ⨯ Plan rejected. Re-planning...\n')));
782
+ currentMessages.push({ role: 'user', content: L('Plan reddedildi. Lütfen farklı bir yaklaşım dene.', 'The plan was rejected. Please try a different approach.') });
783
783
  continue;
784
784
  }
785
785
  }
@@ -813,7 +813,7 @@ const { getFallbackChain } = require('../utils/fallback-chain');
813
813
  * Returns: true (once), 'session', 'persistent', or false (denied).
814
814
  */
815
815
  async function askPermissionPrompt(question, hint, prompter) {
816
- const full = `${tui.C.yellow('⚠')} ${tui.C.bold('İzin gerekiyor')}: ${question}\n${tui.C.muted(hint)}`;
816
+ const full = `${tui.C.yellow('⚠')} ${tui.C.bold(L('İzin gerekiyor', 'Permission required'))}: ${question}\n${tui.C.muted(hint)}`;
817
817
  return new Promise(resolve => {
818
818
  prompter(full, answer => {
819
819
  const key = answer.trim();
@@ -1005,22 +1005,22 @@ async function processToolCalls(toolCalls, onToolCall, onAsk) {
1005
1005
  }
1006
1006
 
1007
1007
  function printHelp() {
1008
- console.log(chalk.cyan('\n 📚 REPL Komutları:\n'));
1009
- console.log(' ' + chalk.yellow('/help'.padEnd(22)) + chalk.gray('Bu yardım'));
1010
- console.log(' ' + chalk.yellow('/clear'.padEnd(22)) + chalk.gray('Ekranı temizle'));
1011
- console.log(' ' + chalk.yellow('/history'.padEnd(22)) + chalk.gray('Bu oturumun geçmişi'));
1012
- console.log(' ' + chalk.yellow('/memory'.padEnd(22)) + chalk.gray('Memory\'i göster'));
1013
- console.log(' ' + chalk.yellow('/plan [on|off|show]'.padEnd(22)) + chalk.gray('Plan modu'));
1014
- console.log(' ' + chalk.yellow('/forget'.padEnd(22)) + chalk.gray('Memory\'i temizle'));
1015
- console.log(' ' + chalk.yellow('/sessions'.padEnd(22)) + chalk.gray('Geçmiş oturumları listele'));
1016
- console.log(' ' + chalk.yellow('/resume [id|last]'.padEnd(22)) + chalk.gray('Önceki oturuma dön'));
1017
- console.log(' ' + chalk.yellow('/system <text>'.padEnd(22)) + chalk.gray('System prompt değiştir'));
1018
- console.log(' ' + chalk.yellow('/model <name>'.padEnd(22)) + chalk.gray('Model değiştir'));
1019
- console.log(' ' + chalk.yellow('/identity [ad]'.padEnd(22)) + chalk.gray('Bot adını değiştir'));
1020
- console.log(' ' + chalk.yellow('/tokens'.padEnd(22)) + chalk.gray('Token kullanımı'));
1021
- console.log(' ' + chalk.yellow('/save'.padEnd(22)) + chalk.gray('Oturumu manuel kaydet'));
1022
- console.log(' ' + chalk.yellow('/exit veya /quit'.padEnd(22)) + chalk.gray('Çıkış (Ctrl+C de çalışır)'));
1023
- console.log(chalk.cyan('\n 🛠️ Tüm CLI Komutları (REPL içinden):\n'));
1008
+ console.log(chalk.cyan(L('\n 📚 REPL Komutları:\n', '\n 📚 REPL Commands:\n')));
1009
+ console.log(' ' + chalk.yellow('/help'.padEnd(22)) + chalk.gray(L('Bu yardım', 'This help')));
1010
+ console.log(' ' + chalk.yellow('/clear'.padEnd(22)) + chalk.gray(L('Ekranı temizle', 'Clear the screen')));
1011
+ console.log(' ' + chalk.yellow('/history'.padEnd(22)) + chalk.gray(L('Bu oturumun geçmişi', 'This session\'s history')));
1012
+ console.log(' ' + chalk.yellow('/memory'.padEnd(22)) + chalk.gray(L('Hafızayı göster', 'Show memory')));
1013
+ console.log(' ' + chalk.yellow('/plan [on|off|show]'.padEnd(22)) + chalk.gray(L('Plan modu', 'Plan mode')));
1014
+ console.log(' ' + chalk.yellow('/forget'.padEnd(22)) + chalk.gray(L('Hafızayı temizle', 'Clear memory')));
1015
+ console.log(' ' + chalk.yellow('/sessions'.padEnd(22)) + chalk.gray(L('Geçmiş oturumları listele', 'List past sessions')));
1016
+ console.log(' ' + chalk.yellow('/resume [id|last]'.padEnd(22)) + chalk.gray(L('Önceki oturuma dön', 'Return to a previous session')));
1017
+ console.log(' ' + chalk.yellow('/system <text>'.padEnd(22)) + chalk.gray(L('System prompt değiştir', 'Change system prompt')));
1018
+ console.log(' ' + chalk.yellow('/model <name>'.padEnd(22)) + chalk.gray(L('Model değiştir', 'Change model')));
1019
+ console.log(' ' + chalk.yellow('/identity [ad]'.padEnd(22)) + chalk.gray(L('Bot adını değiştir', 'Change bot name')));
1020
+ console.log(' ' + chalk.yellow('/tokens'.padEnd(22)) + chalk.gray(L('Token kullanımı', 'Token usage')));
1021
+ console.log(' ' + chalk.yellow('/save'.padEnd(22)) + chalk.gray(L('Oturumu elle kaydet', 'Save session manually')));
1022
+ console.log(' ' + chalk.yellow(L('/exit veya /quit', '/exit or /quit').padEnd(22)) + chalk.gray(L('Çıkış (Ctrl+C de çalışır)', 'Exit (Ctrl+C also works)')));
1023
+ console.log(chalk.cyan(L('\n 🛠️ Tüm CLI Komutları (REPL içinden):\n', '\n 🛠️ All CLI Commands (from REPL):\n')));
1024
1024
  for (const [cmd, info] of Object.entries(CLI_COMMANDS)) {
1025
1025
  console.log(' ' + chalk.yellow(cmd.padEnd(22)) + chalk.gray(info.desc));
1026
1026
  }
@@ -1053,7 +1053,7 @@ async function startRepl(args) {
1053
1053
  }
1054
1054
 
1055
1055
  if (!providerUrl || !providerApiKey) {
1056
- console.log(chalk.red('\n ❌ Provider ayarlı değil. Önce: natureco setup\n'));
1056
+ console.log(chalk.red(L('\n ❌ Provider ayarlı değil. Önce: natureco setup\n', '\n ❌ Provider not configured. First: natureco setup\n')));
1057
1057
  process.exit(1);
1058
1058
  }
1059
1059
 
@@ -1062,7 +1062,7 @@ async function startRepl(args) {
1062
1062
 
1063
1063
  // v5.6.19: Oncelik config.botName, sonra memory.botName
1064
1064
  if (!memory.botName) {
1065
- memory.botName = cfg.botName || 'Asistan';
1065
+ memory.botName = cfg.botName || L('Asistan', 'Assistant');
1066
1066
  }
1067
1067
  // BotName'i memory'ye persist et (her oturumda ayni kalsin)
1068
1068
  try {
@@ -1117,7 +1117,7 @@ async function startRepl(args) {
1117
1117
  const session = loadSession(resumeId);
1118
1118
  if (session) {
1119
1119
  messages = session.messages || [];
1120
- console.log(chalk.green(`\n ✓ Oturum yüklendi: ${session.id} (${messages.length} mesaj)\n`));
1120
+ console.log(chalk.green(`\n ✓ ${L('Oturum yüklendi', 'Session loaded')}: ${session.id} (${messages.length} ${L('mesaj', 'messages')})\n`));
1121
1121
  } else {
1122
1122
  console.log(chalk.yellow(`\n ⚠️ ${L('Oturum bulunamadı', 'Session not found')}: ${resumeId}\n`));
1123
1123
  }
@@ -1125,7 +1125,7 @@ async function startRepl(args) {
1125
1125
 
1126
1126
  // System prompt oluştur (memory + identity + persistent bağlam)
1127
1127
  // v5.6.5: Kucuk model tespiti (Groq, Mistral Small, Ollama) - SOUL injection skip
1128
- const botName = memory.botName || 'Asistan';
1128
+ const botName = memory.botName || L('Asistan', 'Assistant');
1129
1129
  const userName = memory.name || memory.nickname || cfg.userName;
1130
1130
  const isSmallModel = (cfg.providerUrl || '').includes('groq.com') ||
1131
1131
  (cfg.providerUrl || '').includes('mistral.ai') ||
@@ -1134,7 +1134,7 @@ async function startRepl(args) {
1134
1134
  // Discover project rules (CLAUDE.md)
1135
1135
  const projectRules = discoverProjectRules(process.cwd());
1136
1136
  if (projectRules) {
1137
- console.log(chalk.cyan(` 📋 Proje kurallari bulundu (CLAUDE.md)\n`));
1137
+ console.log(chalk.cyan(` 📋 ${L('Proje kurallari bulundu', 'Project rules found')} (CLAUDE.md)\n`));
1138
1138
  }
1139
1139
 
1140
1140
  // Build system prompt with tier caching (stable+context cached, volatile fresh)
@@ -1161,20 +1161,20 @@ async function startRepl(args) {
1161
1161
 
1162
1162
  // Header
1163
1163
  console.log('');
1164
- console.log(tui.styled(' 🌿 NatureCo REPL · Persistent Sohbet', { color: tui.PALETTE.primary, bold: true }));
1164
+ console.log(tui.styled(L(' 🌿 NatureCo REPL · Persistent Sohbet', ' 🌿 NatureCo REPL · Persistent Chat'), { color: tui.PALETTE.primary, bold: true }));
1165
1165
  console.log(tui.styled(' ' + '─'.repeat(56), { color: tui.PALETTE.border }));
1166
1166
  console.log(tui.C.muted(' Provider: ') + tui.C.brand(providerUrl.replace(/https?:\/\//, '')));
1167
1167
  console.log(tui.C.muted(' Model: ') + tui.C.brand(model));
1168
- const displayUser = memory.nickname || cfg.userName || require('os').userInfo().username || 'Kullanıcı';
1169
- console.log(tui.C.muted(' Kullanıcı: ') + tui.C.brand(displayUser + (memory.nickname && cfg.userName ? ` (${cfg.userName})` : '')));
1170
- console.log(tui.C.muted(' Bot: ') + tui.C.brand(memory.botName || 'Asistan'));
1171
- if (messages.length > 1) {
1172
- console.log(tui.C.muted(' Oturum: ') + tui.C.amber(`${messages.filter(m => m.role === 'user' || m.role === 'assistant').length} mesaj (resume)`));
1173
- }
1174
- console.log(tui.C.muted(' Komutlar: ') + tui.C.yellow('/help') + tui.C.muted(' · ') + tui.C.yellow('/memory') + tui.C.muted(' · ') + tui.C.yellow('/sessions') + tui.C.muted(' · ') + tui.C.yellow('/exit'));
1168
+ const displayUser = memory.nickname || cfg.userName || require('os').userInfo().username || L('Kullanıcı', 'User');
1169
+ console.log(tui.C.muted(L(' Kullanıcı: ', ' User: ')) + tui.C.brand(displayUser + (memory.nickname && cfg.userName ? ` (${cfg.userName})` : '')));
1170
+ console.log(tui.C.muted(' Bot: ') + tui.C.brand(memory.botName || L('Asistan', 'Assistant')));
1171
+ if (messages.length > 1) {
1172
+ console.log(tui.C.muted(L(' Oturum: ', ' Session: ')) + tui.C.amber(`${messages.filter(m => m.role === 'user' || m.role === 'assistant').length} ${L('mesaj', 'messages')} (${L('devam', 'resumed')})`));
1173
+ }
1174
+ console.log(tui.C.muted(L(' Komutlar: ', ' Commands: ')) + tui.C.yellow('/help') + tui.C.muted(' · ') + tui.C.yellow('/memory') + tui.C.muted(' · ') + tui.C.yellow('/sessions') + tui.C.muted(' · ') + tui.C.yellow('/exit'));
1175
1175
  console.log('');
1176
1176
  // v5.4.7: Hard-coded kimlik — v5.14.5: memory fact'lerinden kullanici adini tespit et
1177
- const displayBotName = memory.botName || 'Asistan';
1177
+ const displayBotName = memory.botName || L('Asistan', 'Assistant');
1178
1178
  const nameFromFact = (() => {
1179
1179
  const facts = memory.facts || [];
1180
1180
  for (const f of facts) {
@@ -1186,7 +1186,7 @@ async function startRepl(args) {
1186
1186
  return null;
1187
1187
  })();
1188
1188
  const displayUserName = memory.name || nameFromFact || memory.nickname || cfg.userName;
1189
- console.log(tui.C.brand(' 👋 Ben ' + displayBotName + ', ' + displayUserName + '. Sen nasilsin?'));
1189
+ console.log(tui.C.brand(L(` 👋 Ben ${displayBotName}, ${displayUserName}. Sen nasılsın?`, ` 👋 I am ${displayBotName}, ${displayUserName}. How are you?`)));
1190
1190
  console.log('');
1191
1191
 
1192
1192
  // Theseus deseni: oturum basinda "geçen sefer kalanlari" proaktif hatirlat
@@ -1194,7 +1194,7 @@ async function startRepl(args) {
1194
1194
  try {
1195
1195
  const pending = require('../tools/memory_tree')._internal.getPending(cfg.userName);
1196
1196
  if (pending && pending.length) {
1197
- console.log(tui.C.muted(' 📌 Geçen oturumdan kalanlar:'));
1197
+ console.log(tui.C.muted(L(' 📌 Geçen oturumdan kalanlar:', ' 📌 Left over from last session:')));
1198
1198
  for (const item of pending.slice(0, 6)) console.log(tui.C.muted(' • ' + item));
1199
1199
  console.log('');
1200
1200
  }
@@ -1217,7 +1217,7 @@ async function startRepl(args) {
1217
1217
  const rl = readline.createInterface({
1218
1218
  input: createPasteSafeInput(process.stdin),
1219
1219
  output: createOutputFilter(process.stdout),
1220
- prompt: tui.styled(' 💬 Sen ▸ ', { color: tui.PALETTE.primary, bold: true }),
1220
+ prompt: tui.styled(L(' 💬 Sen ▸ ', ' 💬 You ▸ '), { color: tui.PALETTE.primary, bold: true }),
1221
1221
  terminal: true,
1222
1222
  });
1223
1223
  // Pipe/script kullanımında EOF, yanıt hâlâ üretilirken gelir —
@@ -1239,10 +1239,10 @@ async function startRepl(args) {
1239
1239
  // Bu, Parton'un "oturum sonunda konusmalar kaydedilmiyor" sikayetini cözüyor
1240
1240
  const persistResult = await persistSessionToMemory(messages, memory, cfg);
1241
1241
  if (persistResult && persistResult.factsAdded > 0) {
1242
- console.log(chalk.gray(`\n 🧠 ${persistResult.factsAdded} yeni fact memory'ye kaydedildi`));
1242
+ console.log(chalk.gray(`\n 🧠 ${persistResult.factsAdded} ${L("yeni fact memory'ye kaydedildi", 'new facts saved to memory')}`));
1243
1243
  }
1244
1244
  if (persistResult && persistResult.preferencesAdded > 0) {
1245
- console.log(chalk.gray(` 🎯 ${persistResult.preferencesAdded} yeni tercih kaydedildi`));
1245
+ console.log(chalk.gray(` 🎯 ${persistResult.preferencesAdded} ${L('yeni tercih kaydedildi', 'new preferences saved')}`));
1246
1246
  }
1247
1247
 
1248
1248
  // v5.46: oturum-sonu hafıza-sağlığı ipucu (gürültüsüz). Yinelenen/çelişen kayıt varsa
@@ -1252,19 +1252,19 @@ async function startRepl(args) {
1252
1252
  const { lintUser } = require('../utils/memory-lint');
1253
1253
  const { flatFindings, treeFindings } = lintUser(cfg.userName);
1254
1254
  const n = (flatFindings.length + treeFindings.length);
1255
- if (n > 0) console.log(chalk.gray(` 💡 Hafızada ${n} olası yinelenen/çelişen kayıt — "natureco memory lint" ile gözden geçir.`));
1255
+ if (n > 0) console.log(chalk.gray(` 💡 ${L('Hafızada', 'In memory')} ${n} ${L('olası yinelenen/çelişen kayıt —', 'possible duplicate/conflicting records —')} "natureco memory lint" ${L('ile gözden geçir.', 'to review.')}`));
1256
1256
  } catch {}
1257
1257
 
1258
1258
  const sessId = saveSession(messages, {
1259
1259
  provider: providerUrl, model, user: cfg.userName,
1260
1260
  bot: memory.botName, factCount: memory.facts?.length || 0,
1261
1261
  });
1262
- console.log(chalk.gray(`\n 💾 Oturum kaydedildi: ${sessId}`));
1262
+ console.log(chalk.gray(`\n 💾 ${L('Oturum kaydedildi', 'Session saved')}: ${sessId}`));
1263
1263
  }
1264
1264
  // Global buffer temizle
1265
1265
  if (global._fixBuffer) global._fixBuffer = '';
1266
1266
  disableBracketedPaste(process.stdout);
1267
- console.log(chalk.gray('\n 👋 Görüşürüz!\n'));
1267
+ console.log(chalk.gray(L('\n 👋 Görüşürüz!\n', '\n 👋 See you!\n')));
1268
1268
  process.exit(exitCode);
1269
1269
  };
1270
1270
 
@@ -1392,7 +1392,7 @@ async function startRepl(args) {
1392
1392
  case 'clear': console.clear(); break;
1393
1393
  case 'exit': case 'quit': case 'q': await cleanup(0); return;
1394
1394
  case 'history':
1395
- console.log(chalk.cyan('\n 📜 Bu oturumun geçmişi:\n'));
1395
+ console.log(chalk.cyan(L('\n 📜 Bu oturumun geçmişi:\n', '\n 📜 This session\'s history:\n')));
1396
1396
  for (const m of messages.filter(m => !m._internal)) {
1397
1397
  const role = m.role === 'user' ? chalk.green('You') : chalk.blue('AI ');
1398
1398
  const content = (m.content || '').slice(0, 120) + ((m.content || '').length > 120 ? '...' : '');
@@ -1402,16 +1402,16 @@ async function startRepl(args) {
1402
1402
  break;
1403
1403
  case 'memory':
1404
1404
  console.log(chalk.cyan('\n 🧠 Memory:\n'));
1405
- console.log(' Kullanıcı: ' + chalk.cyan(memory.name));
1406
- console.log(' Nickname: ' + chalk.cyan(memory.nickname || '(yok)'));
1407
- console.log(' Bot: ' + chalk.cyan(memory.botName || 'Asistan'));
1405
+ console.log(L(' Kullanıcı: ', ' User: ') + chalk.cyan(memory.name));
1406
+ console.log(L(' Takma ad: ', ' Nickname: ') + chalk.cyan(memory.nickname || L('(yok)', '(none)')));
1407
+ console.log(' Bot: ' + chalk.cyan(memory.botName || L('Asistan', 'Assistant')));
1408
1408
  if (memory.facts && memory.facts.length > 0) {
1409
1409
  console.log(' Facts (' + memory.facts.length + '):');
1410
1410
  for (const f of memory.facts) {
1411
- console.log(' • ' + chalk.gray((f.value || f) + (f.score ? ' [skor:' + f.score + ']' : '')));
1411
+ console.log(' • ' + chalk.gray((f.value || f) + (f.score ? ` [${L('skor', 'score')}:${f.score}]` : '')));
1412
1412
  }
1413
1413
  } else {
1414
- console.log(chalk.gray(' (Henüz fact yok)'));
1414
+ console.log(chalk.gray(L(' (Henüz fact yok)', ' (No facts yet)')));
1415
1415
  }
1416
1416
  console.log('');
1417
1417
  break;
@@ -1420,26 +1420,26 @@ async function startRepl(args) {
1420
1420
  if (fs.existsSync(path.join(MEMORY_DIR, `${(cfg.userName || 'default').toLowerCase()}.json`))) {
1421
1421
  fs.unlinkSync(path.join(MEMORY_DIR, `${(cfg.userName || 'default').toLowerCase()}.json`));
1422
1422
  }
1423
- memory = { name: cfg.userName, nickname: null, botName: 'Asistan', facts: [], preferences: [], history: [] };
1423
+ memory = { name: cfg.userName, nickname: null, botName: L('Asistan', 'Assistant'), facts: [], preferences: [], history: [] };
1424
1424
  // System prompt'u rebuild with cleared memory
1425
1425
  promptOpts.memoryFacts = [];
1426
1426
  memoryStore.clear();
1427
1427
  promptOpts.memorySnapshotBlock = memoryStore.getSystemPromptBlock();
1428
1428
  systemPrompt = rebuildSystemPrompt(promptOpts);
1429
1429
  messages[0] = { role: 'system', content: systemPrompt, _internal: true };
1430
- console.log(chalk.green(' ✓ Memory temizlendi'));
1430
+ console.log(chalk.green(L(' ✓ Memory temizlendi', ' ✓ Memory cleared')));
1431
1431
  } catch (e) {
1432
1432
  console.log(chalk.red(' ❌ ' + e.message));
1433
1433
  }
1434
1434
  break;
1435
1435
  case 'sessions':
1436
1436
  const idx = loadSessionsIndex();
1437
- console.log(chalk.cyan('\n 📚 Geçmiş Oturumlar (' + idx.sessions.length + ')\n'));
1437
+ console.log(chalk.cyan(L('\n 📚 Geçmiş Oturumlar (', '\n 📚 Past Sessions (') + idx.sessions.length + ')\n'));
1438
1438
  for (let i = 0; i < Math.min(10, idx.sessions.length); i++) {
1439
1439
  const s = idx.sessions[i];
1440
1440
  console.log(` ${chalk.gray((i + 1).toString().padStart(2) + '.')} ${chalk.cyan(s.id)} ${chalk.muted('— ' + s.firstUserMessage)}`);
1441
1441
  }
1442
- console.log(chalk.gray('\n Devam etmek için: /resume <id> veya /resume last\n'));
1442
+ console.log(chalk.gray(L('\n Devam etmek için: /resume <id> veya /resume last\n', '\n To continue: /resume <id> or /resume last\n')));
1443
1443
  break;
1444
1444
  case 'resume':
1445
1445
  if (!arg) { console.log(chalk.yellow(L(' Kullanım: /resume <id> veya /resume last', ' Usage: /resume <id> or /resume last'))); break; }
@@ -1449,7 +1449,7 @@ async function startRepl(args) {
1449
1449
  const sysIdx = messages.findIndex(m => m._internal);
1450
1450
  if (sysIdx >= 0) messages[sysIdx] = { role: 'system', content: systemPrompt, _internal: true };
1451
1451
  else messages.unshift({ role: 'system', content: systemPrompt, _internal: true });
1452
- console.log(chalk.green(` ✓ Oturum yüklendi: ${session.id} (${messages.length} mesaj)`));
1452
+ console.log(chalk.green(` ✓ ${L('Oturum yüklendi', 'Session loaded')}: ${session.id} (${messages.length} ${L('mesaj', 'messages')})`));
1453
1453
  } else {
1454
1454
  console.log(chalk.yellow(` ⚠️ ${L('Oturum bulunamadı', 'Session not found')}: ${arg}`));
1455
1455
  }
@@ -1466,7 +1466,7 @@ async function startRepl(args) {
1466
1466
  const volTiers = buildTiers(volOpts);
1467
1467
  systemPrompt = assemble(_cachedStable, _cachedContext, volTiers.volatile);
1468
1468
  messages[0] = { role: 'system', content: systemPrompt, _internal: true };
1469
- console.log(chalk.green(' ✓ System prompt güncellendi'));
1469
+ console.log(chalk.green(L(' ✓ System prompt güncellendi', ' ✓ System prompt updated')));
1470
1470
  break;
1471
1471
  case 'model':
1472
1472
  if (!arg) { console.log(chalk.yellow(L(' Kullanım: /model <name>', ' Usage: /model <name>'))); break; }
@@ -1474,7 +1474,7 @@ async function startRepl(args) {
1474
1474
  console.log(chalk.green(' ✓ Model: ') + chalk.cyan(model));
1475
1475
  break;
1476
1476
  case 'identity':
1477
- if (!arg) { console.log(chalk.yellow(` Mevcut: ${memory.botName || 'Asistan'}`)); break; }
1477
+ if (!arg) { console.log(chalk.yellow(` ${L('Mevcut', 'Current')}: ${memory.botName || L('Asistan', 'Assistant')}`)); break; }
1478
1478
  memory.botName = arg;
1479
1479
  saveMemory(cfg.userName, memory);
1480
1480
  // Rebuild stable tier with new botName
@@ -1485,29 +1485,29 @@ async function startRepl(args) {
1485
1485
  promptOpts.memoryFacts = memory.facts || [];
1486
1486
  systemPrompt = rebuildSystemPrompt(promptOpts);
1487
1487
  messages[0] = { role: 'system', content: systemPrompt, _internal: true };
1488
- console.log(chalk.green(' ✓ Bot adı: ') + chalk.cyan(arg));
1488
+ console.log(chalk.green(L(' ✓ Bot adı: ', ' ✓ Bot name: ')) + chalk.cyan(arg));
1489
1489
  break;
1490
1490
  case 'tokens':
1491
1491
  console.log(chalk.gray(` Token: ~${totalInputTokens} in / ~${totalOutputTokens} out`));
1492
1492
  break;
1493
1493
  case 'plan':
1494
1494
  if (arg === 'on' || arg === 'enter') {
1495
- if (getPlanMode().enter()) console.log(tui.C.cyan('\n 📋 Plan modu aktif. Plan yapın ve /plan off ile çıkın.\n'));
1496
- else console.log(tui.C.yellow(' Zaten plan modunda.'));
1495
+ if (getPlanMode().enter()) console.log(tui.C.cyan(L('\n 📋 Plan modu aktif. Plan yapın ve /plan off ile çıkın.\n', '\n 📋 Plan mode active. Plan and exit with /plan off.\n')));
1496
+ else console.log(tui.C.yellow(L(' Zaten plan modunda.', ' Already in plan mode.')));
1497
1497
  } else if (arg === 'off' || arg === 'exit') {
1498
1498
  if (getPlanMode().isPlanning()) {
1499
- console.log(tui.C.yellow(' Plan modundan çıkılıyor. Plan yazılıp ExitPlanMode ile sunulmalı.'));
1499
+ console.log(tui.C.yellow(L(' Plan modundan çıkılıyor. Plan yazılıp ExitPlanMode ile sunulmalı.', ' Exiting plan mode. Write a plan and submit with ExitPlanMode.')));
1500
1500
  getPlanMode().approve();
1501
1501
  } else {
1502
- console.log(tui.C.yellow(' Plan modunda değil.'));
1502
+ console.log(tui.C.yellow(L(' Plan modunda değil.', ' Not in plan mode.')));
1503
1503
  }
1504
1504
  } else if (arg === 'show') {
1505
1505
  if (getPlanMode().planHistory.length > 0) {
1506
1506
  const last = getPlanMode().planHistory[getPlanMode().planHistory.length - 1];
1507
- console.log(tui.C.cyan('\n 📋 Son Plan:\n'));
1507
+ console.log(tui.C.cyan(L('\n 📋 Son Plan:\n', '\n 📋 Last Plan:\n')));
1508
1508
  console.log(` ${last.plan.replace(/\n/g, '\n ')}`);
1509
1509
  } else {
1510
- console.log(tui.C.yellow(' Henüz plan yok.'));
1510
+ console.log(tui.C.yellow(L(' Henüz plan yok.', ' No plan yet.')));
1511
1511
  }
1512
1512
  } else {
1513
1513
  console.log(tui.C.yellow(L(' Kullanım: /plan on|off|show', ' Usage: /plan on|off|show')));
@@ -1517,16 +1517,16 @@ async function startRepl(args) {
1517
1517
  const sessId = saveSession(messages, {
1518
1518
  provider: providerUrl, model, user: cfg.userName, bot: memory.botName,
1519
1519
  });
1520
- console.log(chalk.green(' ✓ Kaydedildi: ') + chalk.cyan(sessId));
1520
+ console.log(chalk.green(L(' ✓ Kaydedildi: ', ' ✓ Saved: ')) + chalk.cyan(sessId));
1521
1521
  break;
1522
1522
  default:
1523
1523
  // CLI komutları (REPL içinden)
1524
1524
  if (CLI_COMMANDS['/' + cmd]) {
1525
1525
  const cliCmd = CLI_COMMANDS['/' + cmd];
1526
1526
  if (cliCmd.needsArg && !arg) {
1527
- console.log(chalk.yellow(` ${cmd} bir argüman gerekli: ${cliCmd.desc}`));
1527
+ console.log(chalk.yellow(` ${cmd} ${L('bir argüman gerekli', 'requires an argument')}: ${cliCmd.desc}`));
1528
1528
  } else {
1529
- console.log(chalk.gray(` → ${cmd} çalıştırılıyor...`));
1529
+ console.log(chalk.gray(` → ${cmd} ${L('çalıştırılıyor...', 'running...')}`));
1530
1530
  const args2 = [...cliCmd.run];
1531
1531
  if (arg && (cmd === 'seo' || cmd === 'naturehub')) args2.push(arg);
1532
1532
  await runCliCommand(args2);
@@ -1544,19 +1544,19 @@ async function startRepl(args) {
1544
1544
 
1545
1545
  // Çok satırlı (paste) mesajları gönderildikten sonra ekranda göster
1546
1546
  if (line.indexOf('\n') !== -1) {
1547
- process.stdout.write(tui.styled(' 💬 Sen ▸ ', { color: tui.PALETTE.primary, bold: true }));
1547
+ process.stdout.write(tui.styled(L(' 💬 Sen ▸ ', ' 💬 You ▸ '), { color: tui.PALETTE.primary, bold: true }));
1548
1548
  process.stdout.write(line + '\n');
1549
1549
  }
1550
1550
 
1551
1551
  // v5.6.8: Hard-coded fallback - "sen kimsin?" sorulari icin dinamik botName
1552
1552
  const trimmed = (line || '').toLowerCase();
1553
- const isIdentityQuestion = /(sen\s+kim|adin\s+ne|kendini\s+tan|kendin\s+tanit|kimsin|ne\s+adindasin)/.test(trimmed);
1553
+ const isIdentityQuestion = /(sen\s+kim|adin\s+ne|kendini\s+tan|kendin\s+tanit|kimsin|ne\s+adindasin|who\s+are\s+you|what(?:'s|\s+is)\s+your\s+name|introduce\s+yourself)/.test(trimmed);
1554
1554
  if (isIdentityQuestion) {
1555
1555
  // v5.6.10: Hard-coded prefix minimal - model cevabini bozuyordu
1556
1556
  // Once sadece isim yaz, modelin devamini getirsin
1557
- const displayName = memory.botName || 'Asistan';
1557
+ const displayName = memory.botName || L('Asistan', 'Assistant');
1558
1558
  process.stdout.write(tui.styled('\n AI ', { color: tui.PALETTE.secondary, bold: true }));
1559
- process.stdout.write('Merhaba! Ben ' + displayName + '. ');
1559
+ process.stdout.write(L('Merhaba! Ben ', 'Hello! I am ') + displayName + '. ');
1560
1560
  }
1561
1561
 
1562
1562
  // AI cevabı — v5.13.0: workflow orchestrator ALWAYS first
@@ -1591,7 +1591,7 @@ async function startRepl(args) {
1591
1591
  if (wf.passthrough && wf.reply !== undefined && wf.reply !== null) {
1592
1592
  // Simple chat — workflow handled it directly
1593
1593
  const fullReply = String(wf.reply);
1594
- const displayBotName = memory.botName || 'Asistan';
1594
+ const displayBotName = memory.botName || L('Asistan', 'Assistant');
1595
1595
  let fixedReply = String(fullReply);
1596
1596
  fixedReply = fixedReply.replace(/\bMiniMax[-\s\w\.\d]*/gi, displayBotName);
1597
1597
  fixedReply = fixedReply.replace(/\bM2\.5[-\s\w\.\d]*/gi, displayBotName);
@@ -1623,13 +1623,16 @@ async function startRepl(args) {
1623
1623
  }
1624
1624
  return ` ${s} ${t}: ${summary}`;
1625
1625
  }).join('\n');
1626
- const skillInfo = wf.skillsLoaded && wf.skillsLoaded.length > 0
1627
- ? `\n\nKullanilan skill'ler: ${wf.skillsLoaded.join(', ')}`
1628
- : '';
1626
+ const skillInfo = wf.skillsLoaded && wf.skillsLoaded.length > 0
1627
+ ? `\n\n${L('Kullanılan beceriler', 'Skills used')}: ${wf.skillsLoaded.join(', ')}`
1628
+ : '';
1629
1629
  const preWfLen = messages.length;
1630
1630
  messages.push({
1631
1631
  role: 'system',
1632
- content: `=== WORKFLOW SONUCLARI ===\nSu araclar calisti:\n${report}${skillInfo}\n\nKullaniciya bu sonuclari anlamli bir sekilde ozetle.\n=== SONUC BITTI ===`,
1632
+ content: L(
1633
+ `=== İŞ AKIŞI SONUÇLARI ===\nŞu araçlar çalıştı:\n${report}${skillInfo}\n\nBu sonuçları kullanıcı için anlamlı biçimde özetle.\n=== SONUÇ BİTTİ ===`,
1634
+ `=== WORKFLOW RESULTS ===\nThe following tools ran:\n${report}${skillInfo}\n\nSummarize these results clearly for the user.\n=== END RESULTS ===`,
1635
+ ),
1633
1636
  });
1634
1637
  const reply = await sendStreaming(
1635
1638
  providerUrl,
@@ -1657,7 +1660,7 @@ async function startRepl(args) {
1657
1660
  // v5.6.12: Tam metin 'reply' olarak zaten geldi (non-stream mode)
1658
1661
  const fullReply = String(reply || '');
1659
1662
  // Bot adini al
1660
- const displayBotName = memory.botName || 'Asistan';
1663
+ const displayBotName = memory.botName || L('Asistan', 'Assistant');
1661
1664
  // v5.6.9: Tum model adlarini ve varyasyonlari temizle
1662
1665
  let fixedReply = String(fullReply);
1663
1666
  fixedReply = fixedReply.replace(/\bMiniMax[-\s\w\.\d]*/gi, displayBotName);
@@ -1678,8 +1681,8 @@ async function startRepl(args) {
1678
1681
  totalOutputTokens += Math.ceil((fullReply || '').length / 4);
1679
1682
  } else {
1680
1683
  // Workflow failed or returned unexpected format
1681
- const fullReply = wf.error || JSON.stringify(wf).slice(0, 400) || 'Workflow islenemedi.';
1682
- const displayBotName = memory.botName || 'Asistan';
1684
+ const fullReply = wf.error || JSON.stringify(wf).slice(0, 400) || L('İş akışı işlenemedi.', 'Workflow could not be processed.');
1685
+ const displayBotName = memory.botName || L('Asistan', 'Assistant');
1683
1686
  let fixedReply = fullReply.replace(/\bMiniMax[-\s\w\.\d]*/gi, displayBotName);
1684
1687
  process.stdout.write('\n' + fixedReply + '\n');
1685
1688
  messages.push({ role: 'assistant', content: fixedReply });
@@ -1704,6 +1707,7 @@ async function startRepl(args) {
1704
1707
  });
1705
1708
  }
1706
1709
 
1707
- module.exports = startRepl;
1708
- // v5.40: test icin — cross-session hafiza bozulma regresyonu (kod adı ≠ kullanici adi)
1709
- module.exports.extractPreferenceFacts = extractPreferenceFacts;
1710
+ module.exports = startRepl;
1711
+ // v5.40: test icin — cross-session hafiza bozulma regresyonu (kod adı ≠ kullanici adi)
1712
+ module.exports.extractPreferenceFacts = extractPreferenceFacts;
1713
+ module.exports._internal = { printHelp, CLI_COMMANDS };
@@ -1,5 +1,7 @@
1
1
  const chalk = require('chalk');
2
2
  const { execSync, spawn } = require('child_process');
3
+ const { getLang: _gl } = require('../utils/i18n');
4
+ const L = (tr, en) => (_gl() === 'en' ? en : tr);
3
5
  const fs = require('fs');
4
6
  const path = require('path');
5
7
  const os = require('os');
@@ -15,7 +17,7 @@ function sandbox(args) {
15
17
  if (action === 'exec') return execSandbox(params[0], params.slice(1).join(' '));
16
18
 
17
19
  console.log(chalk.red(`\n ❌ Bilinmeyen komut: ${action}\n`));
18
- console.log(chalk.gray(' Kullanım: natureco sandbox [list|create|destroy|exec]\n'));
20
+ console.log(chalk.gray(L(' Kullanım: natureco sandbox [list|create|destroy|exec]\n', ' Usage: natureco sandbox [list|create|destroy|exec]\n')));
19
21
  process.exit(1);
20
22
  }
21
23
 
@@ -80,7 +82,7 @@ function createSandbox(name) {
80
82
 
81
83
  function destroySandbox(name) {
82
84
  if (!name) {
83
- console.log(chalk.red('\n ❌ Sandbox name gerekli\n'));
85
+ console.log(chalk.red(L('\n ❌ Sandbox name gerekli\n', '\n ❌ Sandbox name required\n')));
84
86
  process.exit(1);
85
87
  }
86
88
 
@@ -98,8 +100,8 @@ function destroySandbox(name) {
98
100
 
99
101
  function execSandbox(name, command) {
100
102
  if (!name || !command) {
101
- console.log(chalk.red('\n ❌ Sandbox name ve command gerekli\n'));
102
- console.log(chalk.gray(' Kullanım: natureco sandbox exec <name> <command>\n'));
103
+ console.log(chalk.red(L('\n ❌ Sandbox name ve command gerekli\n', '\n ❌ Sandbox name and command required\n')));
104
+ console.log(chalk.gray(L(' Kullanım: natureco sandbox exec <name> <command>\n', ' Usage: natureco sandbox exec <name> <command>\n')));
103
105
  process.exit(1);
104
106
  }
105
107
 
@@ -1,5 +1,7 @@
1
1
  const chalk = require('chalk');
2
2
  const tui = require('../utils/tui');
3
+ const { getLang: _gl } = require('../utils/i18n');
4
+ const L = (tr, en) => (_gl() === 'en' ? en : tr);
3
5
  const F = require('../utils/format');
4
6
  const { getConfig, saveConfig } = require('../utils/config');
5
7
 
@@ -16,7 +18,7 @@ function secrets(args) {
16
18
  if (action === 'apply') return applySecrets();
17
19
 
18
20
  console.log(chalk.red(`\n ❌ Bilinmeyen komut: ${action}\n`));
19
- console.log(chalk.gray(' Kullanım: natureco secrets [list|set|get|unset|audit|reload|configure|apply]\n'));
21
+ console.log(chalk.gray(L(' Kullanım: natureco secrets [list|set|get|unset|audit|reload|configure|apply]\n', ' Usage: natureco secrets [list|set|get|unset|audit|reload|configure|apply]\n')));
20
22
  process.exit(1);
21
23
  }
22
24
 
@@ -42,9 +44,9 @@ function listSecrets() {
42
44
  });
43
45
 
44
46
  console.log('\n' + tui.table(rows, [
45
- { key: 'key', label: 'İsim', minWidth: 24, render: r => tui.styled(r.key, { color: tui.PALETTE.primary, bold: true }) },
46
- { key: 'masked', label: 'Maskelenmiş', minWidth: 16, render: r => tui.styled(r.masked, { color: tui.PALETTE.warning }) },
47
- { key: 'updated', label: 'Güncellendi', minWidth: 14, render: r => tui.C.muted(r.updated) },
47
+ { key: 'key', label: L('İsim', 'Name'), minWidth: 24, render: r => tui.styled(r.key, { color: tui.PALETTE.primary, bold: true }) },
48
+ { key: 'masked', label: L('Maskelenmiş', 'Masked'), minWidth: 16, render: r => tui.styled(r.masked, { color: tui.PALETTE.warning }) },
49
+ { key: 'updated', label: L('Güncellendi', 'Updated'), minWidth: 14, render: r => tui.C.muted(r.updated) },
48
50
  ], { borderStyle: 'round', zebra: true }));
49
51
  console.log('');
50
52
  }