@web-auto/camo 0.2.0 → 0.2.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -21
- package/README.md +586 -586
- package/bin/browser-service.mjs +11 -11
- package/bin/camo.mjs +22 -22
- package/package.json +48 -48
- package/scripts/build.mjs +19 -19
- package/scripts/bump-version.mjs +34 -34
- package/scripts/check-file-size.mjs +80 -80
- package/scripts/file-size-policy.json +12 -2
- package/scripts/install.mjs +76 -76
- package/scripts/release.sh +54 -54
- package/src/autoscript/action-providers/index.mjs +6 -6
- package/src/autoscript/impact-engine.mjs +78 -78
- package/src/autoscript/runtime.mjs +1017 -1017
- package/src/autoscript/schema.mjs +376 -376
- package/src/cli.mjs +405 -405
- package/src/commands/attach.mjs +141 -141
- package/src/commands/autoscript.mjs +1011 -1011
- package/src/commands/browser.mjs +1255 -1255
- package/src/commands/container.mjs +401 -401
- package/src/commands/cookies.mjs +69 -69
- package/src/commands/create.mjs +98 -98
- package/src/commands/devtools.mjs +349 -349
- package/src/commands/events.mjs +152 -152
- package/src/commands/highlight-mode.mjs +24 -24
- package/src/commands/init.mjs +68 -68
- package/src/commands/lifecycle.mjs +275 -275
- package/src/commands/mouse.mjs +45 -45
- package/src/commands/profile.mjs +46 -46
- package/src/commands/record.mjs +115 -115
- package/src/commands/system.mjs +14 -14
- package/src/commands/window.mjs +123 -123
- package/src/container/change-notifier.mjs +362 -362
- package/src/container/element-filter.mjs +143 -143
- package/src/container/index.mjs +3 -3
- package/src/container/runtime-core/checkpoint.mjs +209 -209
- package/src/container/runtime-core/index.mjs +21 -21
- package/src/container/runtime-core/operations/index.mjs +774 -774
- package/src/container/runtime-core/operations/selector-scripts.mjs +277 -277
- package/src/container/runtime-core/operations/tab-pool.mjs +746 -746
- package/src/container/runtime-core/operations/viewport.mjs +189 -189
- package/src/container/runtime-core/search.mjs +190 -190
- package/src/container/runtime-core/subscription.mjs +224 -224
- package/src/container/runtime-core/utils.mjs +94 -94
- package/src/container/runtime-core/validation.mjs +127 -127
- package/src/container/runtime-core.mjs +1 -1
- package/src/container/subscription-registry.mjs +459 -459
- package/src/core/actions.mjs +561 -561
- package/src/core/browser.mjs +266 -266
- package/src/core/index.mjs +52 -52
- package/src/core/utils.mjs +91 -91
- package/src/events/daemon-entry.mjs +33 -33
- package/src/events/daemon.mjs +80 -80
- package/src/events/progress-log.mjs +109 -109
- package/src/events/ws-server.mjs +239 -239
- package/src/lib/client.mjs +200 -200
- package/src/lifecycle/cleanup.mjs +83 -83
- package/src/lifecycle/lock.mjs +126 -126
- package/src/lifecycle/session-registry.mjs +279 -279
- package/src/lifecycle/session-view.mjs +76 -76
- package/src/lifecycle/session-watchdog.mjs +281 -281
- package/src/services/browser-service/index.js +671 -671
- package/src/services/browser-service/internal/BrowserSession.input.test.js +389 -389
- package/src/services/browser-service/internal/BrowserSession.js +325 -304
- package/src/services/browser-service/internal/ElementRegistry.js +60 -60
- package/src/services/browser-service/internal/ProfileLock.js +84 -84
- package/src/services/browser-service/internal/SessionManager.js +184 -184
- package/src/services/browser-service/internal/SessionManager.test.js +39 -39
- package/src/services/browser-service/internal/browser-session/cookies.js +144 -144
- package/src/services/browser-service/internal/browser-session/input-ops.js +222 -222
- package/src/services/browser-service/internal/browser-session/input-pipeline.js +144 -144
- package/src/services/browser-service/internal/browser-session/logging.js +46 -46
- package/src/services/browser-service/internal/browser-session/navigation.js +38 -38
- package/src/services/browser-service/internal/browser-session/page-hooks.js +442 -442
- package/src/services/browser-service/internal/browser-session/page-management.js +302 -302
- package/src/services/browser-service/internal/browser-session/page-management.test.js +148 -148
- package/src/services/browser-service/internal/browser-session/recording.js +198 -198
- package/src/services/browser-service/internal/browser-session/runtime-events.js +61 -61
- package/src/services/browser-service/internal/browser-session/session-core.js +84 -84
- package/src/services/browser-service/internal/browser-session/session-state.js +38 -38
- package/src/services/browser-service/internal/browser-session/types.js +14 -14
- package/src/services/browser-service/internal/browser-session/utils.js +95 -95
- package/src/services/browser-service/internal/browser-session/viewport-manager.js +46 -46
- package/src/services/browser-service/internal/browser-session/viewport.js +215 -215
- package/src/services/browser-service/internal/container-matcher.js +851 -851
- package/src/services/browser-service/internal/container-registry.js +182 -182
- package/src/services/browser-service/internal/engine-manager.js +259 -259
- package/src/services/browser-service/internal/fingerprint.js +203 -203
- package/src/services/browser-service/internal/heartbeat.js +137 -137
- package/src/services/browser-service/internal/logging.js +46 -46
- package/src/services/browser-service/internal/page-runtime/runtime.js +1317 -1317
- package/src/services/browser-service/internal/pageRuntime.js +28 -28
- package/src/services/browser-service/internal/runtimeInjector.js +31 -31
- package/src/services/browser-service/internal/service-process-logger.js +140 -140
- package/src/services/browser-service/internal/state-bus.js +45 -45
- package/src/services/browser-service/internal/storage-paths.js +42 -42
- package/src/services/browser-service/internal/ws-server.js +1194 -1194
- package/src/services/browser-service/internal/ws-server.test.js +58 -58
- package/src/services/browser-service/server.mjs +6 -6
- package/src/services/controller/cli-bridge.js +93 -93
- package/src/services/controller/container-index.js +50 -50
- package/src/services/controller/container-storage.js +36 -36
- package/src/services/controller/controller-actions.js +207 -207
- package/src/services/controller/controller.js +1138 -1138
- package/src/services/controller/selectors.js +54 -54
- package/src/services/controller/transport.js +125 -125
- package/src/utils/args.mjs +26 -26
- package/src/utils/browser-service.mjs +544 -544
- package/src/utils/command-log.mjs +64 -64
- package/src/utils/config.mjs +214 -214
- package/src/utils/fingerprint.mjs +181 -181
- package/src/utils/help.mjs +216 -216
- package/src/utils/js-policy.mjs +13 -13
- package/src/utils/ws-client.mjs +30 -30
|
@@ -1,143 +1,143 @@
|
|
|
1
|
-
// Container Element Filter - Filter DOM elements by visibility, container definitions
|
|
2
|
-
|
|
3
|
-
function parseCssSelector(css) {
|
|
4
|
-
const raw = typeof css === 'string' ? css.trim() : '';
|
|
5
|
-
if (!raw) return [];
|
|
6
|
-
return raw
|
|
7
|
-
.split(',')
|
|
8
|
-
.map((item) => item.trim())
|
|
9
|
-
.filter(Boolean)
|
|
10
|
-
.map((item) => {
|
|
11
|
-
const tagMatch = item.match(/^[a-zA-Z][\w-]*/);
|
|
12
|
-
const idMatch = item.match(/#([\w-]+)/);
|
|
13
|
-
const classMatches = item.match(/\.([\w-]+)/g) || [];
|
|
14
|
-
return {
|
|
15
|
-
tag: tagMatch ? tagMatch[0].toLowerCase() : null,
|
|
16
|
-
id: idMatch ? idMatch[1] : null,
|
|
17
|
-
classes: classMatches.map((token) => token.slice(1)),
|
|
18
|
-
};
|
|
19
|
-
});
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
export class ElementFilter {
|
|
23
|
-
constructor(options = {}) {
|
|
24
|
-
this.viewportMargin = options.viewportMargin || 0;
|
|
25
|
-
this.minVisibleRatio = options.minVisibleRatio || 0.5;
|
|
26
|
-
}
|
|
27
|
-
|
|
28
|
-
// Check if element is in viewport
|
|
29
|
-
isInViewport(rect, viewport) {
|
|
30
|
-
return (
|
|
31
|
-
rect.left < viewport.width + this.viewportMargin &&
|
|
32
|
-
rect.right > -this.viewportMargin &&
|
|
33
|
-
rect.top < viewport.height + this.viewportMargin &&
|
|
34
|
-
rect.bottom > -this.viewportMargin
|
|
35
|
-
);
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
// Calculate visibility ratio
|
|
39
|
-
getVisibilityRatio(rect, viewport) {
|
|
40
|
-
const visibleLeft = Math.max(0, rect.left);
|
|
41
|
-
const visibleTop = Math.max(0, rect.top);
|
|
42
|
-
const visibleRight = Math.min(viewport.width, rect.right);
|
|
43
|
-
const visibleBottom = Math.min(viewport.height, rect.bottom);
|
|
44
|
-
|
|
45
|
-
const visibleArea = Math.max(0, visibleRight - visibleLeft) * Math.max(0, visibleBottom - visibleTop);
|
|
46
|
-
const totalArea = rect.width * rect.height;
|
|
47
|
-
|
|
48
|
-
return totalArea > 0 ? visibleArea / totalArea : 0;
|
|
49
|
-
}
|
|
50
|
-
|
|
51
|
-
// Filter elements by container definition
|
|
52
|
-
filterByContainer(elements, containerDef) {
|
|
53
|
-
const selectors = containerDef.selectors || [];
|
|
54
|
-
const results = [];
|
|
55
|
-
|
|
56
|
-
for (const element of elements) {
|
|
57
|
-
for (const selector of selectors) {
|
|
58
|
-
if (this.matchesSelector(element, selector)) {
|
|
59
|
-
results.push({
|
|
60
|
-
element,
|
|
61
|
-
container: containerDef,
|
|
62
|
-
matchedSelector: selector,
|
|
63
|
-
});
|
|
64
|
-
break;
|
|
65
|
-
}
|
|
66
|
-
}
|
|
67
|
-
}
|
|
68
|
-
|
|
69
|
-
return results;
|
|
70
|
-
}
|
|
71
|
-
|
|
72
|
-
// Check if element matches selector definition
|
|
73
|
-
matchesSelector(element, selector) {
|
|
74
|
-
if (!element || !selector) return false;
|
|
75
|
-
if (selector.css && element.selector === selector.css) return true;
|
|
76
|
-
|
|
77
|
-
const elementTag = typeof element.tag === 'string' ? element.tag.toLowerCase() : null;
|
|
78
|
-
const elementId = typeof element.id === 'string' ? element.id : null;
|
|
79
|
-
const elementClasses = new Set(Array.isArray(element.classes) ? element.classes : []);
|
|
80
|
-
|
|
81
|
-
const cssVariants = parseCssSelector(selector.css);
|
|
82
|
-
if (cssVariants.length > 0) {
|
|
83
|
-
for (const cssVariant of cssVariants) {
|
|
84
|
-
let matched = true;
|
|
85
|
-
if (cssVariant.tag && elementTag !== cssVariant.tag) matched = false;
|
|
86
|
-
if (cssVariant.id && elementId !== cssVariant.id) matched = false;
|
|
87
|
-
if (matched && cssVariant.classes.length > 0) {
|
|
88
|
-
matched = cssVariant.classes.every((className) => elementClasses.has(className));
|
|
89
|
-
}
|
|
90
|
-
if (matched) return true;
|
|
91
|
-
}
|
|
92
|
-
}
|
|
93
|
-
|
|
94
|
-
const requiredTag = selector.tag ? String(selector.tag).toLowerCase() : null;
|
|
95
|
-
const requiredId = selector.id ? String(selector.id) : null;
|
|
96
|
-
const requiredClasses = Array.isArray(selector.classes)
|
|
97
|
-
? selector.classes.filter(Boolean).map((className) => String(className))
|
|
98
|
-
: [];
|
|
99
|
-
|
|
100
|
-
const hasStructuredSelector = Boolean(requiredTag || requiredId || requiredClasses.length > 0);
|
|
101
|
-
if (!hasStructuredSelector) return false;
|
|
102
|
-
if (requiredTag && elementTag !== requiredTag) return false;
|
|
103
|
-
if (requiredId && elementId !== requiredId) return false;
|
|
104
|
-
if (requiredClasses.length > 0 && !requiredClasses.every((className) => elementClasses.has(className))) {
|
|
105
|
-
return false;
|
|
106
|
-
}
|
|
107
|
-
return true;
|
|
108
|
-
}
|
|
109
|
-
|
|
110
|
-
// Main filter method
|
|
111
|
-
filter(elements, options = {}) {
|
|
112
|
-
const {
|
|
113
|
-
container,
|
|
114
|
-
viewport,
|
|
115
|
-
requireVisible = true,
|
|
116
|
-
minVisibleRatio = this.minVisibleRatio,
|
|
117
|
-
} = options;
|
|
118
|
-
|
|
119
|
-
let results = [...elements];
|
|
120
|
-
|
|
121
|
-
// Filter by container definition
|
|
122
|
-
if (container) {
|
|
123
|
-
results = this.filterByContainer(results, container);
|
|
124
|
-
}
|
|
125
|
-
|
|
126
|
-
// Filter by viewport visibility
|
|
127
|
-
if (requireVisible && viewport) {
|
|
128
|
-
results = results.filter(item => {
|
|
129
|
-
const rect = item.element?.rect || item.rect;
|
|
130
|
-
if (!rect) return false;
|
|
131
|
-
const ratio = this.getVisibilityRatio(rect, viewport);
|
|
132
|
-
item.visibilityRatio = ratio;
|
|
133
|
-
return ratio >= minVisibleRatio;
|
|
134
|
-
});
|
|
135
|
-
}
|
|
136
|
-
|
|
137
|
-
return results;
|
|
138
|
-
}
|
|
139
|
-
}
|
|
140
|
-
|
|
141
|
-
export function createElementFilter(options) {
|
|
142
|
-
return new ElementFilter(options);
|
|
143
|
-
}
|
|
1
|
+
// Container Element Filter - Filter DOM elements by visibility, container definitions
|
|
2
|
+
|
|
3
|
+
function parseCssSelector(css) {
|
|
4
|
+
const raw = typeof css === 'string' ? css.trim() : '';
|
|
5
|
+
if (!raw) return [];
|
|
6
|
+
return raw
|
|
7
|
+
.split(',')
|
|
8
|
+
.map((item) => item.trim())
|
|
9
|
+
.filter(Boolean)
|
|
10
|
+
.map((item) => {
|
|
11
|
+
const tagMatch = item.match(/^[a-zA-Z][\w-]*/);
|
|
12
|
+
const idMatch = item.match(/#([\w-]+)/);
|
|
13
|
+
const classMatches = item.match(/\.([\w-]+)/g) || [];
|
|
14
|
+
return {
|
|
15
|
+
tag: tagMatch ? tagMatch[0].toLowerCase() : null,
|
|
16
|
+
id: idMatch ? idMatch[1] : null,
|
|
17
|
+
classes: classMatches.map((token) => token.slice(1)),
|
|
18
|
+
};
|
|
19
|
+
});
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
export class ElementFilter {
|
|
23
|
+
constructor(options = {}) {
|
|
24
|
+
this.viewportMargin = options.viewportMargin || 0;
|
|
25
|
+
this.minVisibleRatio = options.minVisibleRatio || 0.5;
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
// Check if element is in viewport
|
|
29
|
+
isInViewport(rect, viewport) {
|
|
30
|
+
return (
|
|
31
|
+
rect.left < viewport.width + this.viewportMargin &&
|
|
32
|
+
rect.right > -this.viewportMargin &&
|
|
33
|
+
rect.top < viewport.height + this.viewportMargin &&
|
|
34
|
+
rect.bottom > -this.viewportMargin
|
|
35
|
+
);
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
// Calculate visibility ratio
|
|
39
|
+
getVisibilityRatio(rect, viewport) {
|
|
40
|
+
const visibleLeft = Math.max(0, rect.left);
|
|
41
|
+
const visibleTop = Math.max(0, rect.top);
|
|
42
|
+
const visibleRight = Math.min(viewport.width, rect.right);
|
|
43
|
+
const visibleBottom = Math.min(viewport.height, rect.bottom);
|
|
44
|
+
|
|
45
|
+
const visibleArea = Math.max(0, visibleRight - visibleLeft) * Math.max(0, visibleBottom - visibleTop);
|
|
46
|
+
const totalArea = rect.width * rect.height;
|
|
47
|
+
|
|
48
|
+
return totalArea > 0 ? visibleArea / totalArea : 0;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
// Filter elements by container definition
|
|
52
|
+
filterByContainer(elements, containerDef) {
|
|
53
|
+
const selectors = containerDef.selectors || [];
|
|
54
|
+
const results = [];
|
|
55
|
+
|
|
56
|
+
for (const element of elements) {
|
|
57
|
+
for (const selector of selectors) {
|
|
58
|
+
if (this.matchesSelector(element, selector)) {
|
|
59
|
+
results.push({
|
|
60
|
+
element,
|
|
61
|
+
container: containerDef,
|
|
62
|
+
matchedSelector: selector,
|
|
63
|
+
});
|
|
64
|
+
break;
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
return results;
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
// Check if element matches selector definition
|
|
73
|
+
matchesSelector(element, selector) {
|
|
74
|
+
if (!element || !selector) return false;
|
|
75
|
+
if (selector.css && element.selector === selector.css) return true;
|
|
76
|
+
|
|
77
|
+
const elementTag = typeof element.tag === 'string' ? element.tag.toLowerCase() : null;
|
|
78
|
+
const elementId = typeof element.id === 'string' ? element.id : null;
|
|
79
|
+
const elementClasses = new Set(Array.isArray(element.classes) ? element.classes : []);
|
|
80
|
+
|
|
81
|
+
const cssVariants = parseCssSelector(selector.css);
|
|
82
|
+
if (cssVariants.length > 0) {
|
|
83
|
+
for (const cssVariant of cssVariants) {
|
|
84
|
+
let matched = true;
|
|
85
|
+
if (cssVariant.tag && elementTag !== cssVariant.tag) matched = false;
|
|
86
|
+
if (cssVariant.id && elementId !== cssVariant.id) matched = false;
|
|
87
|
+
if (matched && cssVariant.classes.length > 0) {
|
|
88
|
+
matched = cssVariant.classes.every((className) => elementClasses.has(className));
|
|
89
|
+
}
|
|
90
|
+
if (matched) return true;
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
const requiredTag = selector.tag ? String(selector.tag).toLowerCase() : null;
|
|
95
|
+
const requiredId = selector.id ? String(selector.id) : null;
|
|
96
|
+
const requiredClasses = Array.isArray(selector.classes)
|
|
97
|
+
? selector.classes.filter(Boolean).map((className) => String(className))
|
|
98
|
+
: [];
|
|
99
|
+
|
|
100
|
+
const hasStructuredSelector = Boolean(requiredTag || requiredId || requiredClasses.length > 0);
|
|
101
|
+
if (!hasStructuredSelector) return false;
|
|
102
|
+
if (requiredTag && elementTag !== requiredTag) return false;
|
|
103
|
+
if (requiredId && elementId !== requiredId) return false;
|
|
104
|
+
if (requiredClasses.length > 0 && !requiredClasses.every((className) => elementClasses.has(className))) {
|
|
105
|
+
return false;
|
|
106
|
+
}
|
|
107
|
+
return true;
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
// Main filter method
|
|
111
|
+
filter(elements, options = {}) {
|
|
112
|
+
const {
|
|
113
|
+
container,
|
|
114
|
+
viewport,
|
|
115
|
+
requireVisible = true,
|
|
116
|
+
minVisibleRatio = this.minVisibleRatio,
|
|
117
|
+
} = options;
|
|
118
|
+
|
|
119
|
+
let results = [...elements];
|
|
120
|
+
|
|
121
|
+
// Filter by container definition
|
|
122
|
+
if (container) {
|
|
123
|
+
results = this.filterByContainer(results, container);
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
// Filter by viewport visibility
|
|
127
|
+
if (requireVisible && viewport) {
|
|
128
|
+
results = results.filter(item => {
|
|
129
|
+
const rect = item.element?.rect || item.rect;
|
|
130
|
+
if (!rect) return false;
|
|
131
|
+
const ratio = this.getVisibilityRatio(rect, viewport);
|
|
132
|
+
item.visibilityRatio = ratio;
|
|
133
|
+
return ratio >= minVisibleRatio;
|
|
134
|
+
});
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
return results;
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
export function createElementFilter(options) {
|
|
142
|
+
return new ElementFilter(options);
|
|
143
|
+
}
|
package/src/container/index.mjs
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
// Container module - element filtering and change notification
|
|
2
|
-
export { ElementFilter, createElementFilter } from './element-filter.mjs';
|
|
3
|
-
export { ChangeNotifier, getChangeNotifier, destroyChangeNotifier } from './change-notifier.mjs';
|
|
1
|
+
// Container module - element filtering and change notification
|
|
2
|
+
export { ElementFilter, createElementFilter } from './element-filter.mjs';
|
|
3
|
+
export { ChangeNotifier, getChangeNotifier, destroyChangeNotifier } from './change-notifier.mjs';
|