fleet-python 0.2.0__tar.gz → 0.2.2__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.

Potentially problematic release.


This version of fleet-python might be problematic. Click here for more details.

Files changed (35) hide show
  1. {fleet_python-0.2.0/fleet_python.egg-info → fleet_python-0.2.2}/PKG-INFO +1 -1
  2. fleet_python-0.2.2/examples/dsl_example.py +112 -0
  3. fleet_python-0.2.2/examples/example.py +38 -0
  4. fleet_python-0.2.2/examples/nova_act_example.py +180 -0
  5. fleet_python-0.2.2/examples/openai_example.py +448 -0
  6. {fleet_python-0.2.0 → fleet_python-0.2.2}/examples/quickstart.py +5 -5
  7. {fleet_python-0.2.0 → fleet_python-0.2.2}/fleet/__init__.py +24 -3
  8. {fleet_python-0.2.0 → fleet_python-0.2.2}/fleet/base.py +1 -1
  9. {fleet_python-0.2.0 → fleet_python-0.2.2}/fleet/client.py +60 -28
  10. fleet_python-0.2.2/fleet/env/__init__.py +3 -0
  11. fleet_python-0.2.2/fleet/env/client.py +15 -0
  12. fleet_python-0.2.2/fleet/manager/__init__.py +22 -0
  13. {fleet_python-0.2.0/fleet/env → fleet_python-0.2.2/fleet/manager}/client.py +28 -11
  14. {fleet_python-0.2.0/fleet/env → fleet_python-0.2.2/fleet/manager}/models.py +15 -14
  15. {fleet_python-0.2.0 → fleet_python-0.2.2}/fleet/resources/base.py +5 -2
  16. fleet_python-0.2.2/fleet/resources/browser.py +44 -0
  17. {fleet_python-0.2.0 → fleet_python-0.2.2}/fleet/resources/sqlite.py +5 -5
  18. fleet_python-0.2.2/fleet/verifiers/__init__.py +4 -0
  19. fleet_python-0.2.2/fleet/verifiers/database_snapshot.py +666 -0
  20. fleet_python-0.2.2/fleet/verifiers/sql_differ.py +187 -0
  21. {fleet_python-0.2.0 → fleet_python-0.2.2/fleet_python.egg-info}/PKG-INFO +1 -1
  22. {fleet_python-0.2.0 → fleet_python-0.2.2}/fleet_python.egg-info/SOURCES.txt +11 -3
  23. {fleet_python-0.2.0 → fleet_python-0.2.2}/pyproject.toml +1 -1
  24. fleet_python-0.2.0/examples/browser_control_example.py +0 -51
  25. fleet_python-0.2.0/fleet/env/__init__.py +0 -8
  26. fleet_python-0.2.0/fleet/resources/browser.py +0 -18
  27. {fleet_python-0.2.0 → fleet_python-0.2.2}/LICENSE +0 -0
  28. {fleet_python-0.2.0 → fleet_python-0.2.2}/README.md +0 -0
  29. {fleet_python-0.2.0 → fleet_python-0.2.2}/fleet/exceptions.py +0 -0
  30. {fleet_python-0.2.0/fleet/env → fleet_python-0.2.2/fleet/manager}/base.py +0 -0
  31. {fleet_python-0.2.0 → fleet_python-0.2.2}/fleet/models.py +0 -0
  32. {fleet_python-0.2.0 → fleet_python-0.2.2}/fleet_python.egg-info/dependency_links.txt +0 -0
  33. {fleet_python-0.2.0 → fleet_python-0.2.2}/fleet_python.egg-info/requires.txt +0 -0
  34. {fleet_python-0.2.0 → fleet_python-0.2.2}/fleet_python.egg-info/top_level.txt +0 -0
  35. {fleet_python-0.2.0 → fleet_python-0.2.2}/setup.cfg +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: fleet-python
3
- Version: 0.2.0
3
+ Version: 0.2.2
4
4
  Summary: Python SDK for Fleet environments
5
5
  Author-email: Fleet AI <nic@fleet.so>
6
6
  License: Apache-2.0
