agentenv-framework-protocol 0.1.446__tar.gz → 0.1.449__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.
- agentenv_framework_protocol-0.1.446/README.md → agentenv_framework_protocol-0.1.449/PKG-INFO +94 -6
- agentenv_framework_protocol-0.1.446/PKG-INFO → agentenv_framework_protocol-0.1.449/README.md +36 -62
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/pyproject.toml +5 -3
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/agent_env_environment.py +13 -4
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/apps.py +1 -10
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/conformance/checks.py +164 -8
- agentenv_framework_protocol-0.1.449/src/agentenv_protocol/computer/conformance/page_fixture.py +256 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/driver.py +21 -13
- agentenv_framework_protocol-0.1.449/src/agentenv_protocol/computer/seed.py +53 -0
- agentenv_framework_protocol-0.1.449/src/agentenv_protocol/computer/svc.py +182 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/website_browser.py +27 -6
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/probe_fake.py +136 -1
- agentenv_framework_protocol-0.1.449/tests/test_computer_conformance_page.py +98 -0
- agentenv_framework_protocol-0.1.449/tests/test_computer_seed.py +14 -0
- agentenv_framework_protocol-0.1.449/tests/test_computer_svc_forward.py +227 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_website_browser.py +19 -5
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/.gitignore +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/LICENSE +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/NOTICE +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/THIRD_PARTY_NOTICES.md +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/examples/__init__.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/examples/advanced_agent.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/examples/basic_agent.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/examples/custom_extensions_agent.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/examples/multimodal_agent.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/examples/reference_model.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/examples/streaming_agent.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/__init__.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/a2a_agent/__init__.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/a2a_agent/_trajectory_log.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/a2a_agent/_triggers.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/a2a_agent/extensions.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/a2a_agent/framework.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/a2a_agent/peer_agents.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/a2a_agent/proxy.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/a2a_agent/registry.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/a2a_agent/staging.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/a2a_agent/tasks/__init__.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/a2a_agent/tasks/v1.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/client.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/__init__.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/_declare.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/_linux.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/_load.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/_with_fds.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/app.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/app_data.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/app_runtime.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/card.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/checks.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/conformance/__init__.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/conformance/__main__.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/conformance/client.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/conformance/fixture.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/conformance/mp4.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/conformance/report.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/dataplane.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/errors.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/extensions.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/frames.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/keys.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/launch.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/manifest.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/operations.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/platform.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/queue.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/recording.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/results.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/run_install_step.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/runtime.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/serve.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/serve_app.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/session.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/settings.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/skill.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/spaces.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/computer/tools.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/errors.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/manifest.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/preflight.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/tool_access.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/tool_client.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/tool_context.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/transfers.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/src/agentenv_protocol/types.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/computer_fake.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_a2a_agent.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_a2a_agent_examples.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_a2a_cdp_config.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_a2a_object_transfers.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_a2a_peer_agents.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_a2a_proxy.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_a2a_staging.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_a2a_trajectory_log.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_agent_env_environment.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_client.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_app_data.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_app_server.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_conformance.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_conformance_checks.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_conformance_recording.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_dataplane.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_declare.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_driver.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_extensions.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_frames.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_page.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_queue.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_recording.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_serve.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_computer_spaces.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_control_token.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_data_objects.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_errors.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_extension_methods.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_intake.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_manifest.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_preflight.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_tool_access.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_tool_annotations.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_tool_client.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_tool_context.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_tool_context_fastmcp.py +0 -0
- {agentenv_framework_protocol-0.1.446 → agentenv_framework_protocol-0.1.449}/tests/test_tool_context_injection.py +0 -0
agentenv_framework_protocol-0.1.446/README.md → agentenv_framework_protocol-0.1.449/PKG-INFO
RENAMED
|
@@ -1,3 +1,61 @@
|
|
|
1
|
+
Metadata-Version: 2.5
|
|
2
|
+
Name: agentenv-framework-protocol
|
|
3
|
+
Version: 0.1.449
|
|
4
|
+
Summary: Open data-plane protocol and server SDK for agent environments.
|
|
5
|
+
Project-URL: Homepage, https://www.agentenvframework.com
|
|
6
|
+
Project-URL: Documentation, https://www.agentenvframework.com/docs
|
|
7
|
+
Project-URL: Repository, https://github.com/scaleapi/agentenv-framework/tree/main/packages/agentenv-protocol
|
|
8
|
+
Project-URL: Issues, https://github.com/scaleapi/agentenv-framework/issues
|
|
9
|
+
Project-URL: Changelog, https://github.com/scaleapi/agentenv-framework/releases
|
|
10
|
+
Author: Scale AI
|
|
11
|
+
License-Expression: Apache-2.0
|
|
12
|
+
License-File: LICENSE
|
|
13
|
+
License-File: NOTICE
|
|
14
|
+
License-File: THIRD_PARTY_NOTICES.md
|
|
15
|
+
Keywords: a2a,ai-agents,json-rpc,mcp,model-context-protocol,rl-environments
|
|
16
|
+
Classifier: Development Status :: 4 - Beta
|
|
17
|
+
Classifier: Intended Audience :: Developers
|
|
18
|
+
Classifier: Operating System :: OS Independent
|
|
19
|
+
Classifier: Programming Language :: Python :: 3
|
|
20
|
+
Classifier: Programming Language :: Python :: 3 :: Only
|
|
21
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
22
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
23
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
24
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
25
|
+
Classifier: Topic :: Scientific/Engineering :: Artificial Intelligence
|
|
26
|
+
Classifier: Topic :: Software Development :: Libraries :: Python Modules
|
|
27
|
+
Requires-Python: >=3.10
|
|
28
|
+
Requires-Dist: httpx>=0.27
|
|
29
|
+
Requires-Dist: pydantic>=2.11
|
|
30
|
+
Requires-Dist: starlette>=0.37
|
|
31
|
+
Provides-Extra: agent
|
|
32
|
+
Requires-Dist: a2a-sdk[http-server]<0.4,>=0.3.26; extra == 'agent'
|
|
33
|
+
Requires-Dist: mcp<2,>=1.25; extra == 'agent'
|
|
34
|
+
Requires-Dist: python-multipart>=0.0.13; extra == 'agent'
|
|
35
|
+
Requires-Dist: regex>=2023.12.25; extra == 'agent'
|
|
36
|
+
Requires-Dist: uvicorn>=0.30; extra == 'agent'
|
|
37
|
+
Provides-Extra: app
|
|
38
|
+
Requires-Dist: mcp<2,>=1.25; extra == 'app'
|
|
39
|
+
Requires-Dist: uvicorn>=0.30; extra == 'app'
|
|
40
|
+
Provides-Extra: computer
|
|
41
|
+
Requires-Dist: av>=17; extra == 'computer'
|
|
42
|
+
Requires-Dist: mcp<2,>=1.25; extra == 'computer'
|
|
43
|
+
Requires-Dist: pillow>=10.4; extra == 'computer'
|
|
44
|
+
Requires-Dist: uvicorn>=0.30; extra == 'computer'
|
|
45
|
+
Requires-Dist: websockets>=13; extra == 'computer'
|
|
46
|
+
Provides-Extra: dev
|
|
47
|
+
Requires-Dist: a2a-sdk[http-server]<0.4,>=0.3.26; extra == 'dev'
|
|
48
|
+
Requires-Dist: av>=17; extra == 'dev'
|
|
49
|
+
Requires-Dist: fastmcp<4,>=3.4; extra == 'dev'
|
|
50
|
+
Requires-Dist: mcp<2,>=1.25; extra == 'dev'
|
|
51
|
+
Requires-Dist: pillow>=10.4; extra == 'dev'
|
|
52
|
+
Requires-Dist: pytest-asyncio>=0.23.0; extra == 'dev'
|
|
53
|
+
Requires-Dist: pytest>=9.0; extra == 'dev'
|
|
54
|
+
Requires-Dist: python-multipart>=0.0.13; extra == 'dev'
|
|
55
|
+
Requires-Dist: regex>=2023.12.25; extra == 'dev'
|
|
56
|
+
Requires-Dist: websockets>=13; extra == 'dev'
|
|
57
|
+
Description-Content-Type: text/markdown
|
|
58
|
+
|
|
1
59
|
# agentenv-framework-protocol
|
|
2
60
|
|
|
3
61
|
Open data-plane protocol and server SDK for agent environments. Install it with
|
|
@@ -625,17 +683,36 @@ driver booted with a control token is probed with it: `--token`, by default
|
|
|
625
683
|
| Level | Checks | Needs on the computer |
|
|
626
684
|
|---|---|---|
|
|
627
685
|
| `basic` | P0 ready and a screenshot; P1 the card and tool schemas; P2 native frames, regions and JPEG; P5 refusals and their codes; X the declared extensions (`computer-display`, `computer-spaces`, `computer-keyboard`, `computer-exec`, `data/get`, per-role tool access, the pointer) | nothing |
|
|
628
|
-
| `full` | `basic`, then P3 colours land where the mapping says; P4 clicks show their effect; P5 refusals change nothing; P6 typed and pressed keys arrive; P7 scrolls and drags arrive; P9 commands and `data/add` run as one unprivileged user; X pointer and keyboard input, `data/add`, and a recording's segments matching their files with no gap, a repeated `request_id` joining it and `max_concurrent` held | Linux, `python3` with Tk, a 1280x800 screen or larger, `computer-exec` and `data/add` |
|
|
686
|
+
| `full` | `basic`, then P3 colours land where the mapping says; P4 clicks show their effect; P5 refusals change nothing; P6 typed and pressed keys arrive; P7 scrolls and drags arrive; P9 commands and `data/add` run as one unprivileged user; X pointer and keyboard input, `data/add`, and a recording's segments matching their files with no gap, a repeated `request_id` joining it and `max_concurrent` held; on a page, X the page tools: a prompt answered, a file uploaded, a reload, navigation, back and forward, and tabs | Linux, `python3` with Tk (on a page, `python3` and `computer-page/v1`), a 1280x800 screen or larger, `computer-exec` and `data/add` |
|
|
629
687
|
|
|
630
688
|
At `full` the probe writes the Fixture Desk, a Tk window (`conformance/fixture.py`), into
|
|
631
689
|
`~/.agentenv-probe` with `data/add` and starts it with `computer-exec`. It aims at the boxes the
|
|
632
690
|
window's widgets report, reads back what reached them, and then removes the fixture. When the
|
|
633
|
-
fixture can't be staged, the `full` checks are unverified rather than failed.
|
|
691
|
+
fixture can't be staged, the `full` checks are unverified rather than failed.
|
|
692
|
+
|
|
693
|
+
On a driver whose card says `screen: "page"`, the desk is an HTML page with the same widgets at the
|
|
694
|
+
same places (`conformance/page_fixture.py`). The probe starts its server on loopback, which writes
|
|
695
|
+
what the page reports to the same files, and opens the desk with `computer_tabs` in a tab of its
|
|
696
|
+
own. "Typing leaves the clipboard as it was" fails there when typing arrives as a paste. After the
|
|
697
|
+
input checks it checks the page tools against the desk; a browser that answers dialogs itself makes
|
|
698
|
+
the dialog check not applicable. It then closes its tab and removes the desk, and the file it put in
|
|
699
|
+
`~/Uploads`. The tab that was open before keeps its page and history. The probe leaves out
|
|
634
700
|
the checks for an extension the card doesn't declare. P8 is not applicable to a driver without
|
|
635
701
|
leasing, and unverified for one with it until the probe has lease checks. The probe calls as the
|
|
636
702
|
default role; the tool-access check hides a tool from a role of its own, `agentenv-probe-<random>`,
|
|
637
703
|
and gives it back.
|
|
638
704
|
|
|
705
|
+
### A disk's boot seed
|
|
706
|
+
|
|
707
|
+
A Linux computer's disk form gets the deploy's environment at boot from a NoCloud seed, a FAT filesystem labelled
|
|
708
|
+
`CIDATA` that the launcher writes and the disk's init reads. `agentenv_protocol.computer.seed` defines it. A disk
|
|
709
|
+
composed by one agent-env version boots under another's launcher, so the seed carries every version its launcher
|
|
710
|
+
writes: version 1 in `user-data`, a later version N in `user-data.vN`, and the oldest it carries in
|
|
711
|
+
`agentenv-seed-oldest`. An init reads the newest version it knows, and stops the boot when the seed carries none of
|
|
712
|
+
them. Version 1 is `#agentenv-environment`, then `NAME=<value, base64'd>` a line, in byte order; `SAMPLE` and
|
|
713
|
+
`SAMPLE_USER_DATA` pin it, for a launcher's writer and an init's reader, wherever either is written, to be tested
|
|
714
|
+
against. A change an older init would misread is a new version; one it ignores, such as a new file on the seed, isn't.
|
|
715
|
+
|
|
639
716
|
## Computer apps
|
|
640
717
|
|
|
641
718
|
A computer app is software an agent uses on a computer, beside the driver: a desktop app, a service
|
|
@@ -751,7 +828,16 @@ launches one at a time, runs a load and a reset with the app stopped and relaunc
|
|
|
751
828
|
follows a failed load with a reset, and fails a call that runs past `data_timeout_s` (300 s); a sync
|
|
752
829
|
hook runs in a thread, which the reset and relaunch after it wait for. The driver fronts its apps:
|
|
753
830
|
its card lists each one's card as a child environment, rooted at `/svc/<app>/`, where it forwards
|
|
754
|
-
requests to the app's server
|
|
831
|
+
requests to the app's server, taking the control token:
|
|
832
|
+
|
|
833
|
+
- every method, its body and the answer's streamed both ways, so a large answer isn't held whole;
|
|
834
|
+
- headers passed on but the hop-by-hop ones, those a `Connection` header names and the control token's
|
|
835
|
+
`Authorization`; `Host` as the caller sent it, and in place of any address the caller forwarded,
|
|
836
|
+
the one it reached the driver at: `X-Forwarded-Host`, `X-Forwarded-Proto` and `X-Forwarded-Prefix`
|
|
837
|
+
(`/svc/<app>`), as the gateway sets them;
|
|
838
|
+
- WebSockets, relayed to the app's server both ways with the subprotocol it picks until either side
|
|
839
|
+
closes, the other then closed with its code; refused before they open without the token, or with no
|
|
840
|
+
such app or one not answering. The `computer` extra brings `websockets` for this.
|
|
755
841
|
|
|
756
842
|
`MailApp.declaration()` returns what the class declares, an `AppDeclaration`, which a `computer_app`
|
|
757
843
|
env stores (`browser: true` for a website browser), and `python -m agentenv_protocol.computer._declare <folder> <file> <class>` prints it as
|
|
@@ -804,7 +890,8 @@ are the profile's template. The base class adds:
|
|
|
804
890
|
- **Its control connection**, `self.control`, a `BrowserControl` over the pipe. At each launch it attaches
|
|
805
891
|
to every page with flattened sessions, telling each page it attached to as it opened, a popup say, to run, and keeps a
|
|
806
892
|
record, `since` its server started: open tabs in opened order, each with its URL and title as the browser has them
|
|
807
|
-
when the record is read (Chrome sends no event for a title), the one whose page has focus `active`;
|
|
893
|
+
when the record is read (Chrome sends no event for a title), the visible one whose page has focus `active`;
|
|
894
|
+
`closed_tabs`,
|
|
808
895
|
each as of its page's last load, with `closed_at` and
|
|
809
896
|
`closed_by` (`agentenv`, over this connection; `unknown`, anyone else; `exit` or `stop`, when the browser
|
|
810
897
|
ended on its own or its server stopped it); `downloads`, into `~/Downloads`, each with its state
|
|
@@ -824,8 +911,9 @@ are the profile's template. The base class adds:
|
|
|
824
911
|
drivers and agentenv's own steps alike:
|
|
825
912
|
- `navigate {url}` and `history {direction}` (`back`, `forward` or `reload`), in the active tab;
|
|
826
913
|
- `tabs/list`, `tabs/open {url?}`, `tabs/activate {tab}` and `tabs/close {tab}`, by the browser's own tab
|
|
827
|
-
ids. The active tab is the one a dialog is open on, else the one whose page has focus
|
|
828
|
-
agentenv last brought to the front
|
|
914
|
+
ids. The active tab is the one a dialog is open on, else the visible one whose page has focus (a hidden
|
|
915
|
+
tab's page that had input still says it has focus), else the one agentenv last brought to the front.
|
|
916
|
+
Headless, a tab opened at a URL opens blank and goes there once it's held to the window's size;
|
|
829
917
|
- `dialog/answer {accept, text?}`, the agent's answer to the dialog open on the active tab;
|
|
830
918
|
- `files/choose {paths}`, files in `~/Uploads` for the file chooser open on it, which headless, and so
|
|
831
919
|
alone, it intercepts;
|
agentenv_framework_protocol-0.1.446/PKG-INFO → agentenv_framework_protocol-0.1.449/README.md
RENAMED
|
@@ -1,59 +1,3 @@
|
|
|
1
|
-
Metadata-Version: 2.5
|
|
2
|
-
Name: agentenv-framework-protocol
|
|
3
|
-
Version: 0.1.446
|
|
4
|
-
Summary: Open data-plane protocol and server SDK for agent environments.
|
|
5
|
-
Project-URL: Homepage, https://www.agentenvframework.com
|
|
6
|
-
Project-URL: Documentation, https://www.agentenvframework.com/docs
|
|
7
|
-
Project-URL: Repository, https://github.com/scaleapi/agentenv-framework/tree/main/packages/agentenv-protocol
|
|
8
|
-
Project-URL: Issues, https://github.com/scaleapi/agentenv-framework/issues
|
|
9
|
-
Project-URL: Changelog, https://github.com/scaleapi/agentenv-framework/releases
|
|
10
|
-
Author: Scale AI
|
|
11
|
-
License-Expression: Apache-2.0
|
|
12
|
-
License-File: LICENSE
|
|
13
|
-
License-File: NOTICE
|
|
14
|
-
License-File: THIRD_PARTY_NOTICES.md
|
|
15
|
-
Keywords: a2a,ai-agents,json-rpc,mcp,model-context-protocol,rl-environments
|
|
16
|
-
Classifier: Development Status :: 4 - Beta
|
|
17
|
-
Classifier: Intended Audience :: Developers
|
|
18
|
-
Classifier: Operating System :: OS Independent
|
|
19
|
-
Classifier: Programming Language :: Python :: 3
|
|
20
|
-
Classifier: Programming Language :: Python :: 3 :: Only
|
|
21
|
-
Classifier: Programming Language :: Python :: 3.10
|
|
22
|
-
Classifier: Programming Language :: Python :: 3.11
|
|
23
|
-
Classifier: Programming Language :: Python :: 3.12
|
|
24
|
-
Classifier: Programming Language :: Python :: 3.13
|
|
25
|
-
Classifier: Topic :: Scientific/Engineering :: Artificial Intelligence
|
|
26
|
-
Classifier: Topic :: Software Development :: Libraries :: Python Modules
|
|
27
|
-
Requires-Python: >=3.10
|
|
28
|
-
Requires-Dist: httpx>=0.27
|
|
29
|
-
Requires-Dist: pydantic>=2.11
|
|
30
|
-
Requires-Dist: starlette>=0.37
|
|
31
|
-
Provides-Extra: agent
|
|
32
|
-
Requires-Dist: a2a-sdk[http-server]<0.4,>=0.3.26; extra == 'agent'
|
|
33
|
-
Requires-Dist: mcp<2,>=1.25; extra == 'agent'
|
|
34
|
-
Requires-Dist: python-multipart>=0.0.13; extra == 'agent'
|
|
35
|
-
Requires-Dist: regex>=2023.12.25; extra == 'agent'
|
|
36
|
-
Requires-Dist: uvicorn>=0.30; extra == 'agent'
|
|
37
|
-
Provides-Extra: app
|
|
38
|
-
Requires-Dist: mcp<2,>=1.25; extra == 'app'
|
|
39
|
-
Requires-Dist: uvicorn>=0.30; extra == 'app'
|
|
40
|
-
Provides-Extra: computer
|
|
41
|
-
Requires-Dist: av>=17; extra == 'computer'
|
|
42
|
-
Requires-Dist: mcp<2,>=1.25; extra == 'computer'
|
|
43
|
-
Requires-Dist: pillow>=10.4; extra == 'computer'
|
|
44
|
-
Requires-Dist: uvicorn>=0.30; extra == 'computer'
|
|
45
|
-
Provides-Extra: dev
|
|
46
|
-
Requires-Dist: a2a-sdk[http-server]<0.4,>=0.3.26; extra == 'dev'
|
|
47
|
-
Requires-Dist: av>=17; extra == 'dev'
|
|
48
|
-
Requires-Dist: fastmcp<4,>=3.4; extra == 'dev'
|
|
49
|
-
Requires-Dist: mcp<2,>=1.25; extra == 'dev'
|
|
50
|
-
Requires-Dist: pillow>=10.4; extra == 'dev'
|
|
51
|
-
Requires-Dist: pytest-asyncio>=0.23.0; extra == 'dev'
|
|
52
|
-
Requires-Dist: pytest>=9.0; extra == 'dev'
|
|
53
|
-
Requires-Dist: python-multipart>=0.0.13; extra == 'dev'
|
|
54
|
-
Requires-Dist: regex>=2023.12.25; extra == 'dev'
|
|
55
|
-
Description-Content-Type: text/markdown
|
|
56
|
-
|
|
57
1
|
# agentenv-framework-protocol
|
|
58
2
|
|
|
59
3
|
Open data-plane protocol and server SDK for agent environments. Install it with
|
|
@@ -681,17 +625,36 @@ driver booted with a control token is probed with it: `--token`, by default
|
|
|
681
625
|
| Level | Checks | Needs on the computer |
|
|
682
626
|
|---|---|---|
|
|
683
627
|
| `basic` | P0 ready and a screenshot; P1 the card and tool schemas; P2 native frames, regions and JPEG; P5 refusals and their codes; X the declared extensions (`computer-display`, `computer-spaces`, `computer-keyboard`, `computer-exec`, `data/get`, per-role tool access, the pointer) | nothing |
|
|
684
|
-
| `full` | `basic`, then P3 colours land where the mapping says; P4 clicks show their effect; P5 refusals change nothing; P6 typed and pressed keys arrive; P7 scrolls and drags arrive; P9 commands and `data/add` run as one unprivileged user; X pointer and keyboard input, `data/add`, and a recording's segments matching their files with no gap, a repeated `request_id` joining it and `max_concurrent` held | Linux, `python3` with Tk, a 1280x800 screen or larger, `computer-exec` and `data/add` |
|
|
628
|
+
| `full` | `basic`, then P3 colours land where the mapping says; P4 clicks show their effect; P5 refusals change nothing; P6 typed and pressed keys arrive; P7 scrolls and drags arrive; P9 commands and `data/add` run as one unprivileged user; X pointer and keyboard input, `data/add`, and a recording's segments matching their files with no gap, a repeated `request_id` joining it and `max_concurrent` held; on a page, X the page tools: a prompt answered, a file uploaded, a reload, navigation, back and forward, and tabs | Linux, `python3` with Tk (on a page, `python3` and `computer-page/v1`), a 1280x800 screen or larger, `computer-exec` and `data/add` |
|
|
685
629
|
|
|
686
630
|
At `full` the probe writes the Fixture Desk, a Tk window (`conformance/fixture.py`), into
|
|
687
631
|
`~/.agentenv-probe` with `data/add` and starts it with `computer-exec`. It aims at the boxes the
|
|
688
632
|
window's widgets report, reads back what reached them, and then removes the fixture. When the
|
|
689
|
-
fixture can't be staged, the `full` checks are unverified rather than failed.
|
|
633
|
+
fixture can't be staged, the `full` checks are unverified rather than failed.
|
|
634
|
+
|
|
635
|
+
On a driver whose card says `screen: "page"`, the desk is an HTML page with the same widgets at the
|
|
636
|
+
same places (`conformance/page_fixture.py`). The probe starts its server on loopback, which writes
|
|
637
|
+
what the page reports to the same files, and opens the desk with `computer_tabs` in a tab of its
|
|
638
|
+
own. "Typing leaves the clipboard as it was" fails there when typing arrives as a paste. After the
|
|
639
|
+
input checks it checks the page tools against the desk; a browser that answers dialogs itself makes
|
|
640
|
+
the dialog check not applicable. It then closes its tab and removes the desk, and the file it put in
|
|
641
|
+
`~/Uploads`. The tab that was open before keeps its page and history. The probe leaves out
|
|
690
642
|
the checks for an extension the card doesn't declare. P8 is not applicable to a driver without
|
|
691
643
|
leasing, and unverified for one with it until the probe has lease checks. The probe calls as the
|
|
692
644
|
default role; the tool-access check hides a tool from a role of its own, `agentenv-probe-<random>`,
|
|
693
645
|
and gives it back.
|
|
694
646
|
|
|
647
|
+
### A disk's boot seed
|
|
648
|
+
|
|
649
|
+
A Linux computer's disk form gets the deploy's environment at boot from a NoCloud seed, a FAT filesystem labelled
|
|
650
|
+
`CIDATA` that the launcher writes and the disk's init reads. `agentenv_protocol.computer.seed` defines it. A disk
|
|
651
|
+
composed by one agent-env version boots under another's launcher, so the seed carries every version its launcher
|
|
652
|
+
writes: version 1 in `user-data`, a later version N in `user-data.vN`, and the oldest it carries in
|
|
653
|
+
`agentenv-seed-oldest`. An init reads the newest version it knows, and stops the boot when the seed carries none of
|
|
654
|
+
them. Version 1 is `#agentenv-environment`, then `NAME=<value, base64'd>` a line, in byte order; `SAMPLE` and
|
|
655
|
+
`SAMPLE_USER_DATA` pin it, for a launcher's writer and an init's reader, wherever either is written, to be tested
|
|
656
|
+
against. A change an older init would misread is a new version; one it ignores, such as a new file on the seed, isn't.
|
|
657
|
+
|
|
695
658
|
## Computer apps
|
|
696
659
|
|
|
697
660
|
A computer app is software an agent uses on a computer, beside the driver: a desktop app, a service
|
|
@@ -807,7 +770,16 @@ launches one at a time, runs a load and a reset with the app stopped and relaunc
|
|
|
807
770
|
follows a failed load with a reset, and fails a call that runs past `data_timeout_s` (300 s); a sync
|
|
808
771
|
hook runs in a thread, which the reset and relaunch after it wait for. The driver fronts its apps:
|
|
809
772
|
its card lists each one's card as a child environment, rooted at `/svc/<app>/`, where it forwards
|
|
810
|
-
requests to the app's server
|
|
773
|
+
requests to the app's server, taking the control token:
|
|
774
|
+
|
|
775
|
+
- every method, its body and the answer's streamed both ways, so a large answer isn't held whole;
|
|
776
|
+
- headers passed on but the hop-by-hop ones, those a `Connection` header names and the control token's
|
|
777
|
+
`Authorization`; `Host` as the caller sent it, and in place of any address the caller forwarded,
|
|
778
|
+
the one it reached the driver at: `X-Forwarded-Host`, `X-Forwarded-Proto` and `X-Forwarded-Prefix`
|
|
779
|
+
(`/svc/<app>`), as the gateway sets them;
|
|
780
|
+
- WebSockets, relayed to the app's server both ways with the subprotocol it picks until either side
|
|
781
|
+
closes, the other then closed with its code; refused before they open without the token, or with no
|
|
782
|
+
such app or one not answering. The `computer` extra brings `websockets` for this.
|
|
811
783
|
|
|
812
784
|
`MailApp.declaration()` returns what the class declares, an `AppDeclaration`, which a `computer_app`
|
|
813
785
|
env stores (`browser: true` for a website browser), and `python -m agentenv_protocol.computer._declare <folder> <file> <class>` prints it as
|
|
@@ -860,7 +832,8 @@ are the profile's template. The base class adds:
|
|
|
860
832
|
- **Its control connection**, `self.control`, a `BrowserControl` over the pipe. At each launch it attaches
|
|
861
833
|
to every page with flattened sessions, telling each page it attached to as it opened, a popup say, to run, and keeps a
|
|
862
834
|
record, `since` its server started: open tabs in opened order, each with its URL and title as the browser has them
|
|
863
|
-
when the record is read (Chrome sends no event for a title), the one whose page has focus `active`;
|
|
835
|
+
when the record is read (Chrome sends no event for a title), the visible one whose page has focus `active`;
|
|
836
|
+
`closed_tabs`,
|
|
864
837
|
each as of its page's last load, with `closed_at` and
|
|
865
838
|
`closed_by` (`agentenv`, over this connection; `unknown`, anyone else; `exit` or `stop`, when the browser
|
|
866
839
|
ended on its own or its server stopped it); `downloads`, into `~/Downloads`, each with its state
|
|
@@ -880,8 +853,9 @@ are the profile's template. The base class adds:
|
|
|
880
853
|
drivers and agentenv's own steps alike:
|
|
881
854
|
- `navigate {url}` and `history {direction}` (`back`, `forward` or `reload`), in the active tab;
|
|
882
855
|
- `tabs/list`, `tabs/open {url?}`, `tabs/activate {tab}` and `tabs/close {tab}`, by the browser's own tab
|
|
883
|
-
ids. The active tab is the one a dialog is open on, else the one whose page has focus
|
|
884
|
-
agentenv last brought to the front
|
|
856
|
+
ids. The active tab is the one a dialog is open on, else the visible one whose page has focus (a hidden
|
|
857
|
+
tab's page that had input still says it has focus), else the one agentenv last brought to the front.
|
|
858
|
+
Headless, a tab opened at a URL opens blank and goes there once it's held to the window's size;
|
|
885
859
|
- `dialog/answer {accept, text?}`, the agent's answer to the dialog open on the active tab;
|
|
886
860
|
- `files/choose {paths}`, files in `~/Uploads` for the file chooser open on it, which headless, and so
|
|
887
861
|
alone, it intercepts;
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
[project]
|
|
2
2
|
name = "agentenv-framework-protocol"
|
|
3
|
-
version = "0.1.
|
|
3
|
+
version = "0.1.449"
|
|
4
4
|
description = "Open data-plane protocol and server SDK for agent environments."
|
|
5
5
|
readme = "README.md"
|
|
6
6
|
license = "Apache-2.0"
|
|
@@ -41,13 +41,14 @@ app = [
|
|
|
41
41
|
"mcp>=1.25,<2",
|
|
42
42
|
"uvicorn>=0.30",
|
|
43
43
|
]
|
|
44
|
-
# A computer driver: ComputerDriverEnvironment serves its tools over mcp's FastMCP, crops and encodes frames,
|
|
45
|
-
#
|
|
44
|
+
# A computer driver: ComputerDriverEnvironment serves its tools over mcp's FastMCP, crops and encodes frames, records
|
|
45
|
+
# the display as H.264 with PyAV (computer-recording/v1), and relays WebSockets to its apps on /svc/<app>/.
|
|
46
46
|
computer = [
|
|
47
47
|
"av>=17",
|
|
48
48
|
"mcp>=1.25,<2",
|
|
49
49
|
"Pillow>=10.4",
|
|
50
50
|
"uvicorn>=0.30",
|
|
51
|
+
"websockets>=13",
|
|
51
52
|
]
|
|
52
53
|
dev = [
|
|
53
54
|
"a2a-sdk[http-server]>=0.3.26,<0.4",
|
|
@@ -59,6 +60,7 @@ dev = [
|
|
|
59
60
|
"fastmcp>=3.4,<4", # the standalone-fastmcp mount path
|
|
60
61
|
"Pillow>=10.4", # the computer extra's frame crops and encodings
|
|
61
62
|
"av>=17", # the computer extra's encoder, and the tests' decoder
|
|
63
|
+
"websockets>=13", # the computer extra's /svc/<app>/ relay
|
|
62
64
|
]
|
|
63
65
|
[project.urls]
|
|
64
66
|
Homepage = "https://www.agentenvframework.com"
|
|
@@ -1546,18 +1546,27 @@ def _error_response(error: AgentEnvError) -> Response:
|
|
|
1546
1546
|
return _json_response(error_body(**error.fields()), error.status)
|
|
1547
1547
|
|
|
1548
1548
|
|
|
1549
|
+
def control_check() -> Callable[[Any], bool]:
|
|
1550
|
+
"""Whether a call's headers carry the env's control token as their bearer, with ``CONTROL_TOKEN_ENV`` set; without
|
|
1551
|
+
it, any do."""
|
|
1552
|
+
token = os.environ.get(CONTROL_TOKEN_ENV)
|
|
1553
|
+
if not token:
|
|
1554
|
+
return lambda headers: True
|
|
1555
|
+
expected = f"Bearer {token}".encode()
|
|
1556
|
+
return lambda headers: hmac.compare_digest(headers.get("authorization", "").encode(), expected)
|
|
1557
|
+
|
|
1558
|
+
|
|
1549
1559
|
def control_guard() -> Callable[[Callable], Callable]:
|
|
1550
1560
|
"""What wraps a framework-only route, everything an env serves but its MCP endpoint and its card: with
|
|
1551
1561
|
``CONTROL_TOKEN_ENV`` set, a call that doesn't carry that token as its bearer is refused before the route runs;
|
|
1552
1562
|
without it, nothing."""
|
|
1553
|
-
|
|
1554
|
-
if not token:
|
|
1563
|
+
if not os.environ.get(CONTROL_TOKEN_ENV):
|
|
1555
1564
|
return lambda handler: handler
|
|
1556
|
-
|
|
1565
|
+
allowed = control_check()
|
|
1557
1566
|
|
|
1558
1567
|
def guard(handler: Callable) -> Callable:
|
|
1559
1568
|
async def guarded(request: Request) -> Response:
|
|
1560
|
-
if not
|
|
1569
|
+
if not allowed(request.headers):
|
|
1561
1570
|
return _error_response(AgentEnvError(
|
|
1562
1571
|
"unauthorized", "this route is agent-env's own: it takes the env's control token", status=401))
|
|
1563
1572
|
return await handler(request)
|
|
@@ -3,7 +3,7 @@ Each app's own server answers on its folder's socket (``serve_app``): its card s
|
|
|
3
3
|
paths it owns, and its ``computer-app/v1`` ``ready`` whether it's ready. Every app's server must answer before the
|
|
4
4
|
computer is ready; an app that starts with the computer must also be ready, and a ``demand`` app is checked once
|
|
5
5
|
something launches it. The driver lists each app as a child environment named for its folder, its card's paths under
|
|
6
|
-
``/svc/<name>/``,
|
|
6
|
+
``/svc/<name>/``, where it forwards each request to the app's server (``svc``)."""
|
|
7
7
|
from __future__ import annotations
|
|
8
8
|
|
|
9
9
|
import asyncio
|
|
@@ -91,15 +91,6 @@ async def owned_paths(folders: list[Path]) -> list[str]:
|
|
|
91
91
|
for path in client.extension_params(card, COMPUTER_APP).get("paths") or []]
|
|
92
92
|
|
|
93
93
|
|
|
94
|
-
async def forward(folder: Path, method: str, path: str, query: str, body: bytes,
|
|
95
|
-
content_type: Optional[str]) -> httpx.Response:
|
|
96
|
-
"""The app's server's answer to the request, sent on as it came; it takes as long as the app does."""
|
|
97
|
-
async with httpx.AsyncClient(transport=httpx.AsyncHTTPTransport(uds=str(folder / SOCKET)), base_url="http://app",
|
|
98
|
-
timeout=None) as http:
|
|
99
|
-
return await http.request(method, f"/{path}" + (f"?{query}" if query else ""), content=body,
|
|
100
|
-
headers={"content-type": content_type} if content_type else None)
|
|
101
|
-
|
|
102
|
-
|
|
103
94
|
def endpoint(card: dict, method: str) -> str:
|
|
104
95
|
"""The path of a ``computer-app/v1`` method, as the app's card advertises it."""
|
|
105
96
|
return client.find_extension_method(card, COMPUTER_APP, method)["endpoint"]
|