beast-agent 0.27.0 → 0.28.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/package.json +1 -1
- package/src/agent/engine.js +91 -53
- package/src/agent/obscura.js +245 -0
- package/src/agent/skills.js +14 -10
- package/src/agent/tools.js +105 -51
- package/src/main.js +47 -22
- package/src/preload.js +5 -3
- package/src/renderer/i18n.js +46 -24
- package/src/renderer/renderer.js +106 -38
- package/src/renderer/style.css +11 -0
- package/tests/bg-jobs.test.js +71 -3
- package/tests/obscura.test.js +124 -0
package/src/agent/tools.js
CHANGED
|
@@ -7,6 +7,7 @@ const https = require('https');
|
|
|
7
7
|
const { execFile } = require('child_process');
|
|
8
8
|
const { spawn } = require('child_process');
|
|
9
9
|
const research = require('./research');
|
|
10
|
+
const obscura = require('./obscura');
|
|
10
11
|
|
|
11
12
|
const MAX_CMD_OUTPUT = 16000;
|
|
12
13
|
const MAX_FILE_CHARS = 200000;
|
|
@@ -627,7 +628,7 @@ const definitions = [
|
|
|
627
628
|
function: {
|
|
628
629
|
name: 'web_search',
|
|
629
630
|
description:
|
|
630
|
-
'FAST web search with an automatic chain: built-in browser
|
|
631
|
+
'FAST web search with an automatic chain (order is configurable in Ayarlar → Web Arama): built-in browser (real Chromium searching GOOGLE directly with AI Mode — no bot protection; the response may include an `ai` field holding Google\'s own AI answer), Obscura stealth headless browser (anti-detect; searches DuckDuckGo, installed automatically and ACTIVE by default), TinyFish API (only if a key is configured), then Python multi-engine (ddgs / DuckDuckGo+Bing+Mojeek). If the browser hits CAPTCHA/unusual traffic it is skipped for 10 minutes and the next engine takes over. Returns {ai?, results[{title,url,snippet}]}. Use when fresh or external info is needed; skip for things you already know.',
|
|
631
632
|
parameters: {
|
|
632
633
|
type: 'object',
|
|
633
634
|
properties: {
|
|
@@ -758,13 +759,9 @@ async function exec(name, args, ctx) {
|
|
|
758
759
|
case 'web_search': {
|
|
759
760
|
const q = String(args.query || '');
|
|
760
761
|
const n = Number(args.max_results) || 8;
|
|
761
|
-
/*
|
|
762
|
-
|
|
763
|
-
|
|
764
|
-
if (!r || !r.ok || !(r.results || []).length) {
|
|
765
|
-
const exa = await exaSearch(q, n, ctx.signal);
|
|
766
|
-
if (exa) return JSON.stringify(exa);
|
|
767
|
-
}
|
|
762
|
+
/* sıralı zincir (obscura/tinyfish/python — dahili tarayıcı engine
|
|
763
|
+
tarafındaki hook'tan gelir); Exa KALDIRILDI */
|
|
764
|
+
const r = await searchChainWeb(q, n, { signal: ctx.signal });
|
|
768
765
|
return JSON.stringify(r);
|
|
769
766
|
}
|
|
770
767
|
case 'deep_search': {
|
|
@@ -772,7 +769,7 @@ async function exec(name, args, ctx) {
|
|
|
772
769
|
Gizli tarayıcı okuması engine.research hook'undan gelir (main process). */
|
|
773
770
|
const r = await research.deepSearch(
|
|
774
771
|
args,
|
|
775
|
-
{ search: (q) =>
|
|
772
|
+
{ search: (q) => searchChainWeb(q, 10, { signal: ctx.signal }) },
|
|
776
773
|
ctx.signal
|
|
777
774
|
);
|
|
778
775
|
return JSON.stringify(r);
|
|
@@ -836,53 +833,101 @@ async function exec(name, args, ctx) {
|
|
|
836
833
|
}
|
|
837
834
|
}
|
|
838
835
|
|
|
839
|
-
/* ----------
|
|
840
|
-
|
|
841
|
-
|
|
842
|
-
|
|
836
|
+
/* ---------- Sıralı arama zinciri (Ayarlar → Web Arama'dan değiştirilir) ----------
|
|
837
|
+
Motorlar: browser (dahili Chromium → Google) · obscura (stealth headless →
|
|
838
|
+
DuckDuckGo) · tinyfish (API, anahtar gerekir) · python (ddgs/DDG+Bing+Mojeek).
|
|
839
|
+
Sıra + aç/kapa ayarı settings.json'da (searchChain) saklanır; Obscura
|
|
840
|
+
varsayılan AKTİF. Tarayıcı CAPTCHA/trafik verirse 10 dk atlanır. */
|
|
841
|
+
const SEARCH_ENGINE_IDS = ['browser', 'obscura', 'tinyfish', 'python'];
|
|
842
|
+
const DEFAULT_SEARCH_CHAIN = SEARCH_ENGINE_IDS.map((id) => ({ id, on: true }));
|
|
843
|
+
|
|
844
|
+
let _searchChain = DEFAULT_SEARCH_CHAIN.map((x) => ({ ...x }));
|
|
845
|
+
let _obscuraEnabled = true; /* Obscura varsayılan AKTİF */
|
|
846
|
+
let _browserBanUntil = 0;
|
|
847
|
+
|
|
848
|
+
function normalizeSearchChain(list) {
|
|
849
|
+
const arr = Array.isArray(list) ? list : [];
|
|
850
|
+
const rows = [];
|
|
851
|
+
const seen = new Set();
|
|
852
|
+
for (const item of arr) {
|
|
853
|
+
const id = String((item && item.id) || item || '').trim();
|
|
854
|
+
if (!SEARCH_ENGINE_IDS.includes(id) || seen.has(id)) continue;
|
|
855
|
+
seen.add(id);
|
|
856
|
+
rows.push({ id, on: !(item && item.on === false) });
|
|
857
|
+
}
|
|
858
|
+
for (const id of SEARCH_ENGINE_IDS) {
|
|
859
|
+
if (!seen.has(id)) rows.push({ id, on: true }); /* listede eksik motor varsayılan AÇIK */
|
|
860
|
+
}
|
|
861
|
+
/* obscura varsayılan AKTİF; zincir boş kalmasın: hepsi kapalıysa browser'ı aç */
|
|
862
|
+
if (!rows.some((r) => r.on)) {
|
|
863
|
+
const b = rows.find((r) => r.id === 'browser');
|
|
864
|
+
if (b) b.on = true;
|
|
865
|
+
}
|
|
866
|
+
return rows;
|
|
867
|
+
}
|
|
843
868
|
|
|
844
|
-
function
|
|
845
|
-
|
|
869
|
+
function setSearchChain(list) {
|
|
870
|
+
_searchChain = normalizeSearchChain(list);
|
|
871
|
+
return _searchChain;
|
|
846
872
|
}
|
|
847
873
|
|
|
848
|
-
|
|
849
|
-
|
|
850
|
-
|
|
851
|
-
|
|
852
|
-
|
|
853
|
-
|
|
854
|
-
|
|
855
|
-
|
|
856
|
-
|
|
857
|
-
|
|
858
|
-
|
|
859
|
-
|
|
860
|
-
|
|
861
|
-
|
|
862
|
-
|
|
863
|
-
|
|
864
|
-
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
|
|
868
|
-
|
|
869
|
-
|
|
870
|
-
|
|
871
|
-
|
|
872
|
-
|
|
873
|
-
|
|
874
|
-
|
|
875
|
-
|
|
876
|
-
|
|
877
|
-
|
|
878
|
-
|
|
874
|
+
function setSearchObscuraEnabled(v) {
|
|
875
|
+
_obscuraEnabled = v !== false;
|
|
876
|
+
}
|
|
877
|
+
|
|
878
|
+
function getSearchChain() {
|
|
879
|
+
return _searchChain.map((x) => ({ ...x }));
|
|
880
|
+
}
|
|
881
|
+
|
|
882
|
+
function browserBanned() {
|
|
883
|
+
return Date.now() < _browserBanUntil;
|
|
884
|
+
}
|
|
885
|
+
|
|
886
|
+
function banBrowser(minutes = 10) {
|
|
887
|
+
_browserBanUntil = Date.now() + minutes * 60 * 1000;
|
|
888
|
+
}
|
|
889
|
+
|
|
890
|
+
/* Zinciri sırayla koştur: her motor boş/hata dönerse sıradakine geç.
|
|
891
|
+
browser motoru yalnız engine'den gelir (hook); araç-bağımsız çağrılarda atlanır. */
|
|
892
|
+
async function searchChainWeb(query, maxResults, { signal, browser } = {}) {
|
|
893
|
+
const q = String(query || '').trim().slice(0, 400);
|
|
894
|
+
if (!q) return { ok: false, error: 'boş sorgu' };
|
|
895
|
+
const cap = Math.max(1, Math.min(12, Number(maxResults) || 8));
|
|
896
|
+
let out = null;
|
|
897
|
+
const banned = browserBanned();
|
|
898
|
+
for (const row of _searchChain) {
|
|
899
|
+
if (out && out.ok && (out.results || []).length) break;
|
|
900
|
+
if (!row.on) continue;
|
|
901
|
+
try {
|
|
902
|
+
if (row.id === 'browser') {
|
|
903
|
+
if (typeof browser !== 'function' || banned) continue;
|
|
904
|
+
out = await browser();
|
|
905
|
+
if (!out || !out.ok || !(out.results || []).length) {
|
|
906
|
+
banBrowser(); /* tarayıcı sorunlu — 10 dk atla, alternatifler devrede */
|
|
907
|
+
out = null;
|
|
908
|
+
}
|
|
909
|
+
} else if (row.id === 'obscura') {
|
|
910
|
+
if (!_obscuraEnabled) continue;
|
|
911
|
+
out = await obscura.obscuraSearch(q, { maxResults: cap, signal });
|
|
912
|
+
} else if (row.id === 'tinyfish') {
|
|
913
|
+
out = await tinyfishSearch(q, cap, signal);
|
|
914
|
+
} else if (row.id === 'python') {
|
|
915
|
+
out = await webSearchFast(q, { maxResults: cap, signal });
|
|
916
|
+
}
|
|
917
|
+
} catch {
|
|
918
|
+
out = null;
|
|
919
|
+
}
|
|
920
|
+
if (out && out.ok && !(out.results || []).length) out = null; /* boş → sıradaki motor */
|
|
921
|
+
}
|
|
922
|
+
if (out && out.ok && banned && (out.results || []).length) {
|
|
923
|
+
out.note = 'dahili tarayıcı 10 dk askıda (CAPTCHA/trafik) — alternatif motor kullanıldı';
|
|
879
924
|
}
|
|
925
|
+
return out || { ok: false, error: 'web arama başarısız — tüm motorlar boş döndü' };
|
|
880
926
|
}
|
|
881
927
|
|
|
882
|
-
/* ---------- TinyFish (
|
|
928
|
+
/* ---------- TinyFish (anahtar girilirse zincirdeki kendi sırasında) ----------
|
|
883
929
|
GET https://api.search.tinyfish.ai?query=... · Header: X-API-Key
|
|
884
|
-
|
|
885
|
-
hata/sonuç yoksa eski zincir (tarayıcı → python çoklu-motor → Exa) devam eder. */
|
|
930
|
+
Anahtar yoksa bu motor otomatik atlanır; sıradaki motor devreye girer. */
|
|
886
931
|
let _tinyfishKey = null;
|
|
887
932
|
|
|
888
933
|
function setTinyfishKey(key) {
|
|
@@ -936,10 +981,19 @@ module.exports = {
|
|
|
936
981
|
webSearchFast,
|
|
937
982
|
seedScript,
|
|
938
983
|
bundledScriptPath,
|
|
939
|
-
|
|
940
|
-
|
|
984
|
+
/* arama zinciri (sıra + aç/kapa Ayarlar → Web Arama'dan) */
|
|
985
|
+
SEARCH_ENGINE_IDS,
|
|
986
|
+
DEFAULT_SEARCH_CHAIN,
|
|
987
|
+
setSearchChain,
|
|
988
|
+
setSearchObscuraEnabled,
|
|
989
|
+
getSearchChain,
|
|
990
|
+
searchChainWeb,
|
|
991
|
+
browserBanned,
|
|
992
|
+
banBrowser,
|
|
941
993
|
setTinyfishKey,
|
|
942
994
|
tinyfishSearch,
|
|
995
|
+
/* obscura geçişi */
|
|
996
|
+
obscura,
|
|
943
997
|
/* python altyapısı */
|
|
944
998
|
ensurePython,
|
|
945
999
|
findSystemPython,
|
package/src/main.js
CHANGED
|
@@ -150,7 +150,9 @@ function startNpmUpdateWatch() {
|
|
|
150
150
|
check();
|
|
151
151
|
setInterval(check, 6 * 60 * 60 * 1000);
|
|
152
152
|
}
|
|
153
|
-
const
|
|
153
|
+
const toolsMod = require('./agent/tools');
|
|
154
|
+
const { htmlToText, setSearchChain, setSearchObscuraEnabled, setTinyfishKey } = toolsMod;
|
|
155
|
+
const obscura = require('./agent/obscura');
|
|
154
156
|
const { waToolLine } = require('./agent/watext');
|
|
155
157
|
|
|
156
158
|
/* #3 merkezî log sistemine process-seviye hataları da düşsün */
|
|
@@ -219,8 +221,17 @@ let engine = null;
|
|
|
219
221
|
let settings = loadSettings();
|
|
220
222
|
ensureBeastCode();
|
|
221
223
|
startHealthServer(); /* splash/boot aşamasından itibaren /health ayakta */
|
|
222
|
-
try {
|
|
224
|
+
try { setSearchObscuraEnabled(settings.obscuraEnabled !== false); } catch {} /* Obscura varsayılan AKTİF */
|
|
225
|
+
try { setSearchChain(settings.searchChain); } catch {}
|
|
223
226
|
try { setTinyfishKey(settings.tinyfishKey || null); } catch {}
|
|
227
|
+
/* kurulumda Obscura da kurulsun: yoksa ARKA PLANDA otomatik indir (UI kilitlenmez) */
|
|
228
|
+
setTimeout(() => {
|
|
229
|
+
if (!obscura.obscuraInstalled()) {
|
|
230
|
+
obscura.installObscura().then((r) => {
|
|
231
|
+
console.log('[obscura]', r.ok ? 'kuruldu: ' + r.dir : 'kurulamadı: ' + (r.error || '?'));
|
|
232
|
+
}).catch((e) => console.log('[obscura] kurulamadı:', String((e && e.message) || e)));
|
|
233
|
+
}
|
|
234
|
+
}, 4000).unref?.();
|
|
224
235
|
let wa = null;
|
|
225
236
|
let waChats = new Map(); // jid -> aktif session id
|
|
226
237
|
let waHistory = new Map(); // jid -> [sid,...] bu sohbete ait tüm oturumlar
|
|
@@ -4118,7 +4129,7 @@ ipcMain.handle('agent:interrupt', (_e, sessionId) => {
|
|
|
4118
4129
|
desktopQueue.delete(String(sessionId));
|
|
4119
4130
|
}
|
|
4120
4131
|
} catch {}
|
|
4121
|
-
return engine.interrupt(sessionId);
|
|
4132
|
+
return engine.interrupt(sessionId, 'kullanıcı sohbetteki durdurma (■) düğmesiyle iptal etti');
|
|
4122
4133
|
});
|
|
4123
4134
|
|
|
4124
4135
|
/* ---------- masaüstü sohbet birleştirme ----------
|
|
@@ -4482,7 +4493,9 @@ ipcMain.handle('memory:get', () => memory.loadAll());
|
|
|
4482
4493
|
/* paralel ajanlar: canlı izleme (#14) */
|
|
4483
4494
|
ipcMain.handle('agents:list', () => engine.listBgJobs());
|
|
4484
4495
|
ipcMain.handle('agents:detail', (_e, id) => engine.bgDetail(id));
|
|
4485
|
-
ipcMain.handle('agents:cancel', (_e, id) => ({
|
|
4496
|
+
ipcMain.handle('agents:cancel', (_e, id) => ({
|
|
4497
|
+
ok: engine.interrupt(String(id || ''), 'kullanıcı Paralel Ajanlar panelinden (×) iptal etti'),
|
|
4498
|
+
}));
|
|
4486
4499
|
ipcMain.handle('ceo:get', () => !!engine.ceoMode);
|
|
4487
4500
|
ipcMain.handle('ceo:set', (_e, v) => {
|
|
4488
4501
|
settings.ceoMode = !!v;
|
|
@@ -5190,7 +5203,7 @@ ipcMain.handle('beastcode:stop', () => {
|
|
|
5190
5203
|
const sid = bcSessions.get(ideRoot());
|
|
5191
5204
|
if (!sid) return { ok: false };
|
|
5192
5205
|
let r = false;
|
|
5193
|
-
try { r = engine.interrupt(sid); } catch {}
|
|
5206
|
+
try { r = engine.interrupt(sid, 'kullanıcı Beast Code panelinden ■ ile durdurdu'); } catch {}
|
|
5194
5207
|
return { ok: !!r };
|
|
5195
5208
|
});
|
|
5196
5209
|
|
|
@@ -5211,26 +5224,38 @@ ipcMain.handle('think:set', (_e, v) => {
|
|
|
5211
5224
|
return engine.publicState();
|
|
5212
5225
|
});
|
|
5213
5226
|
|
|
5214
|
-
/*
|
|
5215
|
-
ipcMain.handle('
|
|
5216
|
-
|
|
5217
|
-
|
|
5218
|
-
|
|
5219
|
-
|
|
5220
|
-
|
|
5221
|
-
|
|
5222
|
-
|
|
5223
|
-
|
|
5224
|
-
|
|
5227
|
+
/* Obscura stealth headless tarayıcı (Ayarlar → Web Arama) */
|
|
5228
|
+
ipcMain.handle('obscura:get', () => ({
|
|
5229
|
+
installed: obscura.obscuraInstalled(),
|
|
5230
|
+
dir: obscura.obscuraDir(),
|
|
5231
|
+
enabled: settings.obscuraEnabled !== false,
|
|
5232
|
+
}));
|
|
5233
|
+
ipcMain.handle('obscura:install', async () => {
|
|
5234
|
+
try {
|
|
5235
|
+
const r = await obscura.installObscura();
|
|
5236
|
+
return { ok: !!r.ok, dir: r.dir || obscura.obscuraDir(), error: r.error || null };
|
|
5237
|
+
} catch (e) {
|
|
5238
|
+
return { ok: false, error: String((e && e.message) || e) };
|
|
5225
5239
|
}
|
|
5226
|
-
const k = settings.exaKey || '';
|
|
5227
|
-
return { ok: true, set: !!k, masked: k ? '••••••••' + k.slice(-4) : '' };
|
|
5228
5240
|
});
|
|
5229
|
-
ipcMain.handle('
|
|
5230
|
-
settings.
|
|
5241
|
+
ipcMain.handle('obscura:setEnabled', (_e, v) => {
|
|
5242
|
+
settings.obscuraEnabled = v !== false;
|
|
5231
5243
|
saveSettings();
|
|
5232
|
-
|
|
5233
|
-
return { ok: true,
|
|
5244
|
+
try { setSearchObscuraEnabled(settings.obscuraEnabled); } catch {}
|
|
5245
|
+
return { ok: true, enabled: settings.obscuraEnabled };
|
|
5246
|
+
});
|
|
5247
|
+
|
|
5248
|
+
/* Arama zinciri sırası (Ayarlar → Web Arama'dan değiştirilir) */
|
|
5249
|
+
ipcMain.handle('searchorder:get', () => ({ chain: toolsMod.getSearchChain() }));
|
|
5250
|
+
ipcMain.handle('searchorder:set', (_e, chain) => {
|
|
5251
|
+
try {
|
|
5252
|
+
const rows = setSearchChain(chain);
|
|
5253
|
+
settings.searchChain = rows;
|
|
5254
|
+
saveSettings();
|
|
5255
|
+
return { ok: true, chain: rows };
|
|
5256
|
+
} catch (e) {
|
|
5257
|
+
return { ok: false, error: String((e && e.message) || e) };
|
|
5258
|
+
}
|
|
5234
5259
|
});
|
|
5235
5260
|
|
|
5236
5261
|
/* #TinyFish: anahtar girilirse web_search zincirinin BAŞINDA kullanılır */
|
package/src/preload.js
CHANGED
|
@@ -70,9 +70,11 @@ contextBridge.exposeInMainWorld('beast', {
|
|
|
70
70
|
beastcodeStop: () => ipcRenderer.invoke('beastcode:stop'),
|
|
71
71
|
beastcodeNew: () => ipcRenderer.invoke('beastcode:new'),
|
|
72
72
|
thinkSet: (v) => ipcRenderer.invoke('think:set', v),
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
73
|
+
obscuraGet: () => ipcRenderer.invoke('obscura:get'),
|
|
74
|
+
obscuraInstall: () => ipcRenderer.invoke('obscura:install'),
|
|
75
|
+
obscuraSetEnabled: (v) => ipcRenderer.invoke('obscura:setEnabled', v),
|
|
76
|
+
searchOrderGet: () => ipcRenderer.invoke('searchorder:get'),
|
|
77
|
+
searchOrderSet: (chain) => ipcRenderer.invoke('searchorder:set', chain),
|
|
76
78
|
tinyfishGet: () => ipcRenderer.invoke('tinyfish:get'),
|
|
77
79
|
tinyfishSet: (key) => ipcRenderer.invoke('tinyfish:set', key),
|
|
78
80
|
tinyfishClear: () => ipcRenderer.invoke('tinyfish:clear'),
|
package/src/renderer/i18n.js
CHANGED
|
@@ -111,10 +111,10 @@
|
|
|
111
111
|
lim_saved_toast: 'Limitler kaydedildi',
|
|
112
112
|
lim_unlimited: 'limitsiz',
|
|
113
113
|
tf_h2: 'TinyFish Arama',
|
|
114
|
-
tf_sub: 'Ücretsiz, hızlı web arama API\u2019si. Anahtar girilirse
|
|
114
|
+
tf_sub: 'Ücretsiz, hızlı web arama API\u2019si. Anahtar girilirse zincirde KENDİ SIRASINDA kullanılır; anahtar yoksa motor otomatik atlanır.',
|
|
115
115
|
tf_key_label: 'TinyFish API anahtarı (agent.tinyfish.ai/api-keys)',
|
|
116
116
|
tf_status_set: 'TinyFish aktif — kayıtlı anahtar: ',
|
|
117
|
-
tf_status_unset: 'TinyFish pasif —
|
|
117
|
+
tf_status_unset: 'TinyFish pasif — zincir sıradaki motorla devam eder.',
|
|
118
118
|
tf_empty_toast: 'Anahtar boş — mevcut anahtar korundu',
|
|
119
119
|
tf_saved_toast: 'TinyFish anahtarı kaydedildi',
|
|
120
120
|
tf_cleared_toast: 'TinyFish anahtarı silindi',
|
|
@@ -260,18 +260,30 @@
|
|
|
260
260
|
ws_calls: 'çağrı',
|
|
261
261
|
ws_token: 'token',
|
|
262
262
|
ws_h2: 'Web Arama',
|
|
263
|
-
ws_sub: 'Arama zinciri: 1) dahili tarayıcı (direk Google) 2) python çoklu-motor (ddgs / DDG+Bing+Mojeek)
|
|
264
|
-
|
|
265
|
-
|
|
263
|
+
ws_sub: 'Arama zinciri: 1) dahili tarayıcı (direk Google) 2) Obscura (stealth headless → DuckDuckGo) 3) TinyFish (anahtar varsa) 4) python çoklu-motor (ddgs / DDG+Bing+Mojeek) — otomatik. Sıra ve aç/kapa aşağıdan değiştirilir.',
|
|
264
|
+
oc_h2: 'Obscura (Stealth Tarayıcı)',
|
|
265
|
+
oc_sub: 'Rust tabanlı gizli headless tarayıcı (anti-detect + V8, Chromium\u2019suz). Kurulu değilse ilk açılışta otomatik indirilir (%APPDATA%\\beast\\obscura); DuckDuckGo aramasını bot korumasını aşarak yapar.',
|
|
266
|
+
oc_status_ok: 'Obscura kurulu ve hazır.',
|
|
267
|
+
oc_status_missing: 'Obscura kurulu değil — ilk açılışta otomatik indirilir (≈74 MB).',
|
|
268
|
+
oc_install: 'Kur / Güncelle',
|
|
269
|
+
oc_installing: 'İndiriliyor… (≈74 MB, bağlantıya göre birkaç dakika)',
|
|
270
|
+
oc_installed_toast: 'Obscura kuruldu',
|
|
271
|
+
oc_install_fail: 'Kurulamadı: ',
|
|
272
|
+
oc_enabled: 'Obscura arama zincirinde aktif',
|
|
273
|
+
oc_on_toast: 'Obscura aktif',
|
|
274
|
+
oc_off_toast: 'Obscura pasif',
|
|
275
|
+
so_h2: 'Arama Sırası',
|
|
276
|
+
so_sub: 'Motorlar bu sırayla denenir; boş dönen motor atlanıp sıradaki devreye girer. ↑↓ ile sırayı, kutucukla aç/kapa durumunu değiştir.',
|
|
277
|
+
so_engine_browser: 'Dahili Tarayıcı (Google)',
|
|
278
|
+
so_engine_obscura: 'Obscura (Stealth → DuckDuckGo)',
|
|
279
|
+
so_engine_tinyfish: 'TinyFish API (anahtar gerekir)',
|
|
280
|
+
so_engine_python: 'Python Çoklu-Motor (ddgs/DDG/Bing/Mojeek)',
|
|
281
|
+
so_saved_toast: 'Arama sırası kaydedildi',
|
|
266
282
|
ws_save: 'Kaydet',
|
|
267
283
|
ws_clear: 'Anahtarı Sil',
|
|
268
284
|
ws_note: 'Anahtar maskeli tutulur; yenisini yazıp kaydettiğinde eskisinin yerine geçer. Boş kaydet: mevcut anahtar korunur.',
|
|
269
|
-
ws_status_set: 'Exa aktif — kayıtlı anahtar: ',
|
|
270
|
-
ws_status_unset: 'Exa yapılandırılmadı — ücretsiz python çoklu-motor arama kullanılıyor.',
|
|
271
285
|
ws_empty_toast: 'Anahtar boş — mevcut anahtar korundu',
|
|
272
|
-
ws_saved_toast: 'Exa anahtarı kaydedildi',
|
|
273
286
|
ws_fail_toast: 'Kaydedilemedi',
|
|
274
|
-
ws_cleared_toast: 'Exa anahtarı silindi',
|
|
275
287
|
ag_h2: 'Paralel Ajanlar',
|
|
276
288
|
ag_sub: 'CEO\u2019nun devrettiği arka plan işleri — canlı izleme',
|
|
277
289
|
ag_ceo_label: 'CEO modu — konuşan ajan iş yapmaz, sadece emir verir',
|
|
@@ -300,12 +312,11 @@
|
|
|
300
312
|
us_where_on_toast: 'Açılış özeti açık',
|
|
301
313
|
us_where_off_toast: 'Açılış özeti kapandı',
|
|
302
314
|
ws_h2: 'Web Arama',
|
|
303
|
-
|
|
315
|
+
oc_status_ok: 'Obscura kurulu ve hazır.',
|
|
316
|
+
oc_status_missing: 'Obscura kurulu değil — ilk açılışta otomatik indirilir.',
|
|
304
317
|
ws_save: 'Kaydet',
|
|
305
318
|
ws_clear: 'Anahtarı Sil',
|
|
306
319
|
ws_key_note: 'Anahtar maskeli tutulur; yenisini yazıp kaydettiğinde eskisinin yerine geçer. Boş kaydet: mevcut anahtar korunur.',
|
|
307
|
-
ws_active: 'Exa aktif — kayıtlı anahtar: ',
|
|
308
|
-
ws_notcfg: 'Exa yapılandırılmadı — ücretsiz python çoklu-motor arama kullanılıyor.',
|
|
309
320
|
ws_empty: 'Anahtar boş — mevcut anahtar korundu',
|
|
310
321
|
// terminal & tarayıcı & mini
|
|
311
322
|
term_clear: 'Temizle',
|
|
@@ -641,10 +652,10 @@
|
|
|
641
652
|
lim_saved_toast: 'Limits saved',
|
|
642
653
|
lim_unlimited: 'unlimited',
|
|
643
654
|
tf_h2: 'TinyFish Search',
|
|
644
|
-
tf_sub: 'Free, fast web search API. If a key is set it is used
|
|
655
|
+
tf_sub: 'Free, fast web search API. If a key is set it is used in its own slot of the chain; without a key the engine is skipped automatically.',
|
|
645
656
|
tf_key_label: 'TinyFish API key (agent.tinyfish.ai/api-keys)',
|
|
646
657
|
tf_status_set: 'TinyFish active — saved key: ',
|
|
647
|
-
tf_status_unset: 'TinyFish off —
|
|
658
|
+
tf_status_unset: 'TinyFish off — the chain continues with the next engine.',
|
|
648
659
|
tf_empty_toast: 'Key empty — current key kept',
|
|
649
660
|
tf_saved_toast: 'TinyFish key saved',
|
|
650
661
|
tf_cleared_toast: 'TinyFish key deleted',
|
|
@@ -790,18 +801,30 @@
|
|
|
790
801
|
ws_calls: 'calls',
|
|
791
802
|
ws_token: 'tokens',
|
|
792
803
|
ws_h2: 'Web Search',
|
|
793
|
-
ws_sub: 'Search chain: 1) built-in browser (direct Google) 2) python multi-engine (ddgs / DDG+Bing+Mojeek)
|
|
794
|
-
|
|
795
|
-
|
|
804
|
+
ws_sub: 'Search chain: 1) built-in browser (direct Google) 2) Obscura (stealth headless → DuckDuckGo) 3) TinyFish (if a key is set) 4) python multi-engine (ddgs / DDG+Bing+Mojeek) — automatic. Order and on/off are editable below.',
|
|
805
|
+
oc_h2: 'Obscura (Stealth Browser)',
|
|
806
|
+
oc_sub: 'Rust-based stealth headless browser (anti-detect + V8, no Chromium). If not installed it is auto-downloaded at first launch (%APPDATA%\\beast\\obscura); it searches DuckDuckGo past bot protection.',
|
|
807
|
+
oc_status_ok: 'Obscura is installed and ready.',
|
|
808
|
+
oc_status_missing: 'Obscura is not installed — it is auto-downloaded at first launch (≈74 MB).',
|
|
809
|
+
oc_install: 'Install / Update',
|
|
810
|
+
oc_installing: 'Downloading… (≈74 MB, may take a few minutes)',
|
|
811
|
+
oc_installed_toast: 'Obscura installed',
|
|
812
|
+
oc_install_fail: 'Install failed: ',
|
|
813
|
+
oc_enabled: 'Obscura active in the search chain',
|
|
814
|
+
oc_on_toast: 'Obscura enabled',
|
|
815
|
+
oc_off_toast: 'Obscura disabled',
|
|
816
|
+
so_h2: 'Search Order',
|
|
817
|
+
so_sub: 'Engines are tried in this order; an empty engine is skipped and the next one takes over. Use ↑↓ to reorder, checkbox to enable/disable.',
|
|
818
|
+
so_engine_browser: 'Built-in Browser (Google)',
|
|
819
|
+
so_engine_obscura: 'Obscura (Stealth → DuckDuckGo)',
|
|
820
|
+
so_engine_tinyfish: 'TinyFish API (needs a key)',
|
|
821
|
+
so_engine_python: 'Python Multi-Engine (ddgs/DDG/Bing/Mojeek)',
|
|
822
|
+
so_saved_toast: 'Search order saved',
|
|
796
823
|
ws_save: 'Save',
|
|
797
824
|
ws_clear: 'Delete Key',
|
|
798
825
|
ws_note: 'The key is kept masked; saving a new one replaces the old. Saving empty keeps the current key.',
|
|
799
|
-
ws_status_set: 'Exa active — saved key: ',
|
|
800
|
-
ws_status_unset: 'Exa not configured — using free python multi-engine search.',
|
|
801
826
|
ws_empty_toast: 'Key empty — current key kept',
|
|
802
|
-
ws_saved_toast: 'Exa key saved',
|
|
803
827
|
ws_fail_toast: 'Could not save',
|
|
804
|
-
ws_cleared_toast: 'Exa key deleted',
|
|
805
828
|
ag_h2: 'Parallel Agents',
|
|
806
829
|
ag_sub: 'Background tasks delegated by the CEO — live monitoring',
|
|
807
830
|
ag_ceo_label: 'CEO mode — the talking agent does no work, only gives orders',
|
|
@@ -892,12 +915,11 @@
|
|
|
892
915
|
us_where_on_toast: 'Startup summary on',
|
|
893
916
|
us_where_off_toast: 'Startup summary off',
|
|
894
917
|
ws_h2: 'Web Search',
|
|
895
|
-
|
|
918
|
+
oc_status_ok: 'Obscura is installed and ready.',
|
|
919
|
+
oc_status_missing: 'Obscura is not installed — it is auto-downloaded at first launch.',
|
|
896
920
|
ws_save: 'Save',
|
|
897
921
|
ws_clear: 'Delete Key',
|
|
898
922
|
ws_key_note: 'Key is kept masked; saving a new one replaces the old. Save empty: existing key kept.',
|
|
899
|
-
ws_active: 'Exa active — saved key: ',
|
|
900
|
-
ws_notcfg: 'Exa not configured — free python multi-engine search is used.',
|
|
901
923
|
ws_empty: 'Key empty — existing key kept',
|
|
902
924
|
term_clear: 'Clear',
|
|
903
925
|
term_ph: 'type a command, press Enter…',
|