@@ -0,0 +1,112 @@
1
+ from fleet.verifiers import DatabaseSnapshot, IgnoreConfig
2
+
3
+ async def validate_give_me_more_tasks(
4
+ before: DatabaseSnapshot,
5
+ after: DatabaseSnapshot,
6
+ transcript: str | None = None,
7
+ ) -> int:
8
+ """Validate that bugs are moved to sprint 3 and assigned correctly."""
9
+
10
+ # Get user IDs
11
+ raj_user = after.table("users").eq("name", "Raj Patel").first()
12
+ sarah_kim_user = after.table("users").eq("name", "Sarah Kim").first()
13
+
14
+ if not raj_user:
15
+ raise AssertionError("User 'Raj Patel' not found")
16
+ if not sarah_kim_user:
17
+ raise AssertionError("User 'Sarah Kim' not found")
18
+
19
+ raj_id = raj_user["id"]
20
+ sarah_kim_id = sarah_kim_user["id"]
21
+
22
+ # Verify SCRUM-555 (data pipeline bug) is assigned to Sarah Kim
23
+ after.table("issues").eq("id", "SCRUM-555").assert_eq("owner", sarah_kim_id)
24
+
25
+ # Verify other bugs are assigned to Raj Patel
26
+ other_bugs = [
27
+ "SCRUM-780",
28
+ "SCRUM-781",
29
+ "SCRUM-790",
30
+ "SCRUM-822",
31
+ "SCRUM-882",
32
+ "SCRUM-897",
33
+ "SCRUM-956",
34
+ "SCRUM-1331",
35
+ "SCRUM-1312",
36
+ "SCRUM-1210",
37
+ "SCRUM-1230",
38
+ "SCRUM-1282",
39
+ ]
40
+ for bug_id in other_bugs:
41
+ after.table("issues").eq("id", bug_id).assert_eq("owner", raj_id)
42
+
43
+ # Verify all bugs are in sprint_3
44
+ all_bugs = ["SCRUM-555"] + other_bugs
45
+ for bug_id in all_bugs:
46
+ after.table("sprint_issues").eq("issue_id", bug_id).assert_eq(
47
+ "sprint_id", "sprint_3"
48
+ )
49
+
50
+ # Configure ignore settings
51
+ ignore_config = IgnoreConfig(
52
+ tables={"activities", "pageviews", "sprint_issues"},
53
+ table_fields={
54
+ "issues": {"updated_at", "created_at", "rowid"},
55
+ "users": {"updated_at", "created_at", "rowid"},
56
+ "sprint_issues": {"updated_at", "created_at", "rowid"},
57
+ },
58
+ )
59
+
60
+ # Build expected changes
61
+ expected_changes: list[dict] = []
62
+
63
+ # Assignment changes
64
+ expected_changes.append(
65
+ {
66
+ "table": "issues",
67
+ "pk": "SCRUM-555",
68
+ "field": "owner",
69
+ "after": sarah_kim_id,
70
+ }
71
+ )
72
+ for bug_id in other_bugs:
73
+ expected_changes.append(
74
+ {
75
+ "table": "issues",
76
+ "pk": bug_id,
77
+ "field": "owner",
78
+ "after": raj_id,
79
+ }
80
+ )
81
+
82
+ # Sprint changes
83
+ for bug_id in all_bugs:
84
+ # Remove from previous sprint if present
85
+ before_assignment = (
86
+ before.table("sprint_issues").eq("issue_id", bug_id).first()
87
+ )
88
+ if before_assignment:
89
+ old_sprint = before_assignment.get("sprint_id")
90
+ expected_changes.append(
91
+ {
92
+ "table": "sprint_issues",
93
+ "pk": (old_sprint, bug_id),
94
+ "field": None,
95
+ "after": "__removed__",
96
+ }
97
+ )
98
+
99
+ # Add to sprint_3
100
+ expected_changes.append(
101
+ {
102
+ "table": "sprint_issues",
103
+ "pk": ("sprint_3", bug_id),
104
+ "field": None,
105
+ "after": "__added__",
106
+ }
107
+ )
108
+
109
+ # Enforce invariant
110
+ before.diff(after, ignore_config).expect_only(expected_changes)
111
+
112
+ return TASK_SUCCESSFUL_SCORE
@@ -0,0 +1,38 @@
1
+ #!/usr/bin/env python3
2
+ """Example demonstrating browser control with Fleet Manager Client."""
3
+
4
+ import asyncio
5
+ import fleet as flt
6
+
7
+
8
+ async def main():
9
+ environments = await flt.env.list_envs()
10
+ print("Environments:", len(environments))
11
+
12
+ # Create a new instance
13
+ env = await flt.env.make("hubspot:v1.2.7")
14
+ print("New Instance:", env.instance_id)
15
+
16
+ response = await env.reset(seed=42)
17
+ print("Reset response:", response)
18
+
19
+ print(await env.resources())
20
+
21
+ sqlite = env.db()
22
+ print("SQLite:", await sqlite.describe())
23
+
24
+ print("Query:", await sqlite.query("SELECT * FROM users"))
25
+
26
+ sqlite = await env.state("sqlite://current").describe()
27
+ print("SQLite:", sqlite)
28
+
29
+ browser = env.browser()
30
+ print("CDP URL:", await browser.cdp_url())
31
+ print("Devtools URL:", await browser.devtools_url())
32
+
33
+ # Delete the instance
34
+ await env.close()
35
+
36
+
37
+ if __name__ == "__main__":
38
+ asyncio.run(main())
@@ -0,0 +1,180 @@
1
+ """
2
+ Nova Act + Fleet SDK Integration Example
3
+
4
+ This example demonstrates how to use Amazon Nova Act (an AI-powered browser automation SDK)
5
+ with Fleet's browser instances. Nova Act can navigate websites, fill forms, and extract data
6
+ using natural language commands.
7
+
8
+ Requirements:
9
+ 1. Fleet SDK: pip install fleet-python
10
+ 2. Nova Act SDK: pip install nova-act
11
+ 3. Playwright Chrome: playwright install chrome
12
+ 4. Environment variables:
13
+ - FLEET_API_KEY: Your Fleet API key
14
+ - NOVA_ACT_API_KEY: Your Nova Act API key (get from https://nova.amazon.com/act)
15
+
16
+ Note: Nova Act is currently only available in the US as a research preview.
17
+
18
+ Usage:
19
+ export FLEET_API_KEY=your_fleet_key
20
+ export NOVA_ACT_API_KEY=your_nova_act_key
21
+ python examples/nova_act_example.py
22
+
23
+ Important: Nova Act typically creates its own browser instance. Integration with
24
+ Fleet's CDP endpoint may not be fully supported in the current version.
25
+ """
26
+
27
+ import asyncio
28
+ import fleet as flt
29
+ import nova_act
30
+ import os
31
+ from concurrent.futures import ThreadPoolExecutor
32
+
33
+
34
+ def test_nova_act_sync():
35
+ """Test Nova Act in a synchronous context (outside asyncio loop)."""
36
+ print("\n🧪 Testing Nova Act independently...")
37
+ try:
38
+ with nova_act.NovaAct(
39
+ headless=False,
40
+ starting_page="https://example.com"
41
+ ) as nova:
42
+ print("✅ Nova Act initialized successfully!")
43
+ result = nova.act("What is the main heading on this page?")
44
+ print(f"Test result: {result}")
45
+ return True
46
+ except Exception as e:
47
+ print(f"❌ Nova Act test failed: {type(e).__name__}: {str(e)}")
48
+ import traceback
49
+ traceback.print_exc()
50
+ return False
51
+
52
+
53
+ def run_nova_act_with_fleet_data(fleet_app_url):
54
+ """Run Nova Act examples using Fleet's app URL."""
55
+ print("\n🤖 Starting Nova Act with Fleet app URL...")
56
+
57
+ try:
58
+ with nova_act.NovaAct(
59
+ headless=False,
60
+ starting_page=fleet_app_url,
61
+ cdp_endpoint_url="wss://05bd8217.fleetai.com/cdp/devtools/browser/288477c8-2a6d-4e66-b8de-29bc3033c7a2"
62
+ ) as nova:
63
+ print("✅ Nova Act started successfully!")
64
+ run_nova_examples(nova)
65
+
66
+ except Exception as e:
67
+ print(f"❌ Error during Nova Act operations: {type(e).__name__}: {str(e)}")
68
+ import traceback
69
+ traceback.print_exc()
70
+
71
+
72
+ def run_nova_examples(nova):
73
+ """Run Nova Act examples in a separate function."""
74
+ # Example 1: Navigate and interact with a website
75
+ print("\n📝 Example 1: Basic navigation and interaction")
76
+ nova.act("Navigate to https://example.com")
77
+
78
+ # Extract page title
79
+ result = nova.act(
80
+ "What is the title of this page?",
81
+ schema={"type": "object", "properties": {"title": {"type": "string"}}},
82
+ )
83
+ if result.matches_schema:
84
+ print(f"Page title: {result.parsed_response.get('title')}")
85
+
86
+ # Example 2: More complex interaction
87
+ print("\n📝 Example 2: Search on a website")
88
+ nova.act("Navigate to https://www.python.org")
89
+ nova.act("Search for 'asyncio' in the search box")
90
+
91
+ # Example 3: Extract structured data
92
+ print("\n📝 Example 3: Extract structured information")
93
+ result = nova.act(
94
+ "Find the first 3 search results and return their titles",
95
+ schema={
96
+ "type": "object",
97
+ "properties": {
98
+ "results": {"type": "array", "items": {"type": "string"}}
99
+ },
100
+ },
101
+ )
102
+ if result.matches_schema:
103
+ results = result.parsed_response.get("results", [])
104
+ print("Search results:")
105
+ for i, title in enumerate(results, 1):
106
+ print(f" {i}. {title}")
107
+
108
+ # Example 4: Fill out a form
109
+ print("\n📝 Example 4: Form interaction")
110
+ nova.act("Navigate to https://httpbin.org/forms/post")
111
+ nova.act("Fill the customer name field with 'John Doe'")
112
+ nova.act("Select 'Medium' for the size")
113
+ nova.act("Check the 'Bacon' topping")
114
+
115
+ # You can also use nova_act's ability to take screenshots
116
+ print("\n📸 Taking screenshot...")
117
+ nova.act("Take a screenshot of the current page")
118
+
119
+
120
+ async def main():
121
+ """Main async function for Fleet operations."""
122
+
123
+ # Check for Nova Act API key
124
+ nova_api_key = os.getenv("NOVA_ACT_API_KEY")
125
+ if not nova_api_key:
126
+ print("❌ NOVA_ACT_API_KEY environment variable not set!")
127
+ print("Please set it with: export NOVA_ACT_API_KEY=your_api_key")
128
+ return
129
+ else:
130
+ print(f"✅ Nova Act API key found: {nova_api_key[:8]}...{nova_api_key[-4:]}")
131
+
132
+ # Test Nova Act outside of asyncio loop
133
+ # with ThreadPoolExecutor() as executor:
134
+ # nova_test_future = executor.submit(test_nova_act_sync)
135
+ # nova_works = nova_test_future.result()
136
+
137
+ # if not nova_works:
138
+ # print("\nNova Act is not working properly. Please check:")
139
+ # print("1. You have a valid NOVA_ACT_API_KEY")
140
+ # print("2. You have installed nova-act: pip install nova-act")
141
+ # print("3. You have playwright installed: playwright install chrome")
142
+ # return
143
+
144
+ # Initialize Fleet client
145
+ fleet = flt.AsyncFleet()
146
+ print("\n🚀 Initializing Fleet client...")
147
+
148
+ instance = await fleet.instance("05bd8217")
149
+
150
+ try:
151
+ # Reset the environment to ensure clean state
152
+ # print("🔄 Resetting environment...")
153
+ # await instance.env.reset()
154
+
155
+ # Get browser resource from Fleet
156
+ browser = await instance.env.browser("cdp").describe()
157
+ print(f"🌐 CDP URL: {browser.url}")
158
+ print(f"🔧 DevTools URL: {browser.devtools_url}")
159
+
160
+ # Run Nova Act in a separate thread to avoid asyncio conflicts
161
+ with ThreadPoolExecutor() as executor:
162
+ nova_future = executor.submit(run_nova_act_with_fleet_data, instance.urls.app)
163
+ nova_future.result() # Wait for Nova Act to complete
164
+
165
+ except Exception as e:
166
+ print(f"❌ Error in main flow: {type(e).__name__}: {str(e)}")
167
+ import traceback
168
+ traceback.print_exc()
169
+
170
+
171
+ if __name__ == "__main__":
172
+ try:
173
+ asyncio.run(main())
174
+ except KeyboardInterrupt:
175
+ print("\n\n⚠️ Script interrupted by user")
176
+ print("Nova Act browser may still be running in the background.")
177
+ except Exception as e:
178
+ print(f"\n❌ Unexpected error: {type(e).__name__}: {str(e)}")
179
+ import traceback
180
+ traceback.print_exc()