weavz-io-sdk 0.1.1__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.
@@ -0,0 +1,135 @@
1
+ name: Release Python SDK
2
+
3
+ on:
4
+ workflow_dispatch:
5
+ inputs:
6
+ dry_run:
7
+ description: Build and validate without publishing
8
+ required: true
9
+ default: true
10
+ type: boolean
11
+ confirm_release:
12
+ description: Type release-sdk to publish
13
+ required: false
14
+ type: string
15
+
16
+ permissions:
17
+ contents: write
18
+
19
+ env:
20
+ FORCE_JAVASCRIPT_ACTIONS_TO_NODE24: true
21
+
22
+ concurrency:
23
+ group: python-sdk-release-${{ github.ref_name }}
24
+ cancel-in-progress: false
25
+
26
+ jobs:
27
+ release:
28
+ name: Release weavz-io-sdk
29
+ runs-on: ubuntu-latest
30
+ timeout-minutes: 30
31
+ environment: pypi-release
32
+ steps:
33
+ - uses: actions/checkout@v6
34
+ with:
35
+ fetch-depth: 0
36
+
37
+ - uses: actions/setup-python@v6
38
+ with:
39
+ python-version: '3.13'
40
+
41
+ - name: Validate release request
42
+ run: |
43
+ if [ "$GITHUB_REF_NAME" != "main" ]; then
44
+ echo "SDK releases must run from main. Current ref: ${GITHUB_REF_NAME}"
45
+ exit 1
46
+ fi
47
+
48
+ if [ "$DRY_RUN" = "false" ] && [ "$CONFIRM_RELEASE" != "release-sdk" ]; then
49
+ echo "Real SDK release requires confirm_release=release-sdk"
50
+ exit 1
51
+ fi
52
+ env:
53
+ CONFIRM_RELEASE: ${{ inputs.confirm_release }}
54
+ DRY_RUN: ${{ inputs.dry_run }}
55
+
56
+ - name: Install dependencies
57
+ run: |
58
+ python -m pip install --upgrade pip
59
+ python -m pip install build pytest twine
60
+ python -m pip install -e .
61
+
62
+ - name: Run package checks
63
+ run: |
64
+ python -m pytest tests/test_generated_integrations.py
65
+ python -m build
66
+ python -m twine check dist/*
67
+
68
+ - name: Check package version
69
+ id: package
70
+ run: |
71
+ version="$(python - <<'PY'
72
+ import tomllib
73
+ with open("pyproject.toml", "rb") as f:
74
+ print(tomllib.load(f)["project"]["version"])
75
+ PY
76
+ )"
77
+ echo "version=${version}" >> "$GITHUB_OUTPUT"
78
+
79
+ VERSION="$version" python - <<'PY'
80
+ import os
81
+ import sys
82
+ import urllib.error
83
+ import urllib.request
84
+
85
+ version = os.environ["VERSION"]
86
+ url = f"https://pypi.org/pypi/weavz-io-sdk/{version}/json"
87
+ try:
88
+ urllib.request.urlopen(url, timeout=10).close()
89
+ except urllib.error.HTTPError as exc:
90
+ if exc.code == 404:
91
+ sys.exit(0)
92
+ raise
93
+
94
+ print(f"weavz-io-sdk {version} is already published")
95
+ sys.exit(1)
96
+ PY
97
+
98
+ - name: Publish to PyPI
99
+ if: inputs.dry_run == false
100
+ run: |
101
+ if [ -z "$TWINE_PASSWORD" ]; then
102
+ echo "PYPI_API_TOKEN is required for PyPI publishing"
103
+ exit 1
104
+ fi
105
+
106
+ python -m twine upload dist/*
107
+ env:
108
+ TWINE_USERNAME: __token__
109
+ TWINE_PASSWORD: ${{ secrets.PYPI_API_TOKEN }}
110
+
111
+ - name: Tag release
112
+ if: inputs.dry_run == false
113
+ run: |
114
+ tag="v${VERSION}"
115
+ if git rev-parse "$tag" >/dev/null 2>&1; then
116
+ echo "Git tag ${tag} already exists"
117
+ exit 1
118
+ fi
119
+
120
+ git config user.name "github-actions[bot]"
121
+ git config user.email "41898282+github-actions[bot]@users.noreply.github.com"
122
+ git tag "$tag"
123
+ git push origin "$tag"
124
+ env:
125
+ VERSION: ${{ steps.package.outputs.version }}
126
+
127
+ - name: Create GitHub release
128
+ if: inputs.dry_run == false
129
+ run: |
130
+ gh release create "v${VERSION}" \
131
+ --title "weavz-io-sdk v${VERSION}" \
132
+ --notes "Published weavz-io-sdk ${VERSION} to PyPI."
133
+ env:
134
+ GH_TOKEN: ${{ github.token }}
135
+ VERSION: ${{ steps.package.outputs.version }}
@@ -0,0 +1,9 @@
1
+ __pycache__/
2
+ *.py[cod]
3
+ *.egg-info/
4
+ dist/
5
+ build/
6
+ .eggs/
7
+ *.egg
8
+ .venv/
9
+ generated/
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Weavz
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,480 @@
1
+ Metadata-Version: 2.4
2
+ Name: weavz-io-sdk
3
+ Version: 0.1.1
4
+ Summary: Python SDK for Weavz stateful agent runtime APIs
5
+ Project-URL: Homepage, https://weavz.io
6
+ Project-URL: Repository, https://github.com/weavz/weavz-python-sdk
7
+ Project-URL: Documentation, https://weavz.io/docs/sdks/python
8
+ Project-URL: Issues, https://github.com/weavz/weavz-python-sdk/issues
9
+ Author-email: Weavz <support@weavz.io>
10
+ License-Expression: MIT
11
+ License-File: LICENSE
12
+ Keywords: agent-runtime,agents,api,filesystem,integrations,mcp,sandbox,sdk,stateful-agents,weavz
13
+ Classifier: Development Status :: 3 - Alpha
14
+ Classifier: Intended Audience :: Developers
15
+ Classifier: License :: OSI Approved :: MIT License
16
+ Classifier: Programming Language :: Python :: 3
17
+ Classifier: Programming Language :: Python :: 3.10
18
+ Classifier: Programming Language :: Python :: 3.11
19
+ Classifier: Programming Language :: Python :: 3.12
20
+ Classifier: Programming Language :: Python :: 3.13
21
+ Classifier: Typing :: Typed
22
+ Requires-Python: >=3.10
23
+ Requires-Dist: httpx>=0.25.0
24
+ Requires-Dist: pydantic>=2.0.0
25
+ Description-Content-Type: text/markdown
26
+
27
+ # Weavz Python SDK
28
+
29
+ Official Python SDK for [Weavz](https://weavz.io), the stateful agent runtime for SaaS and AI products.
30
+
31
+ Weavz gives your product one API for connection management, end-user identity, hosted connect flows, action execution, triggers, MCP servers, Human Gates, input partials, Filesystem, State KV, Sandbox execution, and 500+ integrations.
32
+
33
+ ## Links
34
+
35
+ - [Weavz](https://weavz.io)
36
+ - [Dashboard](https://dashboard.weavz.io)
37
+ - [Documentation](https://weavz.io/docs)
38
+ - [Python SDK docs](https://weavz.io/docs/sdks/python)
39
+ - [API reference](https://weavz.io/docs/api-reference)
40
+ - [Integration catalog](https://weavz.io/integrations)
41
+
42
+ ## Installation
43
+
44
+ ```bash
45
+ pip install weavz-io-sdk
46
+ ```
47
+
48
+ The SDK supports Python 3.10 and newer.
49
+
50
+ ```python
51
+ from weavz_sdk import WeavzClient
52
+
53
+ client = WeavzClient(api_key="wvz_your_api_key")
54
+ ```
55
+
56
+ ## What You Can Build
57
+
58
+ - Hosted OAuth and credential connection flows for your customers
59
+ - Multi-tenant workspaces with per-user, fixed, or fallback connection strategies
60
+ - Validated action execution across integrations such as Slack, GitHub, Google Sheets, HubSpot, Notion, Stripe, and more
61
+ - Remote MCP servers for Claude, ChatGPT, Codex, Cursor, and custom agents
62
+ - Code Mode MCP servers where agents search, inspect, and call workspace integrations dynamically
63
+ - Tool Mode MCP servers with a small explicit tool list
64
+ - Filesystem and State KV for durable files, checkpoints, cursors, and lightweight agent state
65
+ - Sandbox workflows that run JavaScript, Python, or Shell through the runtime
66
+ - Human Gates for approvals before sensitive actions run
67
+ - Input partials for defaults, locked fields, and reusable action configuration
68
+ - Triggers and webhooks that forward integration events into your product
69
+
70
+ ## Quick Start
71
+
72
+ This example creates a workspace, enables a built-in integration, and executes an action through the SDK.
73
+
74
+ ```python
75
+ from weavz_sdk import WeavzClient
76
+
77
+ client = WeavzClient(api_key="wvz_your_api_key")
78
+
79
+ workspace = client.workspaces.create(
80
+ name="Production",
81
+ slug="production",
82
+ )["workspace"]
83
+
84
+ client.workspaces.add_integration(
85
+ workspace["id"],
86
+ integration_name="hash-encode",
87
+ integration_alias="hash",
88
+ )
89
+
90
+ result = client.actions.execute(
91
+ "hash-encode",
92
+ "hash",
93
+ workspace_id=workspace["id"],
94
+ integration_alias="hash",
95
+ input={
96
+ "text": "hello from weavz",
97
+ "algorithm": "sha256",
98
+ "encoding": "hex",
99
+ },
100
+ )
101
+
102
+ if result["success"]:
103
+ print(result["output"])
104
+
105
+ client.close()
106
+ ```
107
+
108
+ For a guided Slack setup, see the [Quick Start](https://weavz.io/docs/getting-started/quick-start).
109
+
110
+ ## Configuration
111
+
112
+ ```python
113
+ client = WeavzClient(
114
+ api_key="wvz_your_api_key",
115
+ base_url="https://platform.weavz.io",
116
+ timeout=310.0,
117
+ max_retries=2,
118
+ )
119
+ ```
120
+
121
+ | Option | Required | Default | Description |
122
+ | --- | --- | --- | --- |
123
+ | `api_key` | Yes | - | Weavz API key with the `wvz_` prefix |
124
+ | `base_url` | No | `https://platform.weavz.io` | API base URL |
125
+ | `timeout` | No | `310.0` | Request timeout in seconds |
126
+ | `max_retries` | No | `2` | Retry count for transient failures |
127
+
128
+ Use the context manager to close the underlying HTTP client automatically:
129
+
130
+ ```python
131
+ with WeavzClient(api_key="wvz_your_api_key") as client:
132
+ result = client.connections.list()
133
+ print(result["connections"])
134
+ ```
135
+
136
+ ## Core Product Flows
137
+
138
+ ### Workspaces And Integration Aliases
139
+
140
+ Workspaces scope connections, integration configuration, MCP servers, partials, triggers, and end-user access. Add integrations to a workspace under purpose-readable aliases so agents and logs show stable names.
141
+
142
+ ```python
143
+ workspace = client.workspaces.create(
144
+ name="Acme Customer",
145
+ slug="acme-customer",
146
+ )["workspace"]
147
+
148
+ client.workspaces.add_integration(
149
+ workspace["id"],
150
+ integration_name="slack",
151
+ integration_alias="customer_slack",
152
+ connection_strategy="per_user",
153
+ enabled_actions=["send_channel_message"],
154
+ )
155
+ ```
156
+
157
+ Read more:
158
+
159
+ - [Organizations and workspaces](https://weavz.io/docs/concepts/organizations-and-workspaces)
160
+ - [Workspace integrations](https://weavz.io/docs/concepts/integration-selectors)
161
+ - [Integration aliases](https://weavz.io/docs/guides/integration-aliases)
162
+
163
+ ### Hosted Connect
164
+
165
+ Create a hosted connect session when an end user needs to connect Slack, Google, GitHub, or another integration account.
166
+
167
+ ```python
168
+ session = client.connect.create_token(
169
+ integration_name="slack",
170
+ connection_name="Acme Slack",
171
+ external_id="acme_slack",
172
+ workspace_id=workspace["id"],
173
+ end_user_id="user_123",
174
+ )
175
+
176
+ print(f"Send the user here: {session['connectUrl']}")
177
+
178
+ completed = client.connect.wait(
179
+ session["token"],
180
+ timeout=120.0,
181
+ interval=1.0,
182
+ )
183
+
184
+ if completed["status"] == "COMPLETED":
185
+ print(completed["connectionId"])
186
+ ```
187
+
188
+ Read more:
189
+
190
+ - [Connections](https://weavz.io/docs/concepts/connections)
191
+ - [Hosted connect API](https://weavz.io/docs/api-reference/oauth)
192
+ - [Setting up connections](https://weavz.io/docs/guides/setting-up-connections)
193
+
194
+ ### Execute Actions
195
+
196
+ Execute integration actions directly from your backend or product workflows.
197
+
198
+ ```python
199
+ run = client.actions.execute(
200
+ "slack",
201
+ "send_channel_message",
202
+ workspace_id=workspace["id"],
203
+ integration_alias="customer_slack",
204
+ end_user_id="user_123",
205
+ input={
206
+ "channel": "#support",
207
+ "text": "New customer escalation received.",
208
+ },
209
+ idempotency_key="ticket_123_notify_slack",
210
+ )
211
+
212
+ if run.get("status") == "approval_required":
213
+ print("Approval required:", run["approval"]["id"])
214
+ else:
215
+ print("Action output:", run["output"])
216
+ ```
217
+
218
+ Read more:
219
+
220
+ - [Actions](https://weavz.io/docs/concepts/actions)
221
+ - [Executing actions](https://weavz.io/docs/guides/executing-actions)
222
+ - [Actions API reference](https://weavz.io/docs/api-reference/actions)
223
+
224
+ ### MCP Servers For Agents
225
+
226
+ Create remote MCP servers that expose workspace integrations to AI agents. Code Mode is the best default for broad agent workspaces; Tool Mode is useful for small explicit tool surfaces.
227
+
228
+ ```python
229
+ result = client.mcp_servers.create(
230
+ name="Acme Agent Workspace",
231
+ mode="CODE",
232
+ workspace_id=workspace["id"],
233
+ auth_mode="oauth_and_bearer",
234
+ end_user_access="restricted",
235
+ settings={
236
+ "codeMode": {
237
+ "approvalWaitSeconds": 30,
238
+ },
239
+ },
240
+ )
241
+
242
+ server = result["server"]
243
+ mcp_endpoint = result["mcpEndpoint"]
244
+
245
+ token_result = client.mcp_servers.create_bearer_token(
246
+ server["id"],
247
+ end_user_id="user_123",
248
+ scopes=["mcp:tools", "mcp:code"],
249
+ expires_in=60 * 60 * 24 * 30,
250
+ )
251
+
252
+ print(mcp_endpoint, token_result["bearerToken"])
253
+ ```
254
+
255
+ You can also run Code Mode directly through the SDK:
256
+
257
+ ```python
258
+ code_run = client.mcp_servers.execute_code(
259
+ server["id"],
260
+ """
261
+ const parsed = await weavz.datetime.parse_date({
262
+ dateString: "June 18, 2026 9am",
263
+ timezone: "America/New_York"
264
+ })
265
+
266
+ return { parsed }
267
+ """,
268
+ )
269
+ ```
270
+
271
+ Code Mode responses include `structuredContent.timings` for total execution and per-action latency.
272
+ For Agent Browser workflows, batch several browser actions inside one Code Mode script instead of
273
+ calling `execute_code()` once per click or screenshot.
274
+
275
+ Read more:
276
+
277
+ - [MCP servers](https://weavz.io/docs/concepts/mcp-servers)
278
+ - [MCP Code Mode](https://weavz.io/docs/guides/mcp-code-mode)
279
+ - [MCP Tool Mode](https://weavz.io/docs/guides/mcp-tool-mode)
280
+ - [Weavz MCP App](https://weavz.io/docs/guides/weavz-mcp-app)
281
+
282
+ ### Human Gates
283
+
284
+ Human Gates let you require approval before sensitive actions execute.
285
+
286
+ ```python
287
+ policy = client.approval_policies.create(
288
+ workspace_id=workspace["id"],
289
+ name="Approve external messages",
290
+ sources=["sdk", "mcp_code", "mcp_tools"],
291
+ decision="require_approval",
292
+ risk_mode="always",
293
+ approvers=[{"type": "org_role", "roles": ["owner", "admin"]}],
294
+ timeout_seconds=3600,
295
+ default_on_timeout="reject",
296
+ approval_access_mode="dashboard_and_hosted_link",
297
+ )["policy"]
298
+
299
+ guarded = client.actions.execute(
300
+ "slack",
301
+ "send_channel_message",
302
+ workspace_id=workspace["id"],
303
+ integration_alias="customer_slack",
304
+ end_user_id="user_123",
305
+ input={"channel": "#general", "text": "Launch update"},
306
+ )
307
+
308
+ if guarded.get("status") == "approval_required":
309
+ client.approvals.approve(
310
+ guarded["approval"]["id"],
311
+ reason="Message reviewed",
312
+ )
313
+ ```
314
+
315
+ Read more:
316
+
317
+ - [Human Gates guide](https://weavz.io/docs/guides/human-gates)
318
+ - [Approvals API reference](https://weavz.io/docs/api-reference/approvals)
319
+
320
+ ### Input Partials
321
+
322
+ Input partials let you reuse defaults and lock enforced fields so agents or callers only provide the fields they should control.
323
+
324
+ ```python
325
+ partial = client.partials.create(
326
+ workspace["id"],
327
+ "slack",
328
+ "Support channel default",
329
+ action_name="send_channel_message",
330
+ values={"channel": "#support"},
331
+ enforced_keys=["channel"],
332
+ )["partial"]
333
+
334
+ client.actions.execute(
335
+ "slack",
336
+ "send_channel_message",
337
+ workspace_id=workspace["id"],
338
+ integration_alias="customer_slack",
339
+ partial_ids=[partial["id"]],
340
+ input={"text": "A new ticket needs attention."},
341
+ )
342
+ ```
343
+
344
+ Read more:
345
+
346
+ - [Input partials](https://weavz.io/docs/concepts/input-partials)
347
+ - [Using input partials](https://weavz.io/docs/guides/using-input-partials)
348
+
349
+ ### Triggers
350
+
351
+ Enable triggers to receive integration events in your own webhook endpoint.
352
+
353
+ ```python
354
+ trigger = client.triggers.enable(
355
+ integration_name="github",
356
+ trigger_name="new_push",
357
+ workspace_id=workspace["id"],
358
+ integration_alias="customer_github",
359
+ callback_url="https://yourapp.example.com/webhooks/weavz/github",
360
+ callback_metadata={"customerId": "acme"},
361
+ )["triggerSource"]
362
+
363
+ print(trigger["id"])
364
+ ```
365
+
366
+ Read more:
367
+
368
+ - [Triggers](https://weavz.io/docs/concepts/triggers)
369
+ - [Setting up triggers](https://weavz.io/docs/guides/setting-up-triggers)
370
+
371
+ ## Generated Integration Input Models
372
+
373
+ The SDK includes generated Pydantic models and lookup helpers for integration action inputs.
374
+
375
+ ```python
376
+ from weavz_sdk.integrations import (
377
+ INTEGRATION_ACTIONS,
378
+ SlackSendChannelMessageInput,
379
+ get_action_names,
380
+ validate_action_input,
381
+ )
382
+
383
+ print(get_action_names("slack"))
384
+ print(INTEGRATION_ACTIONS["slack"])
385
+
386
+ input_data = SlackSendChannelMessageInput(
387
+ channel="#general",
388
+ text="Typed input from Python",
389
+ )
390
+
391
+ validated = validate_action_input(
392
+ "slack",
393
+ "send_channel_message",
394
+ input_data,
395
+ )
396
+
397
+ result = client.actions.execute_typed(
398
+ "slack",
399
+ "send_channel_message",
400
+ workspace_id=workspace["id"],
401
+ integration_alias="customer_slack",
402
+ input=validated,
403
+ )
404
+ ```
405
+
406
+ The model naming pattern is `{IntegrationName}{ActionName}Input` in PascalCase. Use `execute()` for dynamic or future integrations and `execute_typed()` when you want generated-model validation before the request is sent.
407
+
408
+ ## AI Framework Adapters
409
+
410
+ MCP is the primary hosted agent surface. The SDK also includes small dependency-free adapters that convert configured workspace actions into common AI tool shapes.
411
+
412
+ ```python
413
+ from weavz_sdk import (
414
+ create_mcp_server_action_tools,
415
+ to_anthropic_tool,
416
+ to_openai_responses_tool,
417
+ )
418
+
419
+ tools = create_mcp_server_action_tools(client, server["id"])
420
+
421
+ openai_tools = [to_openai_responses_tool(tool) for tool in tools]
422
+ anthropic_tools = [to_anthropic_tool(tool) for tool in tools]
423
+ ```
424
+
425
+ Optional framework adapters are created lazily when the matching package is installed.
426
+
427
+ ## Resource Map
428
+
429
+ | Resource | Purpose |
430
+ | --- | --- |
431
+ | `client.workspaces` | Workspace management and workspace integrations |
432
+ | `client.connections` | Connection CRUD and resolution |
433
+ | `client.connect` | Hosted connect session creation, polling, and waiting |
434
+ | `client.actions` | Integration action execution and generated input validation |
435
+ | `client.triggers` | Trigger enablement, listing, testing, and disabling |
436
+ | `client.mcp_servers` | MCP servers, tools, tokens, Code Mode execution, declarations |
437
+ | `client.integrations` | Integration metadata, property options, OAuth status |
438
+ | `client.end_users` | End-user identity, connect tokens, invites |
439
+ | `client.partials` | Input partial presets and enforced fields |
440
+ | `client.approval_policies` | Human Gates policy management |
441
+ | `client.approvals` | Approval inbox, decisions, and waiting |
442
+ | `client.api_keys` | Customer-facing API key management |
443
+
444
+ ## Error Handling
445
+
446
+ ```python
447
+ from weavz_sdk import WeavzError
448
+
449
+ try:
450
+ client.actions.execute(
451
+ "slack",
452
+ "send_channel_message",
453
+ workspace_id=workspace["id"],
454
+ integration_alias="customer_slack",
455
+ input={"channel": "#general", "text": "Hello"},
456
+ )
457
+ except WeavzError as error:
458
+ print(error.code)
459
+ print(error.status)
460
+ print(error.details)
461
+ ```
462
+
463
+ ## Publishing And Development
464
+
465
+ This public repository is a release mirror. SDK development happens in the main Weavz monorepo under `sdks/python/`, then this repository is updated from that source directory for releases.
466
+
467
+ For local checks in this repository:
468
+
469
+ ```bash
470
+ python3 -m venv .venv
471
+ . .venv/bin/activate
472
+ pip install -e . pytest
473
+ python -m pytest tests/test_generated_integrations.py
474
+ ```
475
+
476
+ Live integration tests require a running Weavz API stack.
477
+
478
+ ## License
479
+
480
+ [MIT](LICENSE)