@duckmind/dm-windows-x64 0.60.6 → 0.60.9
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/dm.exe +0 -0
- package/extensions/.dm-extensions.json +70 -123
- package/extensions/dm-9router-ext/src/index.js +410 -5
- package/extensions/dm-caveman/extensions/caveman.js +283 -12
- package/extensions/dm-cliproxy/index.js +182 -2
- package/extensions/dm-cliproxy/scripts/check-config-migration.js +66 -8
- package/extensions/dm-cliproxy/src/apply.js +228 -1
- package/extensions/dm-cliproxy/src/cache.js +42 -1
- package/extensions/dm-cliproxy/src/commands.js +50 -2
- package/extensions/dm-cliproxy/src/compat.js +81 -1
- package/extensions/dm-cliproxy/src/config.js +192 -2
- package/extensions/dm-cliproxy/src/conflicts.js +46 -1
- package/extensions/dm-cliproxy/src/fetch-models.js +190 -1
- package/extensions/dm-cliproxy/src/fetch-usage.js +41 -1
- package/extensions/dm-cliproxy/src/log.js +23 -1
- package/extensions/dm-cliproxy/src/status-quota.js +77 -1
- package/extensions/dm-cliproxy/src/ui-frame.js +50 -1
- package/extensions/dm-cliproxy/src/ui-hub/hub.js +199 -2
- package/extensions/dm-cliproxy/src/ui-hub/index.js +26 -2
- package/extensions/dm-cliproxy/src/ui-hub/shell.js +46 -1
- package/extensions/dm-cliproxy/src/ui-hub/view-diagnostics.js +69 -1
- package/extensions/dm-cliproxy/src/ui-hub/view-models.js +379 -1
- package/extensions/dm-cliproxy/src/ui-hub/view-usage.js +106 -1
- package/extensions/dm-cliproxy/src/ui-picker/catalog.js +41 -1
- package/extensions/dm-cliproxy/src/ui-picker/mutate.js +115 -1
- package/extensions/dm-cliproxy/src/ui-picker/prompt-confirm.js +35 -1
- package/extensions/dm-cliproxy/src/ui-picker/prompt-name.js +62 -1
- package/extensions/dm-cliproxy/src/ui-picker/providers.js +45 -1
- package/extensions/dm-cliproxy/src/ui-picker/render-text.js +34 -1
- package/extensions/dm-cliproxy/src/ui-picker/rows.js +57 -1
- package/extensions/dm-cliproxy/src/ui-setup.js +260 -2
- package/extensions/dm-cliproxy/src/ui-usage.js +151 -1
- package/extensions/dm-cliproxy/src/usage-shared-cache.js +97 -1
- package/extensions/dm-context/src/context.js +144 -1
- package/extensions/dm-context/src/index.js +339 -7
- package/extensions/dm-context/src/utils.js +9 -1
- package/extensions/dm-cua/bin/browser-cua.mjs +73 -8
- package/extensions/dm-cua/index.js +75 -6
- package/extensions/dm-cua/src/browser-cua-lib.mjs +490 -6
- package/extensions/dm-cua/src/browser-install.mjs +331 -2
- package/extensions/dm-fff/src/index.js +688 -12
- package/extensions/dm-fff/src/query.js +60 -1
- package/extensions/dm-goal/src/goal.js +894 -23
- package/extensions/dm-image2/index.js +103 -9
- package/extensions/dm-image2/src/image-lib.mjs +1275 -8
- package/extensions/dm-subagents/install.mjs +62 -8
- package/extensions/dm-subagents/src/agents/agent-management.js +1190 -36
- package/extensions/dm-subagents/src/agents/agent-memory.js +216 -6
- package/extensions/dm-subagents/src/agents/agent-scope.js +5 -1
- package/extensions/dm-subagents/src/agents/agent-selection.js +20 -1
- package/extensions/dm-subagents/src/agents/agent-serializer.js +120 -5
- package/extensions/dm-subagents/src/agents/agents.js +1139 -11
- package/extensions/dm-subagents/src/agents/chain-serializer.js +299 -11
- package/extensions/dm-subagents/src/agents/frontmatter.js +65 -6
- package/extensions/dm-subagents/src/agents/identity.js +29 -1
- package/extensions/dm-subagents/src/agents/proactive-skills.js +141 -1
- package/extensions/dm-subagents/src/agents/skills.js +614 -6
- package/extensions/dm-subagents/src/extension/config.js +35 -2
- package/extensions/dm-subagents/src/extension/control-notices.js +69 -4
- package/extensions/dm-subagents/src/extension/doctor.js +172 -15
- package/extensions/dm-subagents/src/extension/fanout-child.js +158 -231
- package/extensions/dm-subagents/src/extension/index.js +521 -359
- package/extensions/dm-subagents/src/extension/rpc.js +266 -7
- package/extensions/dm-subagents/src/extension/schemas.js +275 -1
- package/extensions/dm-subagents/src/extension/tool-description.js +111 -6
- package/extensions/dm-subagents/src/intercom/intercom-bridge.js +126 -4
- package/extensions/dm-subagents/src/intercom/native-supervisor-channel.js +452 -5
- package/extensions/dm-subagents/src/intercom/result-intercom.js +319 -3
- package/extensions/dm-subagents/src/profiles/profiles.js +458 -3
- package/extensions/dm-subagents/src/runs/background/async-execution.js +834 -40
- package/extensions/dm-subagents/src/runs/background/async-job-tracker.js +435 -14
- package/extensions/dm-subagents/src/runs/background/async-resume.js +334 -8
- package/extensions/dm-subagents/src/runs/background/async-status.js +313 -12
- package/extensions/dm-subagents/src/runs/background/chain-append.js +245 -2
- package/extensions/dm-subagents/src/runs/background/chain-root-attachment.js +136 -1
- package/extensions/dm-subagents/src/runs/background/completion-batcher.js +94 -1
- package/extensions/dm-subagents/src/runs/background/completion-dedupe.js +54 -1
- package/extensions/dm-subagents/src/runs/background/control-channel.js +190 -1
- package/extensions/dm-subagents/src/runs/background/fleet-view.js +483 -17
- package/extensions/dm-subagents/src/runs/background/notify.js +129 -3
- package/extensions/dm-subagents/src/runs/background/parallel-groups.js +34 -1
- package/extensions/dm-subagents/src/runs/background/result-watcher.js +236 -6
- package/extensions/dm-subagents/src/runs/background/run-id-resolver.js +76 -4
- package/extensions/dm-subagents/src/runs/background/run-status.js +427 -23
- package/extensions/dm-subagents/src/runs/background/scheduled-runs.js +487 -4
- package/extensions/dm-subagents/src/runs/background/stale-run-reconciler.js +306 -9
- package/extensions/dm-subagents/src/runs/background/subagent-runner.js +2849 -73
- package/extensions/dm-subagents/src/runs/background/top-level-async.js +5 -1
- package/extensions/dm-subagents/src/runs/background/wait.js +206 -11
- package/extensions/dm-subagents/src/runs/foreground/chain-clarify.js +1013 -12
- package/extensions/dm-subagents/src/runs/foreground/chain-execution.js +980 -101
- package/extensions/dm-subagents/src/runs/foreground/execution.js +1165 -45
- package/extensions/dm-subagents/src/runs/foreground/subagent-executor.js +3157 -222
- package/extensions/dm-subagents/src/runs/shared/acceptance.js +835 -3
- package/extensions/dm-subagents/src/runs/shared/chain-outputs.js +104 -1
- package/extensions/dm-subagents/src/runs/shared/completion-guard.js +116 -3
- package/extensions/dm-subagents/src/runs/shared/dm-args.js +208 -1
- package/extensions/dm-subagents/src/runs/shared/dm-spawn.js +90 -1
- package/extensions/dm-subagents/src/runs/shared/dynamic-fanout.js +282 -1
- package/extensions/dm-subagents/src/runs/shared/long-running-guard.js +148 -1
- package/extensions/dm-subagents/src/runs/shared/mcp-direct-tool-allowlist.js +305 -1
- package/extensions/dm-subagents/src/runs/shared/model-fallback.js +194 -1
- package/extensions/dm-subagents/src/runs/shared/model-scope.js +65 -1
- package/extensions/dm-subagents/src/runs/shared/nested-events.js +851 -8
- package/extensions/dm-subagents/src/runs/shared/nested-path.js +41 -1
- package/extensions/dm-subagents/src/runs/shared/nested-render.js +105 -1
- package/extensions/dm-subagents/src/runs/shared/parallel-utils.js +81 -4
- package/extensions/dm-subagents/src/runs/shared/run-history.js +51 -4
- package/extensions/dm-subagents/src/runs/shared/single-output.js +149 -8
- package/extensions/dm-subagents/src/runs/shared/structured-output.js +58 -1
- package/extensions/dm-subagents/src/runs/shared/subagent-control.js +166 -5
- package/extensions/dm-subagents/src/runs/shared/subagent-prompt-runtime.js +329 -13
- package/extensions/dm-subagents/src/runs/shared/tool-budget.js +73 -1
- package/extensions/dm-subagents/src/runs/shared/turn-budget.js +47 -4
- package/extensions/dm-subagents/src/runs/shared/workflow-graph.js +196 -1
- package/extensions/dm-subagents/src/runs/shared/worktree.js +435 -3
- package/extensions/dm-subagents/src/shared/artifacts.js +92 -2
- package/extensions/dm-subagents/src/shared/atomic-json.js +55 -1
- package/extensions/dm-subagents/src/shared/child-transcript.js +167 -5
- package/extensions/dm-subagents/src/shared/file-coalescer.js +25 -1
- package/extensions/dm-subagents/src/shared/fork-context.js +147 -4
- package/extensions/dm-subagents/src/shared/formatters.js +98 -7
- package/extensions/dm-subagents/src/shared/jsonl-writer.js +56 -2
- package/extensions/dm-subagents/src/shared/model-info.js +62 -1
- package/extensions/dm-subagents/src/shared/post-exit-stdio-guard.js +68 -1
- package/extensions/dm-subagents/src/shared/session-identity.js +6 -1
- package/extensions/dm-subagents/src/shared/session-tokens.js +39 -2
- package/extensions/dm-subagents/src/shared/settings.js +198 -11
- package/extensions/dm-subagents/src/shared/status-format.js +53 -1
- package/extensions/dm-subagents/src/shared/types.js +184 -6
- package/extensions/dm-subagents/src/shared/utils.js +462 -2
- package/extensions/dm-subagents/src/slash/prompt-template-bridge.js +288 -1
- package/extensions/dm-subagents/src/slash/prompt-workflows.js +297 -7
- package/extensions/dm-subagents/src/slash/slash-bridge.js +118 -1
- package/extensions/dm-subagents/src/slash/slash-commands.js +1287 -31
- package/extensions/dm-subagents/src/slash/slash-live-state.js +240 -4
- package/extensions/dm-subagents/src/tui/render-helpers.js +64 -1
- package/extensions/dm-subagents/src/tui/render.js +1542 -4
- package/extensions/dm-usage/index.js +1294 -9
- package/extensions/greedysearch-dm/bin/cdp-greedy.mjs +40 -9
- package/extensions/greedysearch-dm/bin/cdp-headless.mjs +5 -2
- package/extensions/greedysearch-dm/bin/cdp-visible.mjs +5 -2
- package/extensions/greedysearch-dm/bin/cdp.mjs +896 -30
- package/extensions/greedysearch-dm/bin/gschrome.mjs +30 -2
- package/extensions/greedysearch-dm/bin/kill-visible.mjs +7 -2
- package/extensions/greedysearch-dm/bin/launch-visible.mjs +13 -2
- package/extensions/greedysearch-dm/bin/launch.mjs +282 -10
- package/extensions/greedysearch-dm/bin/mcp.mjs +386 -361
- package/extensions/greedysearch-dm/bin/search.mjs +620 -540
- package/extensions/greedysearch-dm/bin/visible.mjs +22 -2
- package/extensions/greedysearch-dm/extractors/bing-copilot.mjs +329 -579
- package/extensions/greedysearch-dm/extractors/chatgpt.mjs +301 -583
- package/extensions/greedysearch-dm/extractors/common.mjs +408 -32
- package/extensions/greedysearch-dm/extractors/consensus.mjs +376 -365
- package/extensions/greedysearch-dm/extractors/consent.mjs +303 -14
- package/extensions/greedysearch-dm/extractors/gemini.mjs +228 -592
- package/extensions/greedysearch-dm/extractors/google-ai.mjs +78 -499
- package/extensions/greedysearch-dm/extractors/logically.mjs +270 -347
- package/extensions/greedysearch-dm/extractors/perplexity.mjs +243 -581
- package/extensions/greedysearch-dm/extractors/selectors.mjs +32 -1
- package/extensions/greedysearch-dm/extractors/semantic-scholar.mjs +130 -317
- package/extensions/greedysearch-dm/index.js +123 -23
- package/extensions/greedysearch-dm/src/fetcher.mjs +576 -2
- package/extensions/greedysearch-dm/src/formatters/results.js +95 -10
- package/extensions/greedysearch-dm/src/formatters/sources.js +57 -1
- package/extensions/greedysearch-dm/src/formatters/synthesis.js +49 -1
- package/extensions/greedysearch-dm/src/github.mjs +222 -7
- package/extensions/greedysearch-dm/src/reddit.mjs +145 -14
- package/extensions/greedysearch-dm/src/search/browser-lifecycle.mjs +340 -9
- package/extensions/greedysearch-dm/src/search/challenge-detect.mjs +112 -4
- package/extensions/greedysearch-dm/src/search/chrome.mjs +486 -285
- package/extensions/greedysearch-dm/src/search/constants.mjs +109 -8
- package/extensions/greedysearch-dm/src/search/defaults.mjs +10 -1
- package/extensions/greedysearch-dm/src/search/engines.mjs +79 -9
- package/extensions/greedysearch-dm/src/search/fetch-source.mjs +441 -349
- package/extensions/greedysearch-dm/src/search/file-sources.mjs +29 -7
- package/extensions/greedysearch-dm/src/search/minimize.mjs +86 -1
- package/extensions/greedysearch-dm/src/search/output.mjs +51 -5
- package/extensions/greedysearch-dm/src/search/paths.mjs +48 -1
- package/extensions/greedysearch-dm/src/search/pdf.mjs +63 -2
- package/extensions/greedysearch-dm/src/search/port-pid.mjs +69 -1
- package/extensions/greedysearch-dm/src/search/progress.mjs +109 -2
- package/extensions/greedysearch-dm/src/search/query.mjs +21 -1
- package/extensions/greedysearch-dm/src/search/recovery.mjs +49 -1
- package/extensions/greedysearch-dm/src/search/research.mjs +2227 -458
- package/extensions/greedysearch-dm/src/search/scale-aware.mjs +61 -11
- package/extensions/greedysearch-dm/src/search/simple-research.mjs +396 -805
- package/extensions/greedysearch-dm/src/search/sources.mjs +412 -1
- package/extensions/greedysearch-dm/src/search/synthesis-runner.mjs +127 -12
- package/extensions/greedysearch-dm/src/search/synthesis.mjs +202 -12
- package/extensions/greedysearch-dm/src/tools/greedy-search-handler.js +209 -23
- package/extensions/greedysearch-dm/src/tools/shared.js +226 -10
- package/extensions/greedysearch-dm/src/utils/content.mjs +35 -4
- package/extensions/greedysearch-dm/src/utils/helpers.js +22 -1
- package/extensions/greedysearch-dm/src/utils/node-runtime.mjs +10 -1
- package/extensions/greedysearch-dm/src/utils/system-cmds.mjs +61 -1
- package/package.json +1 -1
|
@@ -1 +1,32 @@
|
|
|
1
|
-
|
|
1
|
+
export const SELECTORS = {
|
|
2
|
+
perplexity: {
|
|
3
|
+
input: "#ask-input",
|
|
4
|
+
copyButton: null,
|
|
5
|
+
sourceItem: "[data-pplx-citation-url]",
|
|
6
|
+
sourceLink: "a",
|
|
7
|
+
consent: "#onetrust-accept-btn-handler"
|
|
8
|
+
},
|
|
9
|
+
bing: {
|
|
10
|
+
input: "#userInput",
|
|
11
|
+
copyButton: 'button[data-testid="copy-ai-message-button"]',
|
|
12
|
+
sourceLink: 'a[href^="http"][target="_blank"]',
|
|
13
|
+
sourceExclude: "copilot.microsoft.com",
|
|
14
|
+
consent: "#onetrust-accept-btn-handler"
|
|
15
|
+
},
|
|
16
|
+
google: {
|
|
17
|
+
answerContainer: ".pWvJNd",
|
|
18
|
+
sourceLink: 'a[href^="http"]',
|
|
19
|
+
sourceExclude: ["google.", "gstatic", "googleapis"],
|
|
20
|
+
sourceHeadingParent: "[data-snhf]",
|
|
21
|
+
consent: '#L2AGLb, button[jsname="b3VHJd"], .tHlp8d'
|
|
22
|
+
},
|
|
23
|
+
gemini: {
|
|
24
|
+
input: "rich-textarea .ql-editor",
|
|
25
|
+
copyButton: 'button:has(mat-icon[data-mat-icon-name="copy"])',
|
|
26
|
+
sendButton: 'button:has(mat-icon[data-mat-icon-name="arrow_upward"]), [data-test-id="send-button"], .send-button',
|
|
27
|
+
sourcesSidebarButton: "button.legacy-sources-sidebar-button",
|
|
28
|
+
sourcesExclude: ["gemini.google", "gstatic", "google.com/search"],
|
|
29
|
+
citationButtonPattern: 'button[aria-label*="citation from"]',
|
|
30
|
+
citationNameRegex: /from\s{1,20}([^.]{1,200})\.\s/
|
|
31
|
+
}
|
|
32
|
+
};
|
|
@@ -1,315 +1,28 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
Object.defineProperty(navigator, 'product', { get: () => 'Gecko', configurable: true });
|
|
27
|
-
var __greedyMimeTypes = null;
|
|
28
|
-
function __makeMimeTypes() {
|
|
29
|
-
var pdf = { type: 'application/pdf', suffixes: 'pdf', description: 'Portable Document Format', enabledPlugin: null };
|
|
30
|
-
var textPdf = { type: 'text/pdf', suffixes: 'pdf', description: 'Portable Document Format', enabledPlugin: null };
|
|
31
|
-
try { Object.setPrototypeOf(pdf, MimeType.prototype); } catch(_) {}
|
|
32
|
-
try { Object.setPrototypeOf(textPdf, MimeType.prototype); } catch(_) {}
|
|
33
|
-
var m = [pdf, textPdf];
|
|
34
|
-
try { Object.setPrototypeOf(m, MimeTypeArray.prototype); } catch(_) {}
|
|
35
|
-
m.item = function item(i) { return this[i] || null; };
|
|
36
|
-
m.namedItem = function namedItem(name) { return Array.prototype.find.call(this, function(x) { return x && x.type === name; }) || null; };
|
|
37
|
-
return m;
|
|
38
|
-
}
|
|
39
|
-
Object.defineProperty(navigator, 'plugins', {
|
|
40
|
-
get: () => {
|
|
41
|
-
__greedyMimeTypes = __greedyMimeTypes || __makeMimeTypes();
|
|
42
|
-
var plugin0 = { name: 'Chrome PDF Plugin', filename: 'internal-pdf-viewer', description: 'Portable Document Format' };
|
|
43
|
-
var plugin1 = { name: 'Chrome PDF Viewer', filename: 'mhjfbmdgcfjbbpaeojofohoefgiehjai', description: '' };
|
|
44
|
-
var plugin2 = { name: 'Native Client', filename: 'internal-nacl-plugin', description: '' };
|
|
45
|
-
try { Object.setPrototypeOf(plugin0, Plugin.prototype); } catch(_) {}
|
|
46
|
-
try { Object.setPrototypeOf(plugin1, Plugin.prototype); } catch(_) {}
|
|
47
|
-
try { Object.setPrototypeOf(plugin2, Plugin.prototype); } catch(_) {}
|
|
48
|
-
var p = [plugin0, plugin1, plugin2];
|
|
49
|
-
p.item = function item(i) { return this[i] || null; };
|
|
50
|
-
p.namedItem = function namedItem(name) { return Array.prototype.find.call(this, function(x) { return x && x.name === name; }) || null; };
|
|
51
|
-
p.refresh = function refresh() {};
|
|
52
|
-
try { Object.setPrototypeOf(p, PluginArray.prototype); } catch(_) {}
|
|
53
|
-
try {
|
|
54
|
-
__greedyMimeTypes[0].enabledPlugin = p[0];
|
|
55
|
-
__greedyMimeTypes[1].enabledPlugin = p[0];
|
|
56
|
-
} catch(_) {}
|
|
57
|
-
return p;
|
|
58
|
-
},
|
|
59
|
-
configurable: true,
|
|
60
|
-
});
|
|
61
|
-
Object.defineProperty(navigator, 'mimeTypes', {
|
|
62
|
-
get: () => {
|
|
63
|
-
__greedyMimeTypes = __greedyMimeTypes || __makeMimeTypes();
|
|
64
|
-
return __greedyMimeTypes;
|
|
65
|
-
},
|
|
66
|
-
configurable: true,
|
|
67
|
-
});
|
|
68
|
-
Object.defineProperty(navigator, 'languages', { get: () => ['en-US', 'en'], configurable: true });
|
|
69
|
-
try {
|
|
70
|
-
Object.defineProperty(navigator, 'connection', { get: () => ({ effectiveType: '4g', rtt: 50, downlink: 10, downlinkMax: Infinity, saveData: false }), configurable: true });
|
|
71
|
-
} catch(_) {}
|
|
72
|
-
if (!navigator.mediaDevices) {
|
|
73
|
-
Object.defineProperty(navigator, 'mediaDevices', {
|
|
74
|
-
get: () => ({
|
|
75
|
-
enumerateDevices: () => Promise.resolve([
|
|
76
|
-
{ deviceId: 'default', kind: 'audioinput', label: '', groupId: 'default' },
|
|
77
|
-
{ deviceId: 'default', kind: 'audiooutput', label: '', groupId: 'default' },
|
|
78
|
-
{ deviceId: '', kind: 'videoinput', label: '', groupId: '' },
|
|
79
|
-
]),
|
|
80
|
-
getUserMedia: () => Promise.reject(new DOMException('NotAllowedError')),
|
|
81
|
-
getDisplayMedia: () => Promise.reject(new DOMException('NotAllowedError')),
|
|
82
|
-
}),
|
|
83
|
-
configurable: true,
|
|
84
|
-
});
|
|
85
|
-
}
|
|
86
|
-
// ── Missing platform APIs (headless often lacks these) ─
|
|
87
|
-
try {
|
|
88
|
-
if (!navigator.share) {
|
|
89
|
-
navigator.share = function() { return Promise.reject(new Error('NotAllowedError')); };
|
|
90
|
-
}
|
|
91
|
-
} catch(_) {}
|
|
92
|
-
try {
|
|
93
|
-
if (!navigator.contentIndex) {
|
|
94
|
-
Object.defineProperty(navigator, 'contentIndex', { get: () => ({ add: function() {}, delete: function() {}, getAll: function() { return Promise.resolve([]); } }), configurable: true });
|
|
95
|
-
}
|
|
96
|
-
} catch(_) {}
|
|
97
|
-
|
|
98
|
-
if (!window.chrome) {
|
|
99
|
-
window.chrome = {
|
|
100
|
-
app: { isInstalled: false, InstallState: {}, RunningState: {} },
|
|
101
|
-
runtime: {
|
|
102
|
-
OnInstalledReason: {}, OnRestartRequiredReason: {}, PlatformArch: {}, PlatformNaclArch: {}, PlatformOs: {}, RequestUpdateCheckStatus: {},
|
|
103
|
-
connect: () => ({}), sendMessage: () => {}, onMessage: { addListener: () => {} }
|
|
104
|
-
},
|
|
105
|
-
loadTimes: function() { return { requestTime: 0, startLoadTime: Date.now() - 5000, commitLoadTime: Date.now() - 3000, finishDocumentLoadTime: Date.now() - 2000, finishLoadTime: Date.now() - 1000, firstPaintTime: Date.now() - 800, navigationType: 'Other', wasFetchedViaSpdy: true, wasNpnNegotiated: true, npnNegotiatedProtocol: 'h2', wasAlternateProtocolAvailable: false, connectionInfo: 'http/2' }; },
|
|
106
|
-
csi: function() { var t = Date.now(); return { onloadT: t - 2000, startE: t - 5000, pageT: 'back', tran: 2 }; },
|
|
107
|
-
};
|
|
108
|
-
}
|
|
109
|
-
var __greedyNativeFns = [];
|
|
110
|
-
function __markNative(fn) { try { __greedyNativeFns.push(fn); } catch(_) {} return fn; }
|
|
111
|
-
|
|
112
|
-
var origQuery = navigator.permissions?.query;
|
|
113
|
-
if (origQuery) {
|
|
114
|
-
navigator.permissions.query = __markNative(function query(params) {
|
|
115
|
-
if (params && params.name === 'notifications') return Promise.resolve({ state: Notification.permission || 'default', onchange: null });
|
|
116
|
-
return origQuery.apply(this, arguments);
|
|
117
|
-
});
|
|
118
|
-
}
|
|
119
|
-
try {
|
|
120
|
-
var getParam = WebGLRenderingContext.prototype.getParameter;
|
|
121
|
-
WebGLRenderingContext.prototype.getParameter = __markNative(function getParameter(p) {
|
|
122
|
-
if (p === 37445) return 'Intel Inc.';
|
|
123
|
-
if (p === 37446) return 'Intel Iris OpenGL Engine';
|
|
124
|
-
return getParam.call(this, p);
|
|
125
|
-
});
|
|
126
|
-
} catch(_) {}
|
|
127
|
-
// ── WebGL readPixels noise ──────────────────────────
|
|
128
|
-
// CreepJS and other fingerprinters draw content with WebGL and read back the
|
|
129
|
-
// rendered pixels. Adding subtle noise breaks rendering-based fingerprinting.
|
|
130
|
-
try {
|
|
131
|
-
var origReadPixels = WebGLRenderingContext.prototype.readPixels;
|
|
132
|
-
WebGLRenderingContext.prototype.readPixels = __markNative(function readPixels(x, y, width, height, format, type, pixels) {
|
|
133
|
-
var result = origReadPixels.call(this, x, y, width, height, format, type, pixels);
|
|
134
|
-
if (pixels && pixels.length > 0) {
|
|
135
|
-
pixels[0] ^= 1;
|
|
136
|
-
}
|
|
137
|
-
return result;
|
|
138
|
-
});
|
|
139
|
-
} catch(_) {}
|
|
140
|
-
Object.defineProperty(navigator, 'hardwareConcurrency', { get: () => 8, configurable: true });
|
|
141
|
-
Object.defineProperty(navigator, 'deviceMemory', { get: () => 8, configurable: true });
|
|
142
|
-
|
|
143
|
-
// ── Canvas fingerprint noise ─────────────────────────
|
|
144
|
-
// Headless rendering engines produce slightly different canvas output
|
|
145
|
-
// than headed Chrome. Subtle noise breaks hash-based fingerprinting.
|
|
146
|
-
try {
|
|
147
|
-
var __canvasNoise = ((Date.now() & 0xFF) | 1);
|
|
148
|
-
var origFill = CanvasRenderingContext2D.prototype.fillText;
|
|
149
|
-
CanvasRenderingContext2D.prototype.fillText = __markNative(function fillText() {
|
|
150
|
-
this.globalAlpha = 0.9995;
|
|
151
|
-
return origFill.apply(this, arguments);
|
|
152
|
-
});
|
|
153
|
-
} catch(_) {}
|
|
154
|
-
try {
|
|
155
|
-
var origStroke = CanvasRenderingContext2D.prototype.strokeText;
|
|
156
|
-
CanvasRenderingContext2D.prototype.strokeText = __markNative(function strokeText() {
|
|
157
|
-
this.globalAlpha = 0.9995;
|
|
158
|
-
return origStroke.apply(this, arguments);
|
|
159
|
-
});
|
|
160
|
-
} catch(_) {}
|
|
161
|
-
try {
|
|
162
|
-
var origToDataURL = HTMLCanvasElement.prototype.toDataURL;
|
|
163
|
-
HTMLCanvasElement.prototype.toDataURL = __markNative(function toDataURL() {
|
|
164
|
-
var ctx = this.getContext('2d');
|
|
165
|
-
if (ctx) {
|
|
166
|
-
// Spread noise across canvas to break hash-based fingerprinting.
|
|
167
|
-
// Uses a deterministic pattern so it's consistent per page load
|
|
168
|
-
// but varies between sessions.
|
|
169
|
-
var w = this.width, h = this.height;
|
|
170
|
-
if (w > 0 && h > 0) {
|
|
171
|
-
var imgData = ctx.getImageData(0, 0, Math.min(w, 4), Math.min(h, 4));
|
|
172
|
-
if (imgData && imgData.data) {
|
|
173
|
-
for (var __i = 0; __i < imgData.data.length; __i += 4) {
|
|
174
|
-
imgData.data[__i] ^= (__canvasNoise + __i) & 0xFF;
|
|
175
|
-
}
|
|
176
|
-
ctx.putImageData(imgData, 0, 0);
|
|
177
|
-
}
|
|
178
|
-
}
|
|
179
|
-
}
|
|
180
|
-
return origToDataURL.apply(this, arguments);
|
|
181
|
-
});
|
|
182
|
-
} catch(_) {}
|
|
183
|
-
|
|
184
|
-
// ── AudioContext fingerprint noise ────────────────────
|
|
185
|
-
// Headless Chrome's AudioContext produces slightly different output.
|
|
186
|
-
// Subtle noise breaks audio-based fingerprinting.
|
|
187
|
-
try {
|
|
188
|
-
var __audioSeed = ((Date.now() & 0x1F) | 1);
|
|
189
|
-
var origGetChannelData = AudioBuffer.prototype.getChannelData;
|
|
190
|
-
AudioBuffer.prototype.getChannelData = __markNative(function getChannelData(channel) {
|
|
191
|
-
var data = origGetChannelData.call(this, channel);
|
|
192
|
-
for (var __i = 0; __i < data.length; __i += 64) {
|
|
193
|
-
data[__i] *= 0.99999;
|
|
194
|
-
}
|
|
195
|
-
return data;
|
|
196
|
-
});
|
|
197
|
-
} catch(_) {}
|
|
198
|
-
|
|
199
|
-
// ── window outer dimensions ──────────────────────────
|
|
200
|
-
// outerWidth/Height = 0 in headless — a well-known bot signal.
|
|
201
|
-
// Mirror innerWidth/Height (set by --window-size flag) so the ratio is sane.
|
|
202
|
-
try {
|
|
203
|
-
if (!window.outerWidth) Object.defineProperty(window, 'outerWidth', { get: () => window.innerWidth || 1920, configurable: true });
|
|
204
|
-
if (!window.outerHeight) Object.defineProperty(window, 'outerHeight', { get: () => window.innerHeight || 1080, configurable: true });
|
|
205
|
-
} catch(_) {}
|
|
206
|
-
|
|
207
|
-
// ── screen properties ─────────────────────────────────
|
|
208
|
-
// Headless Chrome often reports an 800x600 screen even when the viewport is
|
|
209
|
-
// 1920x1080. Keep screen metrics internally consistent with our launch flags.
|
|
210
|
-
try {
|
|
211
|
-
Object.defineProperty(screen, 'width', { get: () => 1920, configurable: true });
|
|
212
|
-
Object.defineProperty(screen, 'height', { get: () => 1080, configurable: true });
|
|
213
|
-
Object.defineProperty(screen, 'availWidth', { get: () => 1920, configurable: true });
|
|
214
|
-
Object.defineProperty(screen, 'availHeight', { get: () => 1040, configurable: true });
|
|
215
|
-
Object.defineProperty(screen, 'colorDepth', { get: () => 24, configurable: true });
|
|
216
|
-
Object.defineProperty(screen, 'pixelDepth', { get: () => 24, configurable: true });
|
|
217
|
-
} catch(_) {}
|
|
218
|
-
|
|
219
|
-
// ── navigator.userAgentData (UA Client Hints) ─────────
|
|
220
|
-
// Derive version from the UA string already set by --user-agent flag so the
|
|
221
|
-
// two APIs are always consistent. Removes any "HeadlessChrome" brand entry.
|
|
222
|
-
try {
|
|
223
|
-
var _uaMajor = (navigator.userAgent.match(new RegExp('Chrome/([0-9]+)')) || [])[1] || '136';
|
|
224
|
-
var _uaFull = (navigator.userAgent.match(new RegExp('Chrome/([0-9.]+)')) || [])[1] || (_uaMajor + '.0.0.0');
|
|
225
|
-
var _brands = [
|
|
226
|
-
{ brand: 'Not)A;Brand', version: '99' },
|
|
227
|
-
{ brand: 'Google Chrome', version: _uaMajor },
|
|
228
|
-
{ brand: 'Chromium', version: _uaMajor },
|
|
229
|
-
];
|
|
230
|
-
Object.defineProperty(navigator, 'userAgentData', {
|
|
231
|
-
get: function() {
|
|
232
|
-
return {
|
|
233
|
-
brands: _brands, mobile: false, platform: 'Windows',
|
|
234
|
-
getHighEntropyValues: function() {
|
|
235
|
-
return Promise.resolve({
|
|
236
|
-
architecture: 'x86', bitness: '64',
|
|
237
|
-
brands: _brands,
|
|
238
|
-
fullVersionList: [
|
|
239
|
-
{ brand: 'Not)A;Brand', version: '99.0.0.0' },
|
|
240
|
-
{ brand: 'Google Chrome', version: _uaFull },
|
|
241
|
-
{ brand: 'Chromium', version: _uaFull },
|
|
242
|
-
],
|
|
243
|
-
mobile: false, model: '', platform: 'Windows',
|
|
244
|
-
platformVersion: '15.0.0', uaFullVersion: _uaFull, wow64: false,
|
|
245
|
-
});
|
|
246
|
-
},
|
|
247
|
-
toJSON: function() { return { brands: _brands, mobile: false, platform: 'Windows' }; },
|
|
248
|
-
};
|
|
249
|
-
},
|
|
250
|
-
configurable: true,
|
|
251
|
-
});
|
|
252
|
-
} catch(_) {}
|
|
253
|
-
|
|
254
|
-
// ── CDP Runtime serialization guard ──────────────────
|
|
255
|
-
// Sites detect CDP by putting a getter on Error.prototype.stack
|
|
256
|
-
// and checking if console.log triggers it (only happens when
|
|
257
|
-
// Runtime domain is enabled). We monkey-patch console methods to
|
|
258
|
-
// strip custom getters from arguments before they reach CDP.
|
|
259
|
-
try {
|
|
260
|
-
var _origLog = console.log, _origError = console.error,
|
|
261
|
-
_origWarn = console.warn, _origDebug = console.debug,
|
|
262
|
-
_origInfo = console.info;
|
|
263
|
-
var _safeArg = function(a) {
|
|
264
|
-
if (a instanceof Error) {
|
|
265
|
-
try { return new Error(a.message); } catch(_) { return a; }
|
|
266
|
-
}
|
|
267
|
-
return a;
|
|
268
|
-
};
|
|
269
|
-
console.log = __markNative(function log() { return _origLog.apply(console, Array.prototype.map.call(arguments, _safeArg)); });
|
|
270
|
-
console.error = __markNative(function error() { return _origError.apply(console, Array.prototype.map.call(arguments, _safeArg)); });
|
|
271
|
-
console.warn = __markNative(function warn() { return _origWarn.apply(console, Array.prototype.map.call(arguments, _safeArg)); });
|
|
272
|
-
console.debug = __markNative(function debug() { return _origDebug.apply(console, Array.prototype.map.call(arguments, _safeArg)); });
|
|
273
|
-
console.info = __markNative(function info() { return _origInfo.apply(console, Array.prototype.map.call(arguments, _safeArg)); });
|
|
274
|
-
} catch(_) {}
|
|
275
|
-
|
|
276
|
-
// ── Native function masking ──────────────────────────
|
|
277
|
-
// Patched APIs should not stringify as user-defined stealth code.
|
|
278
|
-
try {
|
|
279
|
-
var __nativeToString = Function.prototype.toString;
|
|
280
|
-
Function.prototype.toString = function toString() {
|
|
281
|
-
if (__greedyNativeFns.indexOf(this) !== -1) {
|
|
282
|
-
var name = this.name || '';
|
|
283
|
-
return 'function ' + name + '() { [native code] }';
|
|
284
|
-
}
|
|
285
|
-
return __nativeToString.call(this);
|
|
286
|
-
};
|
|
287
|
-
} catch(_) {}
|
|
288
|
-
})();
|
|
289
|
-
`})])}async function y(e,t,r=15000,n=500){let i=String.raw`
|
|
290
|
-
new Promise((resolve) => {
|
|
291
|
-
const _deadline = Date.now() + ${r};
|
|
292
|
-
const _baseInterval = ${n};
|
|
293
|
-
|
|
294
|
-
function _jitter(ms) {
|
|
295
|
-
return Math.max(50, ms + (Math.random() * ms * 0.4 - ms * 0.2));
|
|
296
|
-
}
|
|
297
|
-
|
|
298
|
-
function _poll() {
|
|
299
|
-
try {
|
|
300
|
-
if (document.querySelector('${t}')) { resolve(true); return; }
|
|
301
|
-
if (Date.now() < _deadline) { setTimeout(_poll, _jitter(_baseInterval)); }
|
|
302
|
-
else { resolve(false); }
|
|
303
|
-
} catch(_) { resolve(false); }
|
|
304
|
-
}
|
|
305
|
-
|
|
306
|
-
_poll();
|
|
307
|
-
})
|
|
308
|
-
`;return await u(["eval",e,i],r+5000)==="true"}async function _(e){let t=e.indexOf("--stdin");if(t===-1)return e;let r=await new Promise((i)=>{let a="";process.stdin.setEncoding("utf8"),process.stdin.on("data",(o)=>a+=o),process.stdin.on("end",()=>i(a.trim()))}),n=[...e];return n[t]=r,n}function w(e){let t=e.includes("--short"),r=e.filter((l)=>l!=="--short"),n=r.indexOf("--tab"),i=n===-1?null:r[n+1];if(n!==-1)r=r.filter((l,c)=>c!==n&&c!==n+1);let a=r.indexOf("--locale"),o=a===-1?null:r[a+1];if(a!==-1)r=r.filter((l,c)=>c!==a&&c!==a+1);return{query:r.join(" "),tabPrefix:i,short:t,locale:o}}function b(e,t){if(!e.length||e[0]==="--help")process.stderr.write(t),process.exit(1)}function v(e,t,r=300){if(!t||e.length<=r)return e;let n=e.slice(0,r),i=n.lastIndexOf(" ");return i>0?`${n.slice(0,i)}…`:`${n}…`}function x(e){process.stdout.write(`${JSON.stringify(e,null,2)}
|
|
309
|
-
`)}function g(e,t,r=null){if(!e||typeof e!=="object")return;let n=r?` (+${Date.now()-r}ms)`:"";if(e.lastStage=t,!Array.isArray(e.stages))e.stages=[];e.stages.push({stage:t,at:Date.now()});let i=e.engine||"extractor";console.error(`[${i}] stage: ${t}${n}`)}function m({engine:e,mode:t="headless",clipboardEmpty:r=null,fallbackUsed:n=null,blockedBy:i=null,verificationResult:a=null,inputReady:o=null,durationMs:l=null,lastStage:c=null,stages:f=null}={}){return{engine:e,mode:t,clipboardEmpty:r,fallbackUsed:n,blockedBy:i,verificationResult:a,inputReady:o,durationMs:l,lastStage:c,stages:f}}function P(e,t=null){if(t){let r=JSON.stringify({_envelope:t,error:e.message});process.stdout.write(`${r}
|
|
310
|
-
`)}process.stderr.write(`Error: ${e.message}
|
|
311
|
-
`),process.exit(1)}var L=`Usage: node extractors/semantic-scholar.mjs "<query>" [--tab <prefix>]
|
|
312
|
-
`,F=".cl-paper-row[data-paper-id]";function D(e){let t=String(e||"").replaceAll("-"," ");return`https://www.semanticscholar.org/search?q=${encodeURIComponent(t)}&sort=relevance`}async function G(e){await u(["eval",e,String.raw`
|
|
1
|
+
import {
|
|
2
|
+
buildEnvelope,
|
|
3
|
+
cdp,
|
|
4
|
+
formatAnswer,
|
|
5
|
+
getOrOpenTab,
|
|
6
|
+
handleError,
|
|
7
|
+
logStage,
|
|
8
|
+
outputJson,
|
|
9
|
+
parseArgs,
|
|
10
|
+
prepareArgs,
|
|
11
|
+
validateQuery,
|
|
12
|
+
waitForSelector
|
|
13
|
+
} from "./common.mjs";
|
|
14
|
+
const USAGE = `Usage: node extractors/semantic-scholar.mjs "<query>" [--tab <prefix>]
|
|
15
|
+
`;
|
|
16
|
+
const RESULT_SELECTOR = ".cl-paper-row[data-paper-id]";
|
|
17
|
+
function semanticScholarSearchUrl(query) {
|
|
18
|
+
const normalized = String(query || "").replaceAll("-", " ");
|
|
19
|
+
return `https://www.semanticscholar.org/search?q=${encodeURIComponent(normalized)}&sort=relevance`;
|
|
20
|
+
}
|
|
21
|
+
async function dismissCookieBanner(tab) {
|
|
22
|
+
await cdp([
|
|
23
|
+
"eval",
|
|
24
|
+
tab,
|
|
25
|
+
String.raw`
|
|
313
26
|
(() => {
|
|
314
27
|
const selectors = [
|
|
315
28
|
'.osano-cm-dialog__close',
|
|
@@ -323,7 +36,14 @@ import{spawn as C}from"node:child_process";import{basename as T}from"node:path";
|
|
|
323
36
|
}
|
|
324
37
|
return null;
|
|
325
38
|
})()
|
|
326
|
-
`
|
|
39
|
+
`
|
|
40
|
+
]).catch(() => null);
|
|
41
|
+
}
|
|
42
|
+
async function extractPapers(tab, { limit = 8 } = {}) {
|
|
43
|
+
const raw = await cdp([
|
|
44
|
+
"eval",
|
|
45
|
+
tab,
|
|
46
|
+
String.raw`
|
|
327
47
|
((limit) => {
|
|
328
48
|
function clean(value) {
|
|
329
49
|
return String(value || '').replace(/\s+/g, ' ').trim();
|
|
@@ -379,8 +99,101 @@ import{spawn as C}from"node:child_process";import{basename as T}from"node:path";
|
|
|
379
99
|
citationCount,
|
|
380
100
|
};
|
|
381
101
|
}));
|
|
382
|
-
})(${
|
|
383
|
-
`
|
|
384
|
-
|
|
102
|
+
})(${limit})
|
|
103
|
+
`
|
|
104
|
+
]);
|
|
105
|
+
try {
|
|
106
|
+
return JSON.parse(raw);
|
|
107
|
+
} catch {
|
|
108
|
+
return [];
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
function formatPaperSummary(papers) {
|
|
112
|
+
if (!papers.length)
|
|
113
|
+
return "Semantic Scholar returned no paper results.";
|
|
114
|
+
return papers.map((paper) => {
|
|
115
|
+
const parts = [];
|
|
116
|
+
if (paper.authors?.length)
|
|
117
|
+
parts.push(paper.authors.join(", "));
|
|
118
|
+
if (paper.venue)
|
|
119
|
+
parts.push(paper.venue);
|
|
120
|
+
if (paper.date)
|
|
121
|
+
parts.push(paper.date);
|
|
122
|
+
if (Number.isFinite(paper.citationCount)) {
|
|
123
|
+
parts.push(`${paper.citationCount.toLocaleString()} citations`);
|
|
124
|
+
}
|
|
125
|
+
const meta = parts.length ? ` — ${parts.join(" · ")}` : "";
|
|
126
|
+
const tldr = paper.tldr ? `
|
|
127
|
+
TLDR: ${paper.tldr}` : "";
|
|
128
|
+
return `${paper.rank}. ${paper.title}${meta}${tldr}`;
|
|
129
|
+
}).join(`
|
|
385
130
|
|
|
386
|
-
`)
|
|
131
|
+
`);
|
|
132
|
+
}
|
|
133
|
+
async function main() {
|
|
134
|
+
const args = await prepareArgs(process.argv.slice(2));
|
|
135
|
+
validateQuery(args, USAGE);
|
|
136
|
+
const { query, tabPrefix, short } = parseArgs(args);
|
|
137
|
+
const startTime = Date.now();
|
|
138
|
+
const mode = process.env.GREEDY_SEARCH_VISIBLE === "1" ? "visible" : "headless";
|
|
139
|
+
const env = {
|
|
140
|
+
engine: "semantic-scholar",
|
|
141
|
+
mode,
|
|
142
|
+
blockedBy: null,
|
|
143
|
+
verificationResult: null,
|
|
144
|
+
inputReady: null
|
|
145
|
+
};
|
|
146
|
+
try {
|
|
147
|
+
if (!tabPrefix)
|
|
148
|
+
await cdp(["list"]);
|
|
149
|
+
const tab = await getOrOpenTab(tabPrefix);
|
|
150
|
+
logStage(env, "nav", startTime);
|
|
151
|
+
await cdp(["nav", tab, semanticScholarSearchUrl(query)], 25000);
|
|
152
|
+
await new Promise((r) => setTimeout(r, 800));
|
|
153
|
+
logStage(env, "consent", startTime);
|
|
154
|
+
await dismissCookieBanner(tab);
|
|
155
|
+
logStage(env, "results-wait", startTime);
|
|
156
|
+
const inputReady = await waitForSelector(tab, RESULT_SELECTOR, 15000, 500);
|
|
157
|
+
env.inputReady = inputReady;
|
|
158
|
+
if (!inputReady) {
|
|
159
|
+
const body = await cdp([
|
|
160
|
+
"eval",
|
|
161
|
+
tab,
|
|
162
|
+
"document.body?.innerText || ''"
|
|
163
|
+
]).catch(() => "");
|
|
164
|
+
if (/captcha|cloudflare|verify|robot|blocked/i.test(body)) {
|
|
165
|
+
env.blockedBy = "verification";
|
|
166
|
+
env.verificationResult = "needs-human";
|
|
167
|
+
throw new Error("Semantic Scholar verification required — please solve it in the visible browser window");
|
|
168
|
+
}
|
|
169
|
+
throw new Error("Semantic Scholar results not found");
|
|
170
|
+
}
|
|
171
|
+
logStage(env, "extract", startTime);
|
|
172
|
+
const papers = await extractPapers(tab, { limit: short ? 5 : 8 });
|
|
173
|
+
const sources = papers.filter((paper) => paper.title && paper.url).map((paper) => ({
|
|
174
|
+
title: paper.pdfUrl ? `${paper.title} (PDF)` : paper.title,
|
|
175
|
+
url: paper.url,
|
|
176
|
+
semanticScholarUrl: paper.semanticScholarUrl,
|
|
177
|
+
paperId: paper.paperId,
|
|
178
|
+
citationCount: paper.citationCount,
|
|
179
|
+
venue: paper.venue,
|
|
180
|
+
year: paper.date
|
|
181
|
+
}));
|
|
182
|
+
const answer = formatPaperSummary(papers);
|
|
183
|
+
const durationMs = Date.now() - startTime;
|
|
184
|
+
outputJson({
|
|
185
|
+
answer: formatAnswer(answer, short),
|
|
186
|
+
sources,
|
|
187
|
+
query,
|
|
188
|
+
url: semanticScholarSearchUrl(query),
|
|
189
|
+
papers,
|
|
190
|
+
_envelope: buildEnvelope({ ...env, durationMs })
|
|
191
|
+
});
|
|
192
|
+
} catch (error) {
|
|
193
|
+
handleError(error, buildEnvelope({
|
|
194
|
+
...env,
|
|
195
|
+
durationMs: Date.now() - startTime
|
|
196
|
+
}));
|
|
197
|
+
}
|
|
198
|
+
}
|
|
199
|
+
main();
|