agentic-stealth-browser 2.3.0__tar.gz → 2.5.0__tar.gz
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.
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/CHANGELOG.md +107 -0
- agentic_stealth_browser-2.5.0/CODE_OF_CONDUCT.md +70 -0
- agentic_stealth_browser-2.5.0/CONTRIBUTING.md +237 -0
- agentic_stealth_browser-2.5.0/MANIFEST.in +19 -0
- agentic_stealth_browser-2.5.0/PKG-INFO +277 -0
- agentic_stealth_browser-2.5.0/README.md +238 -0
- agentic_stealth_browser-2.5.0/SECURITY.md +39 -0
- agentic_stealth_browser-2.5.0/agentic_stealth_browser.egg-info/PKG-INFO +277 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/agentic_stealth_browser.egg-info/SOURCES.txt +74 -1
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/agentic_stealth_browser.egg-info/top_level.txt +3 -0
- agentic_stealth_browser-2.5.0/assets/hn-demo.gif +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/audit/logger.py +0 -6
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/behavior/human_behavior.py +7 -1
- agentic_stealth_browser-2.5.0/canary/__init__.py +8 -0
- agentic_stealth_browser-2.5.0/canary/badge_gen.py +48 -0
- agentic_stealth_browser-2.5.0/canary/dashboard_gen.py +77 -0
- agentic_stealth_browser-2.5.0/canary/history.py +101 -0
- agentic_stealth_browser-2.5.0/canary/readme_gen.py +54 -0
- agentic_stealth_browser-2.5.0/canary/runner.py +83 -0
- agentic_stealth_browser-2.5.0/canary/score.py +26 -0
- agentic_stealth_browser-2.5.0/canary/sites.py +91 -0
- agentic_stealth_browser-2.5.0/canary/templates/badge.svg.j2 +17 -0
- agentic_stealth_browser-2.5.0/canary/templates/dashboard.html.j2 +185 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/core/agent_browser.py +353 -8
- agentic_stealth_browser-2.5.0/docs/ATTACH_OVER_CDP.md +146 -0
- agentic_stealth_browser-2.5.0/docs/README.md +28 -0
- agentic_stealth_browser-2.5.0/docs/agentic-stealth-browser-analysis-report.md +93 -0
- agentic_stealth_browser-2.5.0/docs/canary/README.md +43 -0
- agentic_stealth_browser-2.5.0/docs/canary/badge.svg +17 -0
- agentic_stealth_browser-2.5.0/docs/canary/history.jsonl +1 -0
- agentic_stealth_browser-2.5.0/docs/canary/index.html +213 -0
- agentic_stealth_browser-2.5.0/docs/canary.md +43 -0
- agentic_stealth_browser-2.5.0/docs/plans/2026-06-01-v2.4.0-attach-mode-hardening.md +439 -0
- agentic_stealth_browser-2.5.0/docs/plans/2026-06-03-v2.5.0-real-backend-adapters.md +479 -0
- agentic_stealth_browser-2.5.0/docs/plans/misc/GOAL_MODE_HERMES_BROWSER_DASHBOARD.md +71 -0
- agentic_stealth_browser-2.5.0/docs/plans/misc/HN_POST.md +52 -0
- agentic_stealth_browser-2.5.0/docs/plans/misc/OPEN_SOURCE_READINESS.md +161 -0
- agentic_stealth_browser-2.5.0/docs/plans/misc/RELEASE_AUTONOMOUS_PLAN.md +115 -0
- agentic_stealth_browser-2.5.0/examples/recipes/01_cloudflare_bypass.py +32 -0
- agentic_stealth_browser-2.5.0/examples/recipes/02_linkedin_search.py +48 -0
- agentic_stealth_browser-2.5.0/examples/recipes/03_amazon_product.py +49 -0
- agentic_stealth_browser-2.5.0/examples/recipes/README.md +18 -0
- agentic_stealth_browser-2.5.0/mcp_security.py +411 -0
- agentic_stealth_browser-2.5.0/plugins/__init__.py +6 -0
- agentic_stealth_browser-2.5.0/plugins/template/__init__.py +4 -0
- agentic_stealth_browser-2.5.0/plugins/template/plugin.py +85 -0
- agentic_stealth_browser-2.5.0/production/adapters/__init__.py +111 -0
- agentic_stealth_browser-2.5.0/production/adapters/_jsonrpc_stdio.py +87 -0
- agentic_stealth_browser-2.5.0/production/adapters/agentic_stealth_mcp.py +240 -0
- agentic_stealth_browser-2.5.0/production/adapters/base.py +118 -0
- agentic_stealth_browser-2.5.0/production/adapters/cdp_bridge.py +197 -0
- agentic_stealth_browser-2.5.0/production/adapters/playwright_mcp.py +251 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/cli.py +16 -15
- agentic_stealth_browser-2.5.0/production/dashboard_adapter_bridge.py +76 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/hermes_dashboard.py +84 -2
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/mcp_input_validator.py +21 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/mcp_server.py +349 -5
- agentic_stealth_browser-2.5.0/production/sdk/__init__.py +14 -0
- agentic_stealth_browser-2.5.0/production/sdk/client.py +305 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/proxy/proxy_manager.py +7 -7
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/pyproject.toml +31 -1
- agentic_stealth_browser-2.5.0/scripts/canary_run.py +54 -0
- agentic_stealth_browser-2.5.0/scripts/evaluate_stealth.py +286 -0
- agentic_stealth_browser-2.5.0/scripts/generate-demo-gif.py +214 -0
- agentic_stealth_browser-2.5.0/scripts/health_check.py +257 -0
- agentic_stealth_browser-2.5.0/scripts/hn-demo.py +61 -0
- agentic_stealth_browser-2.5.0/scripts/make-gif.py +80 -0
- agentic_stealth_browser-2.5.0/scripts/migrate_v1_to_v2.py +154 -0
- agentic_stealth_browser-2.5.0/scripts/perf_benchmark.py +290 -0
- agentic_stealth_browser-2.5.0/scripts/setup_rbb.sh +220 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/sessions/cookie_manager.py +74 -33
- agentic_stealth_browser-2.5.0/stealth/__init__.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/stealth/presets.py +24 -0
- agentic_stealth_browser-2.5.0/tests/test_adapter_agentic_stealth_mcp.py +389 -0
- agentic_stealth_browser-2.5.0/tests/test_adapter_cdp_bridge.py +295 -0
- agentic_stealth_browser-2.5.0/tests/test_adapter_playwright_mcp.py +416 -0
- agentic_stealth_browser-2.5.0/tests/test_attach_over_cdp.py +395 -0
- agentic_stealth_browser-2.5.0/tests/test_backend_adapter_contract.py +293 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_cookie_manager_unit.py +10 -10
- agentic_stealth_browser-2.5.0/tests/test_dashboard_protocol_bridge.py +170 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_hermes_dashboard.py +42 -2
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_human_behavior_fuzz.py +8 -10
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_mcp_server_runtime.py +168 -2
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_mcp_stealth_workflows.py +4 -1
- agentic_stealth_browser-2.5.0/tests/test_mcp_url_safety.py +100 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_phase7_fixes.py +24 -5
- agentic_stealth_browser-2.5.0/workflows/library/auto-session-test.yaml +4 -0
- agentic_stealth_browser-2.5.0/workflows/library/common/login.yaml +2 -0
- agentic_stealth_browser-2.5.0/workflows/library/common/verify-email.yaml +2 -0
- agentic_stealth_browser-2.5.0/workflows/library/linkedin/send-connection-request.yaml +63 -0
- agentic_stealth_browser-2.5.0/workflows/library/meta-test.yaml +2 -0
- agentic_stealth_browser-2.5.0/workflows/library/simple-test.yaml +7 -0
- agentic_stealth_browser-2.5.0/workflows/library/teach-test/test-teach.yaml +8 -0
- agentic_stealth_browser-2.5.0/workflows/library/upwork/add-portfolio-item.yaml +54 -0
- agentic_stealth_browser-2.5.0/workflows/library/upwork/apply.yaml +2 -0
- agentic_stealth_browser-2.5.0/workflows/library/upwork/edit-title.yaml +40 -0
- agentic_stealth_browser-2.5.0/workflows/library/upwork/submit-proposal.yaml +48 -0
- agentic_stealth_browser-2.5.0/workflows/library/upwork/update-rate.yaml +40 -0
- agentic_stealth_browser-2.3.0/MANIFEST.in +0 -9
- agentic_stealth_browser-2.3.0/PKG-INFO +0 -184
- agentic_stealth_browser-2.3.0/README.md +0 -145
- agentic_stealth_browser-2.3.0/agentic_stealth_browser.egg-info/PKG-INFO +0 -184
- agentic_stealth_browser-2.3.0/examples/recipes/README.md +0 -10
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/.env.example +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/LICENSE +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/agentic_stealth_browser.egg-info/dependency_links.txt +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/agentic_stealth_browser.egg-info/entry_points.txt +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/agentic_stealth_browser.egg-info/requires.txt +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/ai/__init__.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/ai/ai_hooks.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/audit/__init__.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/behavior/__init__.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/behavior/adaptive_tuner.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/behavior/orchestration.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/behavior/persona_rotator.py +0 -0
- {agentic_stealth_browser-2.3.0/core → agentic_stealth_browser-2.5.0/canary}/py.typed +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/core/__init__.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/core/account_health.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/core/account_warming.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/core/connection_pool.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/core/error_messages.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/core/feature_flags.py +0 -0
- /agentic_stealth_browser-2.3.0/proxy/__init__.py → /agentic_stealth_browser-2.5.0/core/py.typed +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/core/session_checkpoint.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/core/types.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/examples/recipes/linkedin.md +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/linkedin/__init__.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/linkedin/actions.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/Dockerfile +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/__init__.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/approval_gate.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/audit_enrichment.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/deprecations.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/docker-compose.yml +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/docker-healthcheck.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/mcp_session_isolation.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/metrics.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/otel_export.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/policy_engine.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/profiler.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/rate_limiter.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/production/workflow_orchestrator.py +0 -0
- {agentic_stealth_browser-2.3.0/recovery → agentic_stealth_browser-2.5.0/proxy}/__init__.py +0 -0
- {agentic_stealth_browser-2.3.0/scraping → agentic_stealth_browser-2.5.0/recovery}/__init__.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/recovery/anti_block_orchestrator.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/recovery/detectors.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/recovery/explain_blocked.py +0 -0
- {agentic_stealth_browser-2.3.0/sessions → agentic_stealth_browser-2.5.0/scraping}/__init__.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/scraping/scraper.py +0 -0
- {agentic_stealth_browser-2.3.0/stealth → agentic_stealth_browser-2.5.0/sessions}/__init__.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/sessions/session_manager.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/setup.cfg +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/stealth/advanced_stealth.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/stealth/cache.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/stealth/firefox_adapter.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/stealth/headers.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/stealth/profiles.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/stealth/tls_fingerprint.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/stealth/tls_ja3_ja4.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/debug_nowsecure.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/detection_check.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/detection_runner.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/fingerprint_scorecard.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/run_detection_tests.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_account_health.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_account_warming.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_adaptive_tuner.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_basic.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_cdp_snapshots.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_connection_pool.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_contract_agent_browser.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_detectors.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_differential.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_docker_config.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_e2e_anti_block_recovery.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_e2e_protected_sites_placeholder.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_golden_master.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_integration_modules.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_linkedin_actions.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_mcp_contract.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_metrics_collector_unit.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_mutation_stealth.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_persona_rotator.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_player.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_proxy_config_unit.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_proxy_manager.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_rate_limiter_unit.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_recorder.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_recovery.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_recovery_phase1.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_recovery_state_machine.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_rehearsal_validation.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_selector_auto_heal.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_session_checkpoint.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_stealth_cache.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_stealth_coverage.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_stealth_modules.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_stress_multi_account.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_tls_ja3_ja4.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_workflow_orchestrator.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_workflow_schema.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_workflow_schema_unit.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/tests/test_workflow_versioning.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/workflows/__init__.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/workflows/action_interpreter.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/workflows/player.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/workflows/recorder.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/workflows/recovery.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/workflows/schema.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/workflows/selector_generator.py +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/workflows/test-echo.yaml +0 -0
- {agentic_stealth_browser-2.3.0 → agentic_stealth_browser-2.5.0}/workflows/variable_resolver.py +0 -0
|
@@ -7,6 +7,113 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
7
7
|
|
|
8
8
|
---
|
|
9
9
|
|
|
10
|
+
## [Unreleased]
|
|
11
|
+
|
|
12
|
+
## [2.5.0] — Real Dashboard Backend Adapters (#444) (2026-06-07)
|
|
13
|
+
|
|
14
|
+
### Added
|
|
15
|
+
- **`BackendAdapter` Protocol + `Capability` enum** (`production/adapters/base.py:84`): runtime-checkable protocol with `launch`/`close`/`navigate`/`click`/`fill`/`screenshot`/`status`/`capabilities` surface. All three backends (M1/M2/M3) implement it. New `AdapterLaunchError` and `AdapterCapabilityError` exception types; `register_adapter` enforces non-empty string names. (#444 M0)
|
|
16
|
+
- **`CDPBridgeAdapter`** (`production/adapters/cdp_bridge.py`): Playwright `connect_over_cdp` over WebSocket. Used for adopted-context / WSL-host workflows where the operator already owns a browser process. (#444 M1)
|
|
17
|
+
- **`PlaywrightMCPAdapter`** (`production/adapters/playwright_mcp.py`): stdio subprocess + MCP JSON-RPC. Spawns `npx @playwright/mcp` with an explicit env allowlist (PATH, HOME) and a 16 MB `MAX_FRAME_BYTES` frame cap. (#444 M2)
|
|
18
|
+
- **`AgenticStealthMCPAdapter`** (`production/adapters/agentic_stealth_mcp.py`): stdio subprocess + MCP JSON-RPC, round-trips through the bundled `production.mcp_server` runtime. Same env allowlist, frame cap, and stderr-drain guarantees as M2. (#444 M3)
|
|
19
|
+
- **Dashboard backend wiring (M4)**: `BrowserRuntimeManager` resolves the configured backend through the adapter registry, records an audit event on backend switch, surfaces negotiated capabilities in dashboard status, and rejects unsupported actions with a backend-specific error. `production/dashboard_adapter_bridge.py` is now a thin shim that re-exports the three M1–M3 adapters. (#444 M4)
|
|
20
|
+
|
|
21
|
+
### Changed
|
|
22
|
+
- `production/hermes_dashboard.py` re-exports `BackendAdapter` from `production/adapters/`.
|
|
23
|
+
- `production/dashboard_adapter_bridge.py` thin shim replaces the three alias backends.
|
|
24
|
+
- `MANIFEST.in`: ships `assets/*.{gif,png,jpg,svg}` (demo GIF), `docs/`, `CODE_OF_CONDUCT.md`, `CONTRIBUTING.md`, `SECURITY.md` (sdist previously dropped the demo GIF and the entire `docs/` tree).
|
|
25
|
+
- `README.md`: added "What is this / When to use / When NOT to use" block at top, honest comparison table (region client-hello profiles, not full uTLS), install-from-source section, full project tree + doc index. Dropped unverified test-count badge and Buy Me A Coffee. 177 → 238 lines.
|
|
26
|
+
- New `docs/README.md` operator/reference/planning index. Root-level `*PLAN.md` / `*READINESS.md` / `*DASHBOARD.md` / `HN_POST.md` moved to `docs/plans/misc/` as historical.
|
|
27
|
+
- Examples rewritten for honesty and reproducibility: `01_cloudflare_bypass.py` (nowsecure.nl + screenshot), `02_linkedin_search.py` (`linkedin_2026` preset + webdriver check + DDG), `03_amazon_product.py` (product → title + price). `recipes/README.md` table updated.
|
|
28
|
+
- `pyproject.toml` version 2.4.1 → 2.5.0.
|
|
29
|
+
|
|
30
|
+
### Fixed
|
|
31
|
+
- **#444 M0 review (showstoppers)**:
|
|
32
|
+
- **S1 capability gating**: M2/M3 `navigate`/`click`/`fill`/`screenshot` now call `self.supports()` and raise `AdapterCapabilityError` if the adapter doesn't declare the capability (enforces `base.py:84` protocol contract). New `_require_capability()` helper on each adapter.
|
|
33
|
+
- **S2 stderr drain**: M2/M3 `stderr=PIPE` is now drained by a background task started right after `spawn` and cancelled in `close()`. A noisy child no longer fills the ~64 KB kernel pipe buffer, blocks on its next stderr write, hangs the handshake, and triggers a slow SIGKILL on close.
|
|
34
|
+
- **F1 stale state on retry**: after MCP handshake failure, `terminate_subprocess()` is called and `self._proc` / `self._client` are cleared. A caller that catches `AdapterLaunchError` and then calls `close()` no longer operates on a dead `Process` handle.
|
|
35
|
+
- **#444 M0 review (smaller)**:
|
|
36
|
+
- **F2 frame cap**: `_jsonrpc_stdio.readline()` now enforces `MAX_FRAME_BYTES = 16 MB` and raises `ConnectionError` on overflow. A misbehaving server emitting a multi-GB line no longer OOMs the client.
|
|
37
|
+
- **F3 env allowlist**: both stdio adapters now pass an explicit `env={PATH, HOME}` to `asyncio.create_subprocess_exec` instead of inheriting the operator's full environment (`OPENAI_API_KEY`, `AWS_*`, `DATABASE_URL`, ...).
|
|
38
|
+
- **A3 dead tautology**: `cdp_bridge.screenshot()` had a defensive `Capability.SCREENSHOT` check that could never fire (always in `capabilities()`). Branch removed; M0 contract is the only contract that matters.
|
|
39
|
+
- **M0 code-quality review (17abc50)**: exception types narrowed to library-specific where appropriate, `isinstance` coverage tightened, defensive tautology branches removed, transport teardown made symmetric with launch.
|
|
40
|
+
- **Adapter capability gating**: now consistent across M1/M2/M3 — each action is contractually declared, not assumed.
|
|
41
|
+
- **Ruff/format housekeeping** (4432701): 12 ruff format issues + 1 unused import fixed.
|
|
42
|
+
|
|
43
|
+
### Tests / CI
|
|
44
|
+
- `tests/test_backend_adapter_contract.py` — new contract test pinning the M0 Protocol surface, `Capability` enum members, and `register_adapter` duplicate/empty/non-string rejection.
|
|
45
|
+
- `tests/test_adapter_cdp_bridge.py`, `tests/test_adapter_playwright_mcp.py`, `tests/test_adapter_agentic_stealth_mcp.py` — new per-adapter tests covering launch, capability negotiation, action gating, stderr drain, env allowlist, and close lifecycle.
|
|
46
|
+
- `tests/test_dashboard_protocol_bridge.py` — new dashboard-wiring test (M4): audit event on backend switch, capability surface, unsupported-action rejection.
|
|
47
|
+
- `pytest -q`: 1025 collected, 1023 passed, 2 e2e skipped, 0 failed (139 s; baseline maintained).
|
|
48
|
+
- `ruff check` + `ruff format --check` clean across 159 Python files.
|
|
49
|
+
|
|
50
|
+
Closes #444.
|
|
51
|
+
|
|
52
|
+
---
|
|
53
|
+
|
|
54
|
+
## [2.4.1] — v2.4.0 Stabilization Patch (2026-06-03)
|
|
55
|
+
|
|
56
|
+
### Fixed / Security / Reliability (P0/P1 per #459)
|
|
57
|
+
- **#454** MCP nav/scrape: `is_url_safe` now fails closed for non-http(s) schemes (`file:`, `javascript:`, `data:`, `ftp:`, ...), missing hosts, DNS errors, and empty resolutions. Unsafe inputs raise `MCP_SSRF_BLOCKED` before any browser navigation. Added unit matrix + dispatch regression tests.
|
|
58
|
+
- **#455** MCP runtime: declarative input validation from `production/mcp_input_validator.py` is now enforced in `tools/call` dispatch (types, lengths, ranges, required, patterns, `additionalProperties: false`). Validation errors return stable `MCP_VALIDATION_ERROR` without invoking handlers. Schema/validator parity and dispatch tests added.
|
|
59
|
+
- **#451** CDP attach: adopted user tabs (`new_context=False`) are no longer closed on `close()`. New `_owns_page` tracking + conditional teardown; adopted contexts/pages preserved per contract. Updated tests + docs.
|
|
60
|
+
- **#452** CDP attach: post-`connect_over_cdp` failures (bad context_index, new_context, page create, stealth) now best-effort rollback `_pw`, `_remote_browser`, owned ctxs (never adopted), and reset attach flags for clean retry.
|
|
61
|
+
- **#453** CDP attach: attach path now initializes `human`, `orchestrator`, `logger`, `scraper`, `ai`, `recovery` (with attach degradation notes). `safe_goto`/`safe_click`/`safe_type` + MCP `stealth_scrape` now operational on attached sessions.
|
|
62
|
+
- **#458** Hermes dashboard: startup rejects default/empty/`change-me` password when binding to non-loopback (0.0.0.0, RFC1918, public, IPv6 non-loop). Loopback dev still convenient. Added guard tests.
|
|
63
|
+
- **#457** CLI `scrape`: removed double `launch()` (async-with already launches; now passes preset/region via ctor so aenter applies them). Exactly one launch + one close. Aligned all user-facing names/help/examples to `agentic-stealth-browser`. Mocked regression test.
|
|
64
|
+
- **#456** Packaging: `pyproject.toml` now includes `production.*`, `workflows.*`, `plugins.*`. `MANIFEST.in` extended. CI verify expanded for SDK import + bundled workflow discovery from clean cwd. MCP server workflow root switched to user-writable `~/.agentic-browser/...` + bundled discovery fallback for install safety.
|
|
65
|
+
- **#447** MCP version: `SERVER_VERSION` now derives from `importlib.metadata.version("agentic-stealth-browser")` (falls back to 2.4.1); no longer stale.
|
|
66
|
+
- **#448** CDP attach gate: relaxed RFC1918 rejection under `allow_remote=true` for attach (WSL host IPs are intentionally private); link-local/cloud still blocked. Nav remains strict. Reconciled docs + tests with real WSL workflow.
|
|
67
|
+
- **#450** Docs/metadata: toned down TLS/JA3/JA4 claims to "region client-hello profiles (process-level)"; attach degradation already documented the limits. No wire-level full-stack spoofing claimed.
|
|
68
|
+
- **#449** Release hygiene: refreshed counts, changelog, version to 2.4.1, support notes, publish smoke.
|
|
69
|
+
|
|
70
|
+
### Added
|
|
71
|
+
- Runtime helpers and ownership tracking for attach mode.
|
|
72
|
+
- Validation dispatch + matrix tests; single-launch CLI mock test; dashboard bind security tests.
|
|
73
|
+
|
|
74
|
+
### Changed
|
|
75
|
+
- `pyproject.toml` version 2.4.0 → 2.4.1; packages.find + MANIFEST.in for full artifacts.
|
|
76
|
+
- Attach lifecycle docs/examples (no more auto-launch + attach in same `async with`).
|
|
77
|
+
- MCP attach remote safety contract + tests for WSL compatibility.
|
|
78
|
+
|
|
79
|
+
### Tests / CI
|
|
80
|
+
- All non-e2e/non-live green.
|
|
81
|
+
- Focused attach + MCP safety + validation + CLI mocks + dashboard guard.
|
|
82
|
+
- `ruff check` + `ruff format --check` pass.
|
|
83
|
+
- Wheel build + import + discovery smoke updated in publish.yml.
|
|
84
|
+
|
|
85
|
+
Closes #447, #448, #449, #450, #451, #452, #453, #454, #455, #456, #457, #458, #459 (patch scope).
|
|
86
|
+
|
|
87
|
+
---
|
|
88
|
+
|
|
89
|
+
## [2.4.0] — Attach-Mode Hardening (2026-06-01)
|
|
90
|
+
|
|
91
|
+
### Fixed
|
|
92
|
+
- **#438** `stealth_attach_over_cdp` loopback gate reused `is_url_safe` — DNS rebinding / hostname→private-IP bypass closed. Replaces string match with full RFC-1918 + link-local + cloud-metadata check. The gate is now a two-layer check: `is_loopback_host` first, then `is_url_safe` only when `allow_remote=true` (so even explicitly-allowed remote hosts can't be RFC-1918 or link-local).
|
|
93
|
+
- **#441** Link-local IPv6 (`fe80::/10`) added to `_BLOCKED_NETWORKS`. Side-effect of #438's refactor — `is_url_safe` now rejects IPv6 link-local the same way it rejects IPv4 `169.254.0.0/16`.
|
|
94
|
+
- **#440** `add_init_script` install failure now surfaces in the return payload as `stealth_applied: false` + `stealth_error: "<ExceptionType>: <message>"`. Previously silent. New `stealth_requested` field distinguishes caller intent from actual install result.
|
|
95
|
+
- **#439** `AgentBrowser.close()` teardown logic now uses a typed `TeardownMode` enum (`LAUNCHED | POOLED | ATTACHED_OWNED_CTX | ATTACHED_ADOPTED_CTX`) instead of 3 scattered `getattr` flag checks. Each branch owns exactly one teardown. Easier to reason about, easier to extend.
|
|
96
|
+
|
|
97
|
+
### Added
|
|
98
|
+
- **`is_loopback_host(url: str) -> bool`** helper in `production/mcp_server.py` — literal/IP/DNS loopback check. Used by the attach loopback gate.
|
|
99
|
+
- **6 new tests in `tests/test_mcp_url_safety.py`** covering loopback literal, `localhost`, bare `host:port` normalization, RFC-1918 rejection, link-local IPv6 rejection.
|
|
100
|
+
- **4 new tests in `tests/test_attach_over_cdp.py`** covering the two-layer gate (RFC-1918, link-local IPv6, with/without `allow_remote=true`).
|
|
101
|
+
- **4 new tests in `tests/test_attach_over_cdp.py`** for `TeardownMode` enum and stealth-failure surface (monkeypatched `add_init_script` rejection).
|
|
102
|
+
|
|
103
|
+
### Changed
|
|
104
|
+
- `production/mcp_server.py`: new `is_loopback_host` helper. `_BLOCKED_NETWORKS` extended with `fe80::/10`. `_tool_stealth_attach_over_cdp` rewritten as a two-layer gate.
|
|
105
|
+
- `core/agent_browser.py`: new `TeardownMode` enum. `close()` branches on the enum. `attach_over_cdp` return dict now includes `stealth_requested` and `stealth_error` fields.
|
|
106
|
+
- `pyproject.toml`: `version` bumped 2.3.0 → 2.4.0.
|
|
107
|
+
|
|
108
|
+
### Test coverage
|
|
109
|
+
- 22/22 pass in `tests/test_attach_over_cdp.py` + `tests/test_mcp_url_safety.py`
|
|
110
|
+
- No new regressions in the unit-test suite (3 pre-existing failures on master — `test_human_behavior_fuzz` MockPage signature mismatch + `test_phase7_fixes` merge conflict — both unrelated to this release)
|
|
111
|
+
|
|
112
|
+
### Closes
|
|
113
|
+
- #438, #439, #440, #441
|
|
114
|
+
|
|
115
|
+
---
|
|
116
|
+
|
|
10
117
|
## [2.3.0] — Show HN & Community Launch (2026-05-28)
|
|
11
118
|
|
|
12
119
|
### Added
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
# Contributor Covenant Code of Conduct
|
|
2
|
+
|
|
3
|
+
## Our Pledge
|
|
4
|
+
|
|
5
|
+
We as members, contributors, and leaders pledge to make participation in our
|
|
6
|
+
community a harassment-free experience for everyone, regardless of age, body
|
|
7
|
+
size, visible or invisible disability, ethnicity, sex characteristics, gender
|
|
8
|
+
identity and expression, level of experience, education, socio-economic status,
|
|
9
|
+
nationality, personal appearance, race, caste, color, religion, or sexual
|
|
10
|
+
identity and orientation.
|
|
11
|
+
|
|
12
|
+
We pledge to act and interact in ways that contribute to an open, welcoming,
|
|
13
|
+
diverse, inclusive, and healthy community.
|
|
14
|
+
|
|
15
|
+
## Our Standards
|
|
16
|
+
|
|
17
|
+
Examples of behavior that contributes to a positive environment for our
|
|
18
|
+
community include:
|
|
19
|
+
|
|
20
|
+
* Demonstrating empathy and kindness toward other people
|
|
21
|
+
* Being respectful of differing opinions, viewpoints, and experiences
|
|
22
|
+
* Giving and gracefully accepting constructive feedback
|
|
23
|
+
* Accepting responsibility and apologizing to those affected by our mistakes,
|
|
24
|
+
and learning from the experience
|
|
25
|
+
* Focusing on what is best not just for us as individuals, but for the overall
|
|
26
|
+
community
|
|
27
|
+
|
|
28
|
+
Examples of unacceptable behavior include:
|
|
29
|
+
|
|
30
|
+
* The use of sexualized language or imagery, and sexual attention or advances of
|
|
31
|
+
any kind
|
|
32
|
+
* Trolling, insulting or derogatory comments, and personal or political attacks
|
|
33
|
+
* Public or private harassment
|
|
34
|
+
* Publishing others' private information, such as a physical or email address,
|
|
35
|
+
without their explicit permission
|
|
36
|
+
* Other conduct which could reasonably be considered inappropriate in a
|
|
37
|
+
professional setting
|
|
38
|
+
|
|
39
|
+
## Enforcement Responsibilities
|
|
40
|
+
|
|
41
|
+
Community leaders are responsible for clarifying and enforcing our standards of
|
|
42
|
+
acceptable behavior and will take appropriate and fair corrective action in
|
|
43
|
+
response to any behavior that they deem inappropriate, threatening, offensive,
|
|
44
|
+
or harmful.
|
|
45
|
+
|
|
46
|
+
Community leaders have the right and responsibility to remove, edit, or reject
|
|
47
|
+
comments, commits, code, wiki edits, issues, and other contributions that are
|
|
48
|
+
not aligned to this Code of Conduct, and will communicate reasons for moderation
|
|
49
|
+
decisions when appropriate.
|
|
50
|
+
|
|
51
|
+
## Scope
|
|
52
|
+
|
|
53
|
+
This Code of Conduct applies within all community spaces, and also applies when
|
|
54
|
+
an individual is officially representing the community in public spaces.
|
|
55
|
+
|
|
56
|
+
## Enforcement
|
|
57
|
+
|
|
58
|
+
Instances of abusive, harassing, or otherwise unacceptable behavior may be
|
|
59
|
+
reported to the community leaders responsible for enforcement at
|
|
60
|
+
[GitHub Issues](https://github.com/shanewas/agentic-stealth-browser/issues).
|
|
61
|
+
All complaints will be reviewed and investigated promptly and fairly.
|
|
62
|
+
|
|
63
|
+
## Attribution
|
|
64
|
+
|
|
65
|
+
This Code of Conduct is adapted from the [Contributor Covenant][homepage],
|
|
66
|
+
version 2.1, available at
|
|
67
|
+
[https://www.contributor-covenant.org/version/2/1/code_of_conduct.html][v2.1].
|
|
68
|
+
|
|
69
|
+
[homepage]: https://www.contributor-covenant.org
|
|
70
|
+
[v2.1]: https://www.contributor-covenant.org/version/2/1/code_of_conduct.html
|
|
@@ -0,0 +1,237 @@
|
|
|
1
|
+
# CONTRIBUTING.md (#55)
|
|
2
|
+
|
|
3
|
+
Thank you for your interest in contributing to the Agentic Stealth Browser! This guide will help you get started.
|
|
4
|
+
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
## Development Setup
|
|
8
|
+
|
|
9
|
+
### 1. Clone the Repository
|
|
10
|
+
|
|
11
|
+
```bash
|
|
12
|
+
git clone https://github.com/shanewas/agentic-stealth-browser.git
|
|
13
|
+
cd agentic-stealth-browser
|
|
14
|
+
```
|
|
15
|
+
|
|
16
|
+
### 2. Create a Virtual Environment
|
|
17
|
+
|
|
18
|
+
```bash
|
|
19
|
+
python3 -m venv .venv
|
|
20
|
+
source .venv/bin/activate
|
|
21
|
+
```
|
|
22
|
+
|
|
23
|
+
### 3. Install Dependencies
|
|
24
|
+
|
|
25
|
+
```bash
|
|
26
|
+
pip install -e ".[dev]"
|
|
27
|
+
playwright install chromium
|
|
28
|
+
```
|
|
29
|
+
|
|
30
|
+
### 4. Run Tests
|
|
31
|
+
|
|
32
|
+
```bash
|
|
33
|
+
# Run all tests
|
|
34
|
+
pytest tests/ -v
|
|
35
|
+
|
|
36
|
+
# Run specific test files
|
|
37
|
+
pytest tests/test_stealth_modules.py -v
|
|
38
|
+
pytest tests/test_contract_agent_browser.py -v
|
|
39
|
+
pytest tests/test_recovery_phase1.py -v
|
|
40
|
+
|
|
41
|
+
# Run with coverage
|
|
42
|
+
pytest tests/ --cov=core --cov=stealth --cov=recovery --cov=behavior
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
---
|
|
46
|
+
|
|
47
|
+
## Code Style
|
|
48
|
+
|
|
49
|
+
### Formatting
|
|
50
|
+
|
|
51
|
+
We use standard Python conventions:
|
|
52
|
+
- 4-space indentation
|
|
53
|
+
- Maximum line length: 120 characters
|
|
54
|
+
- Type hints for all public APIs
|
|
55
|
+
- Docstrings for all public methods
|
|
56
|
+
|
|
57
|
+
### Naming Conventions
|
|
58
|
+
|
|
59
|
+
- Classes: `PascalCase` (e.g., `AgentBrowser`, `StealthConfig`)
|
|
60
|
+
- Functions/Methods: `snake_case` (e.g., `safe_goto`, `warm_up_before_work`)
|
|
61
|
+
- Constants: `UPPER_SNAKE_CASE` (e.g., `DEFAULT_PERSONA`, `MAX_RETRIES`)
|
|
62
|
+
- Private methods: Leading underscore (e.g., `_run_step`, `_check_circuit_breaker`)
|
|
63
|
+
|
|
64
|
+
---
|
|
65
|
+
|
|
66
|
+
## Making Changes
|
|
67
|
+
|
|
68
|
+
### 1. Create a Branch
|
|
69
|
+
|
|
70
|
+
```bash
|
|
71
|
+
git checkout -b feat/your-feature-name
|
|
72
|
+
# or
|
|
73
|
+
git checkout -b fix/issue-description
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
### 2. Make Your Changes
|
|
77
|
+
|
|
78
|
+
- Follow the existing code style
|
|
79
|
+
- Add tests for new functionality
|
|
80
|
+
- Update documentation if needed
|
|
81
|
+
|
|
82
|
+
### 3. Run Tests
|
|
83
|
+
|
|
84
|
+
```bash
|
|
85
|
+
# Ensure all tests pass
|
|
86
|
+
pytest tests/ -v
|
|
87
|
+
|
|
88
|
+
# Check for any import issues
|
|
89
|
+
python -c "from core.agent_browser import AgentBrowser"
|
|
90
|
+
python -c "from stealth.advanced_stealth import get_stealth_script"
|
|
91
|
+
```
|
|
92
|
+
|
|
93
|
+
### 4. Commit Your Changes
|
|
94
|
+
|
|
95
|
+
```bash
|
|
96
|
+
git add .
|
|
97
|
+
git commit -m "feat: description of your change
|
|
98
|
+
|
|
99
|
+
More detailed description if needed.
|
|
100
|
+
|
|
101
|
+
Closes #123"
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
### 5. Push and Create a Pull Request
|
|
105
|
+
|
|
106
|
+
```bash
|
|
107
|
+
git push origin your-branch-name
|
|
108
|
+
```
|
|
109
|
+
|
|
110
|
+
Then open a PR on GitHub.
|
|
111
|
+
|
|
112
|
+
---
|
|
113
|
+
|
|
114
|
+
## Pull Request Guidelines
|
|
115
|
+
|
|
116
|
+
### Title Format
|
|
117
|
+
|
|
118
|
+
- `feat: ` for new features
|
|
119
|
+
- `fix: ` for bug fixes
|
|
120
|
+
- `docs: ` for documentation changes
|
|
121
|
+
- `test: ` for test additions/changes
|
|
122
|
+
- `refactor: ` for code refactoring
|
|
123
|
+
- `perf: ` for performance improvements
|
|
124
|
+
- `security: ` for security fixes
|
|
125
|
+
|
|
126
|
+
### Description
|
|
127
|
+
|
|
128
|
+
Include:
|
|
129
|
+
- What this PR does
|
|
130
|
+
- Why this change is needed
|
|
131
|
+
- Any related issues (e.g., "Closes #123")
|
|
132
|
+
- Testing instructions
|
|
133
|
+
|
|
134
|
+
### Requirements
|
|
135
|
+
|
|
136
|
+
- [ ] All tests pass
|
|
137
|
+
- [ ] New code has tests
|
|
138
|
+
- [ ] Documentation is updated (if applicable)
|
|
139
|
+
- [ ] No sensitive data in code or commits
|
|
140
|
+
|
|
141
|
+
---
|
|
142
|
+
|
|
143
|
+
## Architecture Overview
|
|
144
|
+
|
|
145
|
+
```
|
|
146
|
+
agentic-stealth-browser/
|
|
147
|
+
├── core/
|
|
148
|
+
│ ├── agent_browser.py # Main AgentBrowser class
|
|
149
|
+
│ ├── error_messages.py # User-friendly error messages
|
|
150
|
+
│ └── types.py # Type hints and stubs
|
|
151
|
+
├── stealth/
|
|
152
|
+
│ ├── advanced_stealth.py # Stealth script generation
|
|
153
|
+
│ ├── tls_fingerprint.py # TLS profile management
|
|
154
|
+
│ ├── headers.py # HTTP header spoofing
|
|
155
|
+
│ ├── profiles.py # Persona/DeviceProfile system
|
|
156
|
+
│ └── presets.py # Platform presets
|
|
157
|
+
├── behavior/
|
|
158
|
+
│ ├── human_behavior.py # Human-like behavior simulation
|
|
159
|
+
│ └── orchestration.py # Behavior orchestration
|
|
160
|
+
├── recovery/
|
|
161
|
+
│ ├── anti_block_orchestrator.py # Block detection & recovery
|
|
162
|
+
│ └── explain_blocked.py # Block explanation
|
|
163
|
+
├── proxy/
|
|
164
|
+
│ └── proxy_manager.py # Proxy management & rotation
|
|
165
|
+
├── sessions/
|
|
166
|
+
│ ├── session_manager.py # Session management
|
|
167
|
+
│ └── cookie_manager.py # Cookie management
|
|
168
|
+
├── production/
|
|
169
|
+
│ ├── metrics.py # Metrics collection
|
|
170
|
+
│ ├── rate_limiter.py # Rate limiting
|
|
171
|
+
│ ├── cli.py # CLI entry point
|
|
172
|
+
│ └── agent_orchestrator.py # Multi-agent orchestration
|
|
173
|
+
├── audit/
|
|
174
|
+
│ └── logger.py # Audit logging
|
|
175
|
+
├── scraping/
|
|
176
|
+
│ └── scraper.py # Stealth scraping
|
|
177
|
+
├── ai/
|
|
178
|
+
│ └── ai_hooks.py # AI integration hooks
|
|
179
|
+
├── tests/ # Test suite
|
|
180
|
+
# (documentation lives in README.md and git history)
|
|
181
|
+
└── mcp_security.py # MCP security hardening
|
|
182
|
+
```
|
|
183
|
+
|
|
184
|
+
---
|
|
185
|
+
|
|
186
|
+
## Adding New Features
|
|
187
|
+
|
|
188
|
+
### New Stealth Patches
|
|
189
|
+
|
|
190
|
+
1. Add the patch to `stealth/advanced_stealth.py`
|
|
191
|
+
2. Add tests to `tests/test_stealth_modules.py`
|
|
192
|
+
3. Update relevant sections in README.md if behavior changes
|
|
193
|
+
|
|
194
|
+
### New Platform Preset
|
|
195
|
+
|
|
196
|
+
1. Add the preset to `stealth/presets.py`
|
|
197
|
+
2. Add a recipe to `README.md`
|
|
198
|
+
3. Test against the target site
|
|
199
|
+
|
|
200
|
+
### New Recovery Strategy
|
|
201
|
+
|
|
202
|
+
1. Update `PLATFORM_STRATEGIES` in `recovery/anti_block_orchestrator.py`
|
|
203
|
+
2. Add tests to `tests/test_recovery_phase1.py`
|
|
204
|
+
3. Document rate limiting behavior changes in README.md or relevant code comments
|
|
205
|
+
|
|
206
|
+
### New Human Behavior
|
|
207
|
+
|
|
208
|
+
1. Add the behavior to `behavior/human_behavior.py`
|
|
209
|
+
2. Respect `self.realism_level` for CI/light mode
|
|
210
|
+
3. Add tests
|
|
211
|
+
|
|
212
|
+
---
|
|
213
|
+
|
|
214
|
+
## Reporting Issues
|
|
215
|
+
|
|
216
|
+
When reporting a bug, include:
|
|
217
|
+
- Python version
|
|
218
|
+
- Playwright version
|
|
219
|
+
- Error message and stack trace
|
|
220
|
+
- Code snippet that reproduces the issue
|
|
221
|
+
- Debug report (`await browser.debug_report(print_report=True)`)
|
|
222
|
+
- Health status (`await browser.get_health_status()`)
|
|
223
|
+
|
|
224
|
+
---
|
|
225
|
+
|
|
226
|
+
## Security
|
|
227
|
+
|
|
228
|
+
If you discover a security vulnerability:
|
|
229
|
+
1. **Do not** open a public issue
|
|
230
|
+
2. Email the maintainer directly
|
|
231
|
+
3. Include steps to reproduce and potential impact
|
|
232
|
+
|
|
233
|
+
---
|
|
234
|
+
|
|
235
|
+
## License
|
|
236
|
+
|
|
237
|
+
By contributing, you agree that your contributions will be licensed under the MIT License.
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
include LICENSE
|
|
2
|
+
include README.md
|
|
3
|
+
include CHANGELOG.md
|
|
4
|
+
include CODE_OF_CONDUCT.md
|
|
5
|
+
include CONTRIBUTING.md
|
|
6
|
+
include SECURITY.md
|
|
7
|
+
include .env.example
|
|
8
|
+
|
|
9
|
+
include assets/*.gif assets/*.png assets/*.jpg assets/*.svg
|
|
10
|
+
|
|
11
|
+
recursive-include docs *.md *.html *.svg *.jsonl
|
|
12
|
+
recursive-include stealth *.js *.json
|
|
13
|
+
recursive-include production Dockerfile docker-healthcheck.py
|
|
14
|
+
recursive-include examples *.md *.py *.txt
|
|
15
|
+
recursive-include tests *.py *.json
|
|
16
|
+
recursive-include workflows *.yaml *.yml
|
|
17
|
+
recursive-include plugins *.py
|
|
18
|
+
recursive-include production/sdk *.py
|
|
19
|
+
recursive-include scripts *.sh *.py
|