natureco-cli 5.50.1 → 5.51.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/CHANGELOG.md CHANGED
@@ -2,6 +2,17 @@
2
2
 
3
3
  All notable changes to NatureCo CLI will be documented in this file.
4
4
 
5
+ ## [5.51.0] - 2026-07-10 — "PERF: basit istek 2.698 token — %45 daha ucuz (skill keşfi isteğe bağlı)"
6
+
7
+ ### Changed
8
+ - **Gerçek ölçüm: "merhaba" prompt'u 4.883 → 2.698 token** (v5.42 öncesine göre toplam %86 iniş). Bölüm bazlı ölçüm yapıldı ve üç büyük kalem vuruldu:
9
+ - **Skill index (1.468 → ~40 token):** 319 skill'in isim listesi artık sysMsg'e GÖMÜLMÜYOR; tek satır ipucu var. Yeni **`skill_find(query)`** aracı (foldTr'li Türkçe-güvenli arama) ile ajan gerektiğinde arar, `skill_view(name)` ile yükler — progressive disclosure 2. seviye. Eski davranış env ile: `NATURECO_SKILL_INDEX=names|full`.
10
+ - **Araç tanıtımları (~892 → ~540 token)** ve **kurallar (~725 → ~405 token):** her kuralın öğrettiği ders korunarak metinler sıkıştırıldı (cron-daemon dürüstlüğü, kayıt kalitesi, bekleyen işler, "internet erişimim yok deme"...).
11
+ - E2E doğrulama (davranış bozulmadı): skill keşfi (ajan skill_find'ı kendisi çağırıp seo-optimization'ı buldu), dosya yazma (write_file ✓), hafıza recall ("Sen Gencay'sın, ben Hinata" ✓). **630 test yeşil** (+7 yeni: skill_find + yeni indeks varsayılanı).
12
+
13
+ ### Added
14
+ - `src/tools/skill_find.js` — isim+açıklama üzerinde anahtar kelime skorlamalı skill arama (agentic allowlist'e eklendi).
15
+
5
16
  ## [5.50.1] - 2026-07-10 — "PERF: öz-bilgi bloğu sıkıştırıldı (~%55 daha az token)"
6
17
 
7
18
  ### Changed
package/SELF.md CHANGED
@@ -56,9 +56,11 @@
56
56
  ### 4. Skill sistemi
57
57
  - Yerleşikler: paket kökünde `skills/` (her biri `<ad>/SKILL.md`, YAML frontmatter).
58
58
  Kullanıcınınkiler: `~/.natureco/skills/`. Proje: `./.natureco/skills/`.
59
- - İndeks: `src/utils/skill-index.js` (`_discoverSkills`, `buildSkillIndex` — 60+
60
- skill'de KOMPAKT isim listesi üretir, token şişmesin diye; `NATURECO_SKILL_INDEX` env).
61
- - Yükleme: ajan `skill_view` aracıyla (progressive disclosure). CLI: `src/commands/skills.js`
59
+ - İndeks: `src/utils/skill-index.js` (`buildSkillIndex` — 60+ skill'de sysMsg'e yalnız
60
+ TEK SATIR ipucu gider; isim listesi bile gömülmez. `NATURECO_SKILL_INDEX` env:
61
+ off|names|full ile eski davranışlar açılır).
62
+ - Keşif: ajan `skill_find(query)` ile arar (`src/tools/skill_find.js`, foldTr'li),
63
+ `skill_view(name)` ile yükler (progressive disclosure). CLI: `src/commands/skills.js`
62
64
  + `src/utils/skills.js` (list/install/remove; indirme allowlist'i `skills-allowlist.json`).
63
65
  - Görünürlük bağlantıları: `~/.natureco/skills-builtin` ve `~/.natureco/tools`
64
66
  (junction/symlink, `src/utils/builtin-links.js`).
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "natureco-cli",
3
- "version": "5.50.1",
3
+ "version": "5.51.0",
4
4
  "description": "OpenClaw'dan daha güvenli, daha hızlı, daha ucuz AI agent CLI. Multi-agent, self-evolving skills, audit log, maliyet optimizasyonu ve NatureCo platform-native.",
5
5
  "bin": {
6
6
  "natureco": "bin/natureco.js"
@@ -22,7 +22,7 @@ const os = require('os');
22
22
  // digerleri → allowlist/full moda gore). Yani keyfi/yikici komut calismaz.
23
23
  // Diger ~85 arac (discord, telegram, cron, browser...) bilerek DISARIDA.
24
24
  const DEFAULT_ALLOWED = [
25
- 'write_file', 'read_file', 'edit_file', 'skill_view', 'bash', 'file_search', 'list_dir', 'grep_search',
25
+ 'write_file', 'read_file', 'edit_file', 'skill_view', 'skill_find', 'bash', 'file_search', 'list_dir', 'grep_search',
26
26
  'memory_write', 'memory_tree', 'cron_create', 'duckduckgo', 'web_search', 'todo_write',
27
27
  'git', 'http_request', 'notebook_edit', 'clarify', 'code_execution',
28
28
  // orchestration + planlama (guvenli: sub_agent = alt-LLM cagrisi, plan = metin+.md; shell/sistem yok)
@@ -0,0 +1,53 @@
1
+ /**
2
+ * skill_find — istek üzerine skill keşfi (v5.51 token optimizasyonu).
3
+ *
4
+ * Eskiden 319 skill'in İSİM LİSTESİ her istekte sysMsg'e gömülüyordu (~1.450 token).
5
+ * Artık sysMsg'de tek satırlık ipucu var; ajan görev bir uzmanlık istediğinde bu
6
+ * araçla arar (isim+açıklama üzerinde anahtar-kelime skorlaması, foldTr ile
7
+ * Türkçe-güvenli), sonra skill_view(name) ile yükler. Progressive disclosure 2. seviye.
8
+ */
9
+
10
+ const { _discoverSkills, _shorten } = require('../utils/skill-index');
11
+ const { foldTr } = require('../utils/tr-text');
12
+
13
+ module.exports = {
14
+ name: 'skill_find',
15
+ description: 'Görevle ilgili skill ara (isim + açıklama üzerinde anahtar kelime eşleşmesi). Bulduğun skill\'i skill_view(name) ile yükle.',
16
+ inputSchema: {
17
+ type: 'object',
18
+ properties: {
19
+ query: { type: 'string', description: 'Aranacak konu/anahtar kelimeler (ör. "seo audit", "video üretimi", "api tasarımı")' },
20
+ maxResults: { type: 'number', description: 'En fazla sonuç (varsayılan 8)' },
21
+ },
22
+ required: ['query'],
23
+ },
24
+ async execute({ query, maxResults = 8 }) {
25
+ if (!query || !String(query).trim()) {
26
+ return { success: false, error: 'query gerekli' };
27
+ }
28
+ const words = foldTr(String(query)).split(/\s+/).filter(w => w.length > 1);
29
+ const skills = _discoverSkills();
30
+
31
+ const scored = skills.map(s => {
32
+ const name = foldTr(s.name || '');
33
+ const desc = foldTr(s.description || '');
34
+ let score = 0;
35
+ for (const w of words) {
36
+ if (name.includes(w)) score += 3; // isimde geçmesi en güçlü sinyal
37
+ else if (desc.includes(w)) score += 1;
38
+ }
39
+ return { s, score };
40
+ }).filter(r => r.score > 0)
41
+ .sort((a, b) => b.score - a.score)
42
+ .slice(0, Math.max(1, Math.min(20, maxResults)));
43
+
44
+ if (scored.length === 0) {
45
+ return { success: true, results: [], note: 'Eşleşen skill yok — farklı anahtar kelimelerle dene ya da skill olmadan araçlarla ilerle.' };
46
+ }
47
+ return {
48
+ success: true,
49
+ results: scored.map(r => ({ name: r.s.name, description: _shorten(r.s.description, 100), category: r.s.category })),
50
+ note: 'Kullanmak için: skill_view(name)',
51
+ };
52
+ },
53
+ };
@@ -271,46 +271,34 @@ async function workflow(params) {
271
271
  memCtx ? '\nKullanici bilgisi:\n' + memCtx : '',
272
272
  '\n\nOrtam:\n- Isletim sistemi: ' + process.platform + '\n- Kullanici home: ' + os.homedir() + '\n- Masaustu: ' + desktop + '\n- Calisma dizini: ' + process.cwd() + selfInfo,
273
273
  '\n\nArac cagirmak icin TAM olarak su formati kullan:\n<minimax:tool_call>\n<invoke name="ARAC_ADI">\n<parameter name="PARAM">DEGER</parameter>\n</invoke>\n</minimax:tool_call>',
274
- '\n\nKullanabilecegin araclar:',
275
- '- write_file: dosya olustur/uzerine yaz. parametreler: path (TAM yol), content (dosyanin TAM icerigi). Kod/oyun/site isteniyorsa TUM icerigi content icine yaz, kisaltma.',
276
- '- read_file: dosya oku. parametre: path',
277
- '- edit_file: MEVCUT dosyada metin degistir. parametreler: path, old_string (birebir mevcut metin), new_string. Bir dosyanin bir kismini degistirirken write_file yerine bunu kullan (tum dosyayi yeniden yazma).',
278
- '- file_search: glob ile dosya bul. parametre: pattern (orn. "**/*.js", "src/**/*.json").',
279
- '- list_dir: dizin icerigini listele. parametre: path',
280
- '- bash: kabuk komutu calistir (npm, git, node, python, test, ls, grep/findstr, mkdir...). parametre: command. Guvenli komutlar dogrudan calisir; yikici/tehlikeli komutlar guvenlik politikasiyla engellenir. Icerik aramasi icin grep/findstr kullan.',
281
- '- skill_view: gorevle ilgili bir skill yukle. parametre: name',
282
- '- cron_create: zamanlanmis/periyodik gorev (cron) olustur. parametreler: name, schedule (cron ifadesi orn. "0 9 * * *" ya da "every day 9am" gibi preset), command, description.',
283
- '- duckduckgo_search: internetten anlik arama yap (API key gerekmez, HER ZAMAN calisir). parametreler: query, maxResults.',
284
- '- web_search: internetten arama (Tavily API key ayarliysa daha zengin sonuc; ayarli degilse hata doner o zaman duckduckgo_search kullan). parametreler: query, maxResults.',
285
- '- todo_write: gorev/yapilacaklar listesi yonet. parametre: action (list/add/update/start/done/remove/clear), + action\'a gore diger alanlar.',
286
- '- grep_search: dosya ICERIGINDE metin/desen ara (kod tabaninda hizli arama). parametreler: pattern, path, includePattern (opsiyonel glob), maxResults. (bash grep yerine bunu tercih et.)',
287
- '- git: git islemi. parametreler: operation (status/diff/log/branches/add/commit), args, message (commit icin). (Basit git icin bunu kullan.)',
288
- '- http_request: HTTP istegi at (API cagrisi, webhook, veri cekme). parametreler: url, method, headers, body.',
289
- '- code_execution: kod parcasi calistir (sandboxli). parametreler: code, language (python/node/bash).',
290
- '- sub_agent: bir ALT-GOREVI bagimsiz bir alt-agent\'a devret (kendi LLM cagrisini yapar, sonucu doner). parametreler: task (zorunlu), context (ops.), maxTokens (ops.). Paralel arastirma, odakli alt-problem, ya da ana gorevi bolup parcalari delege etmek icin. Birden fazla cagirarak orchestrate edebilirsin.',
291
- '- plan: karmasik/cok-adimli bir gorev icin ONCE plan cikar (SADECE plan metni uretir, HICBIR islem yapmaz; ~/.natureco/plans/ altina kaydeder). parametreler: action ("create" veya "list"), task (create icin), depth ("minimal"/"detailed"). Kullanici "plan yap / once planla / adimlari cikar / yol haritasi" derse bunu kullan.',
292
- '- notebook_edit: Jupyter (.ipynb) hucre duzenle. parametreler: filePath, ...',
293
- '- clarify: kullaniciya netlestirme sorusu sor (belirsizlik varsa). parametreler: question, options.',
294
- '- calendar_add / reminder_add / notes_add / mac_notify: macOS Takvim/Hatirlatici/Notlar/bildirim (kullanici macOS ise; degilse arac "sadece macOS" der).',
295
- '- image_generation: gorsel uret. parametre: prompt, size. | text_to_speech: metni sese cevir (text). | speech_to_text: sesi metne cevir (audioPath).',
296
- '- memory_write: HIZLI tek bilgi kaydet (isim, kisa tercih). parametreler: username ("' + memUser + '"), fact, category. YENI oturumda hatirlanir.',
297
- '- memory_tree: AGAC-HAFIZA — zengin/kategorize kalici bilgi (proje, karar, teknik not, kisisel detay). action: index|read|search|append; username="' + memUser + '"; append icin: root (1-kisisel|2-teknik|3-kararlar) + branch (dal basligi) + content (yaprak). YENI oturumda hatirlanir.',
274
+ '\n\nKullanabilecegin araclar (p: = parametreler):',
275
+ '- write_file: dosya olustur/uzerine yaz. p: path (TAM yol), content (dosyanin TAM icerigi, kisaltma yok).',
276
+ '- read_file: oku (p: path) | list_dir: dizini listele (p: path) | file_search: glob ile dosya bul (p: pattern orn "**/*.js").',
277
+ '- edit_file: MEVCUT dosyada metin degistir. p: path, old_string (birebir mevcut), new_string. Kismi degisiklikte write_file yerine bunu kullan.',
278
+ '- grep_search: dosya ICERIGINDE desen ara (bash grep yerine bunu tercih et). p: pattern, path, includePattern?, maxResults?.',
279
+ '- bash: kabuk komutu (npm/git/node/python/test/mkdir...). p: command. Yikici/tehlikeli komutlar politikayla engellenir.',
280
+ '- skill_find: skill ara (p: query) skill_view: skill yukle (p: name).',
281
+ '- cron_create: zamanlanmis gorev. p: name, schedule ("0 9 * * *" veya "every day 9am"), command, description.',
282
+ '- duckduckgo_search: internet aramasi, API key GEREKMEZ, her zaman calisir. p: query, maxResults | web_search: Tavily key ayarliysa; degilse duckduckgo kullan.',
283
+ '- todo_write: aktif gorev listesi. p: action (list/add/update/start/done/remove/clear) + alanlar.',
284
+ '- git: git islemi (p: operation/args/message) | http_request: HTTP istegi (p: url, method, headers, body) | code_execution: sandbox kod (p: code, language).',
285
+ '- sub_agent: alt-gorevi bagimsiz alt-agent\'a devret (p: task, context?, maxTokens?). Paralel/odakli isler; coklu cagriyla orchestrate edebilirsin.',
286
+ '- plan: cok-adimli gorevde SADECE plan metni uret, islem yapmaz (p: action create/list, task, depth). "once planla / yol haritasi" istenirse.',
287
+ '- notebook_edit: .ipynb hucre duzenle (p: filePath...) | clarify: netlestirme sorusu sor (p: question, options).',
288
+ '- calendar_add / reminder_add / notes_add / mac_notify: macOS asistan islevleri (macOS degilse arac soyler).',
289
+ '- image_generation (p: prompt, size) | text_to_speech (p: text) | speech_to_text (p: audioPath).',
290
+ '- memory_write: HIZLI tek bilgi kaydet (p: username="' + memUser + '", fact, category) | memory_tree: AGAC-HAFIZA, zengin kalici bilgi (p: action index|read|search|append|remove, username="' + memUser + '", append icin root 1-kisisel|2-teknik|3-kararlar + branch + content). Ikisi de YENI oturumda hatirlanir.',
298
291
  '\nKurallar:',
299
- '- Kullanici kalici bilgi paylasirsa (isim, tercih, parola, proje, karar, onemli detay) ya da "hatirla / not al / kaydet" derse HEMEN KAYDET (username="' + memUser + '"): kisa tek bilgi → memory_write; zengin/kategorize bilgi → memory_tree(append, dogru root/branch). Trivial/gecici seyleri kaydetme.',
300
- '- KAYIT KALITESI (onemli): fact\'i kullanicinin SOYLEDIGI ANLAMI ve SPESIFIK DEGERLERI koruyarak yaz. Kod/isim/sayi/tarih/parola gibi degerleri AYNEN gecir (or. "gizli kod adi ONYX-7" → fact: "Projenin gizli kod adi ONYX-7" — "ONYX-7"yi "onyx" yapma, kisaltma). Neyin ne oldugunu DOGRU etiketle: proje kod adi ≠ kullanici adi, sifre ≠ isim. Yanlis ozetleme yeni oturumda yanlis hatirlamaya yol acar.',
301
- '- Kullaniciya ozel bir sey sorulunca (gecmis, proje, tercih, karar) once memory_tree(search/read) ile ilgili kok/dali OKU (hedefli, tum hafizayi degil). Tek primary: bilgi tek yerde yasar; digerine sadece "bkz:". Credential/secret ASLA duz metin.',
302
- '- Bir is YARIM kalirsa ya da kullanici "sonra / yarin / daha sonra yapalim" derse memory_tree(action:append, root:"3-kararlar", branch:"Bekleyen İşler", content:"...") ile kaydet — yeni oturum basinda otomatik hatirlatilir. Bir bekleyen is TAMAMLANINCA memory_tree(action:remove, root:"3-kararlar", query:"<anahtar kelime>") ile kaldir.',
303
- '- Guncel/internet bilgisi gerektiren bir soru gelirse ONCE duckduckgo_search ile ara ("internet erisimim yok" DEME — bu arac her zaman calisir, API key gerekmez).',
304
- '- "Gorev listesi / yapilacaklar / todo" istenirse todo_write kullan (memory_tree DEGIL — o kalici bilgi icin, todo_write ise aktif is takibi icin).',
305
- '- Zamanlanmis/periyodik/tekrarlayan gorev (cron, "her gun/hafta X yap", hatirlatici) istenirse SADECE cron_create arac ini kullan; bash ile crontab/schtasks/Register-ScheduledTask DUZENLEME (tutarsiz olur, "natureco cron list" ile gorunmez). cron_create sonrasi kullaniciya ACIKCA soyle: gorevin fiilen tetiklenmesi icin arka plan servisinin calisiyor olmasi gerekir ("natureco daemon start" ya da "natureco daemon install"); bu adim atlanirsa gorev database\'e kaydedilir ama calismaz. Bunu SOYLEMEDEN "olusturuldu, calisacak" gibi kesin basari iddia etme.',
306
- '- MEVCUT bir dosyayi degistirmeden ONCE read_file ile oku; sonra edit_file ile hedefli degisiklik yap (tum dosyayi write_file ile ezme).',
307
- '- Bir seyi nerede oldugunu bilmiyorsan once file_search/list_dir/bash(grep) ile kesfet.',
308
- '- Kod yazdiktan/degistirdikten sonra gerektiginde bash ile calistir/test et (orn. "node dosya.js", "npm test"); hata cikarsa duzelt.',
309
- '- Birden fazla dosya gerekiyorsa her biri icin AYRI write_file cagir.',
310
- '- Kullanici "masaustu"/"desktop" dediyse ve tam yol vermediyse dosyayi buraya yaz: ' + desktop,
311
- '- Goreceli yol yerine TAM yol kullan.',
312
- '- Arac sonuclari <tool_results> icinde geri gelir; gorev bitince ARAC CAGIRMADAN tek cumlelik ozet yaz.',
313
- '- Basit sohbet/selamlasma ise arac cagirma, dogrudan kisa yanit ver.',
292
+ '- Kalici bilgi paylasilirsa ya da "hatirla/not al/kaydet" denirse HEMEN kaydet (username="' + memUser + '"): kisa → memory_write; zengin → memory_tree(append, dogru root/branch). Trivial/gecici seyleri kaydetme.',
293
+ '- KAYIT KALITESI: fact\'i soylenen ANLAM ve SPESIFIK DEGERLERLE yaz — kod/isim/sayi/tarih AYNEN ("kod adi ONYX-7"yi "onyx" yapma); etiketi dogru koy (proje kodu ≠ kullanici adi). Yanlis ozet = yeni oturumda yanlis hatirlama.',
294
+ '- Kisiye ozel soru (gecmis/proje/tercih) ONCE memory_tree(search/read) ile ilgili dali oku. Bilgi tek yerde yasar; credential ASLA duz metin.',
295
+ '- Yarim kalan is / "sonra yapalim" memory_tree(append, root:"3-kararlar", branch:"Bekleyen İşler") — yeni oturumda otomatik hatirlatilir; tamamlaninca memory_tree(remove) ile kaldir.',
296
+ '- Guncel/internet bilgisi ONCE duckduckgo_search ("internet erisimim yok" DEME).',
297
+ '- Gorev listesi/todo todo_write (memory_tree DEGIL).',
298
+ '- Zamanlanmis/tekrarlayan is SADECE cron_create (bash ile crontab/schtasks DUZENLEME "natureco cron list"te gorunmez). Sonrasinda kullaniciya MUTLAKA soyle: fiilen calismasi icin "natureco daemon start" (veya install) gerekir; bunu soylemeden kesin basari iddia etme.',
299
+ '- Dosya degistirmeden ONCE read_file ile oku, edit_file ile hedefli degistir. Yerini bilmiyorsan file_search/grep_search ile kesfet.',
300
+ '- Kod yazinca/degistirince bash ile calistir/test et, hata varsa duzelt. Coklu dosya = her biri icin AYRI write_file. Hep TAM yol; "masaustu" = ' + desktop + '.',
301
+ '- Arac sonuclari <tool_results> icinde doner; is bitince arac cagirmadan tek cumlelik ozet yaz. Basit sohbette arac cagirma, dogrudan yanitla.',
314
302
  execFull ? '- Kullanici uygulama ac / tarayici kontrol / muzik cal / ekran / GUI istediyse yukaridaki computer-use araclarini KULLAN — "yapamam/engellendi" DEME, dogrudan ilgili araci cagir.' : '',
315
303
  fullToolsBlock,
316
304
  treeDigest ? ('\n\nBILDIGIN KALICI HAFIZA (bu kullaniciya ait, onceki oturumlardan hatirladiklarin; kullaniciya ozel bir sey sorulursa ONCE BUNU KULLAN — dosya arama, uydurma):\n' + treeDigest) : '',
@@ -78,10 +78,17 @@ function buildSkillIndex() {
78
78
  if (mode === 'off') return '';
79
79
  const skills = _discoverSkills();
80
80
  if (skills.length === 0) return '';
81
- // Cok skill (>60) → KOMPAKT isim-listesi (kategorili, virgullu): en dusuk token.
82
- // Az skill → isim + kisa aciklama. Kullanici 'full'/'names' ile ezebilir.
83
81
  const many = skills.length > 60;
84
- const compact = mode === 'names' || (many && mode !== 'full');
82
+ // v5.51: cok skill'de VARSAYILAN artik tek satirlik IPUCU (progressive disclosure
83
+ // 2. seviye): 319 ismin listesi bile ~1.450 token tutuyordu. Ajan gorev bir
84
+ // uzmanlik istediginde skill_find(query) ile arar, skill_view(name) ile yukler.
85
+ // Eski davranislar env ile durur: names (isim listesi), full (isim+aciklama).
86
+ if (many && mode !== 'full' && mode !== 'names') {
87
+ return `## Skills: ${skills.length} adet hazir skill var (SEO, tasarim, video, guvenlik, kod...). ` +
88
+ 'Gorev bir uzmanlik/sablon istiyorsa ONCE skill_find(query) ile ara, buldugunu skill_view(name) ile yukle.';
89
+ }
90
+ // Az skill → isim + kisa aciklama; 'names' → sadece isimler.
91
+ const compact = mode === 'names';
85
92
  const byCategory = {};
86
93
  for (const s of skills) {
87
94
  if (!byCategory[s.category]) byCategory[s.category] = [];