matelab-python-sdk 0.1.0a23__tar.gz → 0.1.0a24__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.
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/CHANGELOG.md +19 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/PKG-INFO +66 -47
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/README.md +65 -46
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/contracts/matelab-integration-v1.lock.json +3 -3
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/contracts/matelab-integration-v1.openapi.yaml +204 -97
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/docs/operation-coverage.yaml +53 -53
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/pyproject.toml +1 -1
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/scripts/generate_models.py +0 -2
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/_generated/models.py +274 -18
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/_wire_validation.py +30 -2
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/domains/literature.py +1 -1
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/domains/records.py +3 -3
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/domains/templates.py +1 -1
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_client.py +25 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_generation.py +79 -4
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_record_mutations.py +37 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_template_lifecycle.py +31 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/uv.lock +1 -1
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/.env.example +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/.github/workflows/release.yml +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/.gitignore +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/AGENTS.md +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/CONTEXT.md +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/LICENSE +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/NOTICE +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/docs/agent-architecture.md +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/docs/agent-workflows.md +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/scripts/check_installed_package.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/scripts/check_release.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/__init__.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/_generated/__init__.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/_hashes.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/_transport.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/client.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/domains/__init__.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/domains/_attachment_content.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/domains/cloud_drive.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/domains/groups.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/domains/notebooks.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/domains/uploads.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/domains/users.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/errors.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/py.typed +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/session.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/src/matelab/streaming.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/conftest.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/provider/test_provider_smoke.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_async_attachment_upload.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_cloud_drive.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_comments_and_downloads.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_consumer_smoke.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_errors.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_extended_records.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_groups.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_notebook_lifecycle.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_notebooks.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_operation_coverage.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_record_lifecycle.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_records.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_release.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_streaming.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_templates.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_transport.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_uploads_and_literature.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/test_users.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/typing/consumer.py +0 -0
- {matelab_python_sdk-0.1.0a23 → matelab_python_sdk-0.1.0a24}/tests/typing/pyproject.toml +0 -0
|
@@ -3,6 +3,25 @@
|
|
|
3
3
|
This file records release-to-release changes and migration impact. It is not the authority for the current interface;
|
|
4
4
|
see [README.md](README.md) for current behavior and [AGENTS.md](AGENTS.md) for maintenance policy.
|
|
5
5
|
|
|
6
|
+
## 0.1.0a24 - 2026-09-26
|
|
7
|
+
|
|
8
|
+
- Adopts immutable `matelab-spec v0.5.0` at commit `4f2959472933da47d1ea3e275552884d51d4fdd9`
|
|
9
|
+
(annotated tag object `cc362a9a36601f5d07d6e90c2c6994e33c202d88`) and OpenAPI SHA-256
|
|
10
|
+
`dee14f76e24b2d7c3d97a6f30a9369ac093d615d132db85836ab86671eadcf18`, aligned with Provider source evidence
|
|
11
|
+
`acb0e12f2d62a8959ab9e9bddf38e34a67c19b48`. The release evidence covers an isolated Provider, not production.
|
|
12
|
+
- Breaking: `templates.save_content()` rejects invalid JSON in JSON code modules with non-null `style` before HTTP.
|
|
13
|
+
Generated write models and whole-request validation now enforce nested JSON content schemas. Readback continues to
|
|
14
|
+
preserve raw code strings (including empty or non-JSON text) and null; reading a module does not guarantee it can
|
|
15
|
+
be saved unchanged. JSON code without a style, or with null style, retains its existing write boundary.
|
|
16
|
+
- Regenerates the private application bootstrap fields and credential-login restriction to an omitted or empty
|
|
17
|
+
WeChat code. Public credential login already omits that input. Record module creation preserves explicit code
|
|
18
|
+
strings and leaves omitted/null initialization to the Provider, which now uses an empty string without synthesizing
|
|
19
|
+
an ECharts series object.
|
|
20
|
+
- Documents Chat SSO expiry against the user's mutable activity timestamp, single-attempt exchange, and lack of
|
|
21
|
+
concurrent one-time guarantees. Synchronizes the release's PVD/PCG renumbering and retired comment-upload issue.
|
|
22
|
+
- Keeps staged files-module append root-only because its dedicated schema and `UpdateRecordRequest.add[]` still
|
|
23
|
+
disagree about folder paths (now PVD-030). Retains the read-only missing table-attachment timestamp compatibility.
|
|
24
|
+
|
|
6
25
|
## 0.1.0a23 - 2026-09-04
|
|
7
26
|
|
|
8
27
|
- Temporarily accepts `readRecord` table file attachments that contain valid `filename`, `hash`, and `size` fields but
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: matelab-python-sdk
|
|
3
|
-
Version: 0.1.
|
|
3
|
+
Version: 0.1.0a24
|
|
4
4
|
Summary: Reusable async Python client for the Matelab Integration Contract
|
|
5
5
|
Author-email: 朱天念 <zhutiannian@gmail.com>
|
|
6
6
|
License-Expression: Apache-2.0
|
|
@@ -35,12 +35,14 @@ This README describes the current SDK interface, integration semantics, examples
|
|
|
35
35
|
[AGENTS.md](AGENTS.md) for durable maintenance rules, and `docs/operation-coverage.yaml` for the machine-readable
|
|
36
36
|
operation inventory.
|
|
37
37
|
|
|
38
|
-
The current alpha is `0.1.
|
|
38
|
+
The current alpha is `0.1.0a24`. `[project].version` in `pyproject.toml` is the sole SDK version source;
|
|
39
39
|
`uv.lock` only mirrors that source.
|
|
40
40
|
|
|
41
|
-
The SDK is pinned to the immutable `matelab-spec v0.
|
|
42
|
-
`contracts/matelab-integration-v1.lock.json`,
|
|
43
|
-
|
|
41
|
+
The SDK is pinned to the immutable `matelab-spec v0.5.0` Contract Release. The sole pin,
|
|
42
|
+
`contracts/matelab-integration-v1.lock.json`, records peeled commit `4f2959472933da47d1ea3e275552884d51d4fdd9`,
|
|
43
|
+
source `openapi/matelab-integration-v1.openapi.yaml`, the local snapshot path, and SHA-256
|
|
44
|
+
`dee14f76e24b2d7c3d97a6f30a9369ac093d615d132db85836ab86671eadcf18`. The annotated tag object is
|
|
45
|
+
`cc362a9a36601f5d07d6e90c2c6994e33c202d88`.
|
|
44
46
|
|
|
45
47
|
## Installation
|
|
46
48
|
|
|
@@ -64,15 +66,17 @@ To test the same artifact a downstream Consumer will install, build and install
|
|
|
64
66
|
|
|
65
67
|
```bash
|
|
66
68
|
uv build --no-build-isolation --out-dir dist/release
|
|
67
|
-
python -m pip install dist/release/matelab_python_sdk-0.1.
|
|
69
|
+
python -m pip install dist/release/matelab_python_sdk-0.1.0a24-py3-none-any.whl
|
|
68
70
|
```
|
|
69
71
|
|
|
70
72
|
Do not infer Provider compatibility from the SDK version alone. A release is also bound to the Contract
|
|
71
73
|
tag, commit, and checksum recorded below.
|
|
72
74
|
|
|
73
|
-
The Contract
|
|
74
|
-
|
|
75
|
-
|
|
75
|
+
The Contract uses Provider source evidence from `acb0e12f2d62a8959ab9e9bddf38e34a67c19b48`; v0.5.0 validation ran
|
|
76
|
+
against an isolated test instance and does not establish production behavior. The corresponding Front Consumer evidence
|
|
77
|
+
is `0c985f5b6da8e8ef4627ca7065cea85e408ae981`; it informs cross-Consumer capability review but does not define the SDK
|
|
78
|
+
interface. Provider limitations that remain relevant to integrations are documented alongside the affected interfaces
|
|
79
|
+
below.
|
|
76
80
|
|
|
77
81
|
## Design
|
|
78
82
|
|
|
@@ -121,7 +125,7 @@ success code it does not allow raises `MatelabProtocolError` rather than assigni
|
|
|
121
125
|
`MatelabTransportError.status_code` remains available for HTTP failures. Provider response bodies, top-level `msg`,
|
|
122
126
|
legacy `errmsg`, opaque `errs`, uncontracted debug fields, and request payloads are not attached to exceptions because
|
|
123
127
|
Provider-authored diagnostics may contain stack traces, credentials, or submitted values.
|
|
124
|
-
The pinned v0.
|
|
128
|
+
The pinned v0.5.0 Contract also declares optional code-4 `errs`, but PVD-029 and PCG-010 record opaque array/object
|
|
125
129
|
containers and insufficient evidence for requiredness, cardinality, or exclusion from other codes. The SDK
|
|
126
130
|
therefore keeps those diagnostics wire-only and does not expose `errs` as stable public metadata. A typed detail
|
|
127
131
|
interface remains blocked until a future Contract release can define one from stronger Provider evidence. `retryable`
|
|
@@ -317,9 +321,9 @@ result cannot be retried through the same client.
|
|
|
317
321
|
|
|
318
322
|
Files-module append and table/files replacement use the general record attachment intents and may be combined with
|
|
319
323
|
other non-conflicting record changes. `RecordFilesAttachmentAppend` currently targets the module root. Although
|
|
320
|
-
v0.
|
|
324
|
+
v0.5.0 records Provider evidence for safe folder paths, its top-level `UpdateRecordRequest.add[]` schema still excludes
|
|
321
325
|
the `path` property declared by the dedicated staged-name append shape; the SDK therefore does not expose folder paths
|
|
322
|
-
until that wire-schema conflict is resolved (PVD-
|
|
326
|
+
until that wire-schema conflict is resolved (PVD-030):
|
|
323
327
|
|
|
324
328
|
```python
|
|
325
329
|
from matelab import RecordAttachmentReplacement, RecordFilesAttachmentAppend, RecordValueUpdate
|
|
@@ -333,6 +337,11 @@ await client.records.update(
|
|
|
333
337
|
)
|
|
334
338
|
```
|
|
335
339
|
|
|
340
|
+
For `RecordModuleCreation(module_type="code", language="json", style="echarts")`, omitted, null, and empty `data` all
|
|
341
|
+
produce an empty string; explicit `"0"` stays `"0"`. Send the desired initial chart configuration as a JSON code string.
|
|
342
|
+
Richtext/code module creation defaults missing `data` to `""`; form/table/files creation ignores it and initializes
|
|
343
|
+
content as `[]`.
|
|
344
|
+
|
|
336
345
|
A replacement starts with an occurrence returned by `records.read()`; applications must not fabricate a
|
|
337
346
|
`RecordAttachmentRef`. The same `RecordAttachmentReplacement` covers both table-file and files-module occurrences:
|
|
338
347
|
|
|
@@ -436,7 +445,8 @@ and `deletePersonalLiteratureItem`.
|
|
|
436
445
|
Every other implemented operation is explicitly `experimental`; the exact per-operation list and its
|
|
437
446
|
PVD/PCG references live in
|
|
438
447
|
`docs/operation-coverage.yaml`. `readApplicationBootstrap` is intentionally unexposed because it returns the Provider
|
|
439
|
-
application environment and menu model,
|
|
448
|
+
application environment and menu model, including required `data_express_enable` and `data_express_text` fields, while
|
|
449
|
+
SDK identity is sourced from token issuance. `readLiteratureCreateTemplate`
|
|
440
450
|
is intentionally unexposed because it returns a frontend form definition and an optional deployment flag rather than
|
|
441
451
|
a resource needed by the SDK interface. There are no `planned` operations. Experimental support means the SDK
|
|
442
452
|
validates and exposes the pinned Contract while preserving limitations such as unstable ordering/pagination,
|
|
@@ -450,6 +460,13 @@ automatically retried, and the returned token set is stored in the same in-memor
|
|
|
450
460
|
session = await client.exchange_chat_sso_code(code="chat-sanitizedcode123", key="sanitized-shared-key")
|
|
451
461
|
```
|
|
452
462
|
|
|
463
|
+
The code suffix must be non-empty and the shared key must be non-blank. The Provider rejects a code after the current
|
|
464
|
+
user's `active_datetime` plus 300 seconds; that timestamp can change through other user activity, so Consumers must not
|
|
465
|
+
derive a deadline from the code or automatically retry an uncertain exchange. A sequential replay is rejected, but the
|
|
466
|
+
Provider's read-then-clear implementation does not guarantee that concurrent exchanges have only one winner.
|
|
467
|
+
Ordinary credential login does not expose the non-empty WeChat binding code branch, which can reassign another account's
|
|
468
|
+
OpenID (PVD-032).
|
|
469
|
+
|
|
453
470
|
Group and user discovery expose sharing identities without inventing Provider pagination:
|
|
454
471
|
|
|
455
472
|
```python
|
|
@@ -460,7 +477,7 @@ targets = await client.users.search("Example Researcher", global_scope=False)
|
|
|
460
477
|
`groups.list()` returns the `GroupSummary` tuple directly. Ordering remains Provider-unspecified and is documented
|
|
461
478
|
rather than repeated as a constant result field. The Provider's members for an unstable first group remain wire-only;
|
|
462
479
|
`users.search()` is the public recipient-discovery interface. These two discovery interfaces are experimental because
|
|
463
|
-
group order is unstable and user search is unpaged, unordered and not field-minimized (PVD-
|
|
480
|
+
group order is unstable and user search is unpaged, unordered and not field-minimized (PVD-017, PVD-025).
|
|
464
481
|
`GroupSummary.notebook_creation_available` expresses whether the group can currently host notebook creation without
|
|
465
482
|
exposing the Provider's data-server routing value.
|
|
466
483
|
|
|
@@ -485,7 +502,7 @@ Consequently, update performs one list pre-read followed by the write. This pres
|
|
|
485
502
|
Provider offers no compare-and-swap or atomic read-modify-write operation. Call `list()` or `shares()` explicitly when
|
|
486
503
|
the application needs current state. `NotebookPermissions` normalizes the Provider's stored and effective masks and
|
|
487
504
|
is reused by record pages instead of maintaining a second nearly identical permission model. Direct shares always
|
|
488
|
-
have implicit read access even when every optional permission is false (PVD-
|
|
505
|
+
have implicit read access even when every optional permission is false (PVD-037).
|
|
489
506
|
`provider_signing_allowed` only represents Provider policy, not an SDK signing operation. Share-list order remains
|
|
490
507
|
unspecified.
|
|
491
508
|
|
|
@@ -510,17 +527,19 @@ await client.templates.save_content(template, modules)
|
|
|
510
527
|
`TemplateModule.data_present` distinguishes a missing `data` property from an explicit null value, while
|
|
511
528
|
`attributes` prevents additive canonical properties from being dropped during a read/save cycle. The SDK does not
|
|
512
529
|
synthesize frontend editor UIDs, layout widths, rows, folders, option encoding, or a fixed set of display module
|
|
513
|
-
types. A JSON-language code module
|
|
514
|
-
|
|
530
|
+
types. A JSON-language code module's `data` remains code text and may be empty, null, or invalid JSON;
|
|
531
|
+
`language=json` does not imply that Consumers can parse it. When template content contains a code module with
|
|
532
|
+
`language=json` and non-null `style`, its code text must be valid JSON to save. Number and boolean table cells preserve
|
|
533
|
+
the Provider's empty string as distinct from scalar and `null` values. The Provider accepts some
|
|
515
534
|
non-canonical module roots and arbitrary table file arrays, but the SDK does not expose that behavior: saved content
|
|
516
|
-
must remain a canonical module list, and a table file cell must be one canonical attachment object or `null` (PVD-
|
|
517
|
-
The Provider supports only whole-content replacement and has no atomic patch or compare-and-swap operation (PCG-
|
|
535
|
+
must remain a canonical module list, and a table file cell must be one canonical attachment object or `null` (PVD-013).
|
|
536
|
+
The Provider supports only whole-content replacement and has no atomic patch or compare-and-swap operation (PCG-008),
|
|
518
537
|
so a read-modify-save sequence can overwrite a concurrent change.
|
|
519
538
|
|
|
520
539
|
The market result retains the Provider's `total_count` and derives `has_more` without echoing the caller's page
|
|
521
540
|
arguments; it does not claim a stable order or continuation token. Template reads remain experimental
|
|
522
541
|
because Provider discovery ordering/pagination and historical `images` compatibility are not fully stable
|
|
523
|
-
(PCG-
|
|
542
|
+
(PCG-011, PCG-012, PVD-038, PVD-022).
|
|
524
543
|
|
|
525
544
|
`templates.list()` returns one tuple. `TemplateSummary.scope` is limited to `owned`, `shared`, `group`, and `public`;
|
|
526
545
|
Provider marketplace acquisitions and system defaults are both public templates. An acquired public template carries
|
|
@@ -535,7 +554,7 @@ transaction. Creation returns the new `TemplateRef`; metadata replacement and ot
|
|
|
535
554
|
the Provider supplies no new resource representation. `update()` therefore requires the complete title, summary, and
|
|
536
555
|
keyword set rather than implying a partial patch. `update_usage()` generates the Provider's required fresh hidden
|
|
537
556
|
correlation value internally. Usage attachments remain unsupported until their staging and binding lifecycle is
|
|
538
|
-
contracted safely (PVD-
|
|
557
|
+
contracted safely (PVD-003). Marketplace revision limitations remain explicit through `content_version`,
|
|
539
558
|
`published_content_version`, and `market_review_reason` (PVD-021).
|
|
540
559
|
|
|
541
560
|
Extended record reads stay behind the same `records` interface:
|
|
@@ -555,7 +574,7 @@ relations = await client.records.relations(source)
|
|
|
555
574
|
as `modules`; it is not the template-shaped `RecordImportItem.data` accepted by record import.
|
|
556
575
|
`records.search()` maps each requested field name to a stored record path. A match exposes only Provider-returned
|
|
557
576
|
entries in `values`, so key membership distinguishes an absent result from an explicit JSON `null`.
|
|
558
|
-
The current Provider excludes encrypted records from search (PVD-
|
|
577
|
+
The current Provider excludes encrypted records from search (PVD-041); an empty search result therefore does
|
|
559
578
|
not prove that no matching encrypted record exists.
|
|
560
579
|
|
|
561
580
|
The Provider calls its notebook directory tree `subtype`; that name remains wire-only. The SDK exposes
|
|
@@ -565,7 +584,7 @@ The Provider calls its notebook directory tree `subtype`; that name remains wire
|
|
|
565
584
|
positive folder ID for one folder.
|
|
566
585
|
|
|
567
586
|
`records.page` fixes the legacy request to `page_size=0&default=1`, preventing the known owner-preference writes
|
|
568
|
-
described by PVD-
|
|
587
|
+
described by PVD-028; its total is derived internally from the Provider's complete matching ID list. The result keeps
|
|
569
588
|
semantic `NotebookPermissions` directly, without a shallow context model or duplicated notebook/owner/template
|
|
570
589
|
display metadata. Effective request pagination, the UI selection list and Provider keyword-filter echo are not exposed.
|
|
571
590
|
Its `search` argument, shared with `records.list()`, maps the Provider's wire-level `content` filter without exposing
|
|
@@ -603,10 +622,10 @@ imported = await client.records.import_dataset(
|
|
|
603
622
|
|
|
604
623
|
Blank-record creation returns `None` because the Provider returns no record identity, even when the caller supplies a
|
|
605
624
|
UID. Import validates the complete batch with generated wire models but cannot map returned database IDs to
|
|
606
|
-
individual inputs or promise atomicity (PCG-
|
|
625
|
+
individual inputs or promise atomicity (PCG-009); it therefore returns only the tuple of database IDs actually
|
|
607
626
|
reported by the Provider. `RecordImportItem.keywords` is a tuple; the adapter owns the Provider's
|
|
608
627
|
legacy semicolon encoding. Folder paths are ordered existing folder titles from the notebook root; they do not create
|
|
609
|
-
missing folders. The current Provider rejects explicit-null table-file imports (PVD-
|
|
628
|
+
missing folders. The current Provider rejects explicit-null table-file imports (PVD-031). Because the SDK accepts
|
|
610
629
|
arbitrary template-shaped data and cannot identify file columns without the template definition, integrations must omit
|
|
611
630
|
an unset file-valued key instead of sending it as `None`. Delete means moving records into the recycle bin, not permanent
|
|
612
631
|
deletion. Delete and restore return `None`; record mutations are not automatically retried.
|
|
@@ -618,8 +637,8 @@ without a readback request. Omitting `target_notebook` copies within the source
|
|
|
618
637
|
Record patching exposes a deliberately narrower capability than the raw Provider operation. Scalar/module changes
|
|
619
638
|
cannot smuggle Provider-native attachment strings; staged attachments use separate form-removal, table-replacement,
|
|
620
639
|
files append/replace/remove, and rich-text types. Unsafe form replacement and table-file removal are absent, while a
|
|
621
|
-
files/images removal is rejected when the observed module contains the same hash more than once (PVD-
|
|
622
|
-
PVD-
|
|
640
|
+
files/images removal is rejected when the observed module contains the same hash more than once (PVD-010, PVD-018,
|
|
641
|
+
and PVD-019). The SDK reads current content only when a change needs attachment type, occurrence, row, or index state;
|
|
623
642
|
ordinary module creation and deletion rely on the Provider's own canonical update validation. `records.update()`
|
|
624
643
|
returns the acknowledgement classification
|
|
625
644
|
`"persisted"`, `"pending"`, or `"unknown"`; it does not
|
|
@@ -628,9 +647,9 @@ retries stay disabled. Encrypted record content is outside the SDK's public read
|
|
|
628
647
|
`RecordSummary.encrypted` flag lets callers identify and skip it, while the Provider password field and frontend-only
|
|
629
648
|
password lifecycle remain unexposed. Files-module attachment append remains root-only because the pinned top-level
|
|
630
649
|
update request schema does not admit the dedicated staged-name append shape's folder `path`; malformed path containers
|
|
631
|
-
may also silently append at root according to PVD-
|
|
650
|
+
may also silently append at root according to PVD-030. A staged attachment is indeterminate once the write has started.
|
|
632
651
|
|
|
633
|
-
Relation addition reads both endpoints and checks their resolved data server before writing; this reduces PVD-
|
|
652
|
+
Relation addition reads both endpoints and checks their resolved data server before writing; this reduces PVD-009
|
|
634
653
|
risk but is not an atomic Provider authorization guarantee. It does not list relations merely to inspect the
|
|
635
654
|
caller-relative `editable` display flag: the mutation endpoint performs the source permission check. Relation
|
|
636
655
|
deletion lists current relations only to refuse an observed cross-notebook target-ID collision because the Provider
|
|
@@ -640,12 +659,12 @@ ignores target notebook identity (PVD-020); its mutation likewise performs autho
|
|
|
640
659
|
`records.comments()`. Each returned `RecordRelationRef` carries only the relation row and declared target IDs.
|
|
641
660
|
Deletion accepts the source `RecordLocator` and one of those observed refs.
|
|
642
661
|
|
|
643
|
-
Comment upload follows the current Provider's literal one-request `file` field
|
|
662
|
+
Comment upload follows the current Provider's literal one-request `file` field. Comment mutations return `None`
|
|
644
663
|
after acknowledgement. Edit first verifies that the selected
|
|
645
664
|
comment is currently observed and caller-owned because the Provider otherwise reports a false success for a missing or
|
|
646
665
|
other-user ID (PVD-004). Delete sends the typed ref directly because the Provider mutation itself enforces record and
|
|
647
666
|
caller ownership. Neither operation performs a post-write read. Staged comment attachments have no Contract abort
|
|
648
|
-
operation, and binding remains affected by PVD-
|
|
667
|
+
operation, and binding remains affected by PVD-003. Comment create/update use the same `body` vocabulary as the
|
|
649
668
|
returned `RecordComment.body`; the SDK does not perform rich-text display normalization, while the Provider's
|
|
650
669
|
documented surrounding-whitespace trim still applies when saving.
|
|
651
670
|
`RecordCommentRef` carries its `RecordLocator`, so update and delete accept the ref rather than an entire comment or a
|
|
@@ -667,9 +686,9 @@ async with await client.records.download_comment_attachment(
|
|
|
667
686
|
```
|
|
668
687
|
|
|
669
688
|
`DownloadStream` exposes status, content type, length, range, and disposition metadata without buffering the
|
|
670
|
-
complete file. Streams are not automatically replayed. `ByteRange` deliberately rejects `bytes=0-0` (PVD-
|
|
689
|
+
complete file. Streams are not automatically replayed. `ByteRange` deliberately rejects `bytes=0-0` (PVD-015).
|
|
671
690
|
Comment attachment refs contain only file identity. Pass the parent comment ref returned by the same read when
|
|
672
|
-
downloading; current Providers do not verify that association (PVD-
|
|
691
|
+
downloading; current Providers do not verify that association (PVD-006).
|
|
673
692
|
|
|
674
693
|
Cross-domain staging keeps resumable state and completed-file identity separate:
|
|
675
694
|
|
|
@@ -691,7 +710,7 @@ Provider URL and upload-session identity needed by internal binding and cleanup
|
|
|
691
710
|
splice either into content. The result does not claim that a later literature/cloud operation checks the uploader or
|
|
692
711
|
consumes the file exactly once. `uploads.abort()` accepts either an active `StagedUploadSession` or a completed
|
|
693
712
|
`StagedFile` and exposes the Provider's legacy code-2 cancellation signal as a `None`-returning compensating cleanup
|
|
694
|
-
that is not independently verified (PVD-
|
|
713
|
+
that is not independently verified (PVD-024).
|
|
695
714
|
Staging mutations are never automatically retried.
|
|
696
715
|
|
|
697
716
|
Literature identities distinguish the personal library from shared libraries:
|
|
@@ -721,7 +740,7 @@ The Provider's static literature form definition and extraction deployment flag
|
|
|
721
740
|
returns a `PublicationMetadataCandidate`: unstored, rich publication evidence rather than metadata already attached to
|
|
722
741
|
a literature item. Its structured authors are `PublicationAuthorCandidate` values. Extraction accepts a DOI, a
|
|
723
742
|
completed staged PDF, or both; a supplied DOI takes precedence over the staged PDF. A non-empty DOI must match
|
|
724
|
-
`^10\.[0-9]+/\S+$`; the generated request model rejects other values before sending them to the Provider (PVD-
|
|
743
|
+
`^10\.[0-9]+/\S+$`; the generated request model rejects other values before sending them to the Provider (PVD-040).
|
|
725
744
|
Literature list
|
|
726
745
|
results likewise exclude Provider-generated citation HTML and author-highlight fragments; Consumers receive the
|
|
727
746
|
underlying citation fields instead of presentation markup. `LiteratureDetail.metadata` is `None` when invalid legacy
|
|
@@ -746,22 +765,22 @@ Create returns `None` and never guesses the new item from list position because
|
|
|
746
765
|
canonical update preflights the raw item response and refuses to drop top-level or nested source/hidden fields. Passing
|
|
747
766
|
`allow_source_metadata_loss=True` explicitly skips that preflight and sends the canonical replacement directly. The
|
|
748
767
|
default read/check/write protection is best effort rather than atomic because the Provider offers no revision or
|
|
749
|
-
compare-and-swap condition; this Provider-specific behavior remains internal to the update operation (PVD-
|
|
768
|
+
compare-and-swap condition; this Provider-specific behavior remains internal to the update operation (PVD-012).
|
|
750
769
|
PDF replace/delete are separate acknowledged mutations and are not presented as atomic with metadata.
|
|
751
770
|
Permanent personal deletion is named `permanently_delete`, returns `None`, and is non-recoverable. Sharing requires
|
|
752
771
|
list-observed item summaries, user-search summaries and a
|
|
753
|
-
valid caller identity, then returns `None` because the Provider supplies no per-recipient IDs (PVD-
|
|
772
|
+
valid caller identity, then returns `None` because the Provider supplies no per-recipient IDs (PVD-008, PVD-027).
|
|
754
773
|
|
|
755
774
|
Literature comments use explicit `create_comment()` and `update_comment()` intents. Creation first reads the current
|
|
756
775
|
detail and rejects when the caller already owns a comment; callers then use that comment's `LiteratureCommentRef` with
|
|
757
776
|
`update_comment()`. The ref contains only the Provider comment-row identity. Update and delete send that identity
|
|
758
777
|
directly because the Provider mutation verifies current ownership and library permission. The creation preflight
|
|
759
778
|
maintains the Integration Contract's one-caller-comment invariant for ordinary SDK use, but is not atomic because the
|
|
760
|
-
Provider has no matching uniqueness constraint (PVD-
|
|
779
|
+
Provider has no matching uniqueness constraint (PVD-026). When sharing with `copy_owner_comment=True`, multiple
|
|
761
780
|
caller-owned comments remain an explicit ambiguity because the Provider would otherwise choose one implicitly. A
|
|
762
781
|
staged attachment can replace one `matelab-staged-file` marker; raw temporary URLs are rejected. These checks prevent
|
|
763
|
-
common misuse but do not repair the Provider's cross-user UID lookup (PVD-
|
|
764
|
-
experimental because the Provider permission JOIN is not scoped to the current user (PVD-
|
|
782
|
+
common misuse but do not repair the Provider's cross-user UID lookup (PVD-003). Shared-library reads and writes remain
|
|
783
|
+
experimental because the Provider permission JOIN is not scoped to the current user (PVD-007); successful SDK calls
|
|
765
784
|
must not be treated as independent authorization proof. Literature PDF downloads reuse `DownloadStream` and the
|
|
766
785
|
stable `ByteRange` subset.
|
|
767
786
|
|
|
@@ -777,16 +796,16 @@ await client.cloud_drive.bind_staged_file(staged, target=folder)
|
|
|
777
796
|
snapshot and quota usage; pagination applies only to `files`, while request page arguments are not echoed. Personal-root
|
|
778
797
|
metadata and permissions are synthetic/fixed for this Contract line and remain wire-only. File rows omit the constant
|
|
779
798
|
caller owner fields and do not invent a folder location that the Provider fails to return for root-wide searches.
|
|
780
|
-
Listings likewise omit search/order/direction request echoes. Ordering has no stable ID tie-breaker (PCG-
|
|
799
|
+
Listings likewise omit search/order/direction request echoes. Ordering has no stable ID tie-breaker (PCG-011, PVD-038).
|
|
781
800
|
Cloud files expose the nullable stored modification timestamp, not the Provider's duplicate display-formatted date and
|
|
782
801
|
time strings.
|
|
783
802
|
|
|
784
803
|
Folder create returns a `CloudFolderRef` built from the Provider ID. Other folder and file mutations return `None`
|
|
785
804
|
after acknowledgement and do not automatically list the drive. Staged finalize accepts a completed `StagedFile`;
|
|
786
|
-
the Provider binds by temporary row ID without checking its owner (PVD-
|
|
805
|
+
the Provider binds by temporary row ID without checking its owner (PVD-002), and finalize atomicity/idempotency remain
|
|
787
806
|
absent. Batch move and permanent delete do not claim Provider per-item results or atomicity. Permanent
|
|
788
807
|
deletion is named `permanently_delete_files` and is non-recoverable. Cloud downloads
|
|
789
|
-
resolve bytes from the final file identity and reuse `DownloadStream`, thumbnail/preview choices and the PVD-
|
|
808
|
+
resolve bytes from the final file identity and reuse `DownloadStream`, thumbnail/preview choices and the PVD-015-safe
|
|
790
809
|
range subset. Cloud mutations are not automatically retried.
|
|
791
810
|
|
|
792
811
|
Owned, shared, and public catalog notebooks use one `NotebookRef`, distinguished by its
|
|
@@ -822,7 +841,7 @@ Template render metadata is also excluded from template summaries and record rea
|
|
|
822
841
|
notebook title/keywords, Provider data-server routing, or the frontend PDF-capability flag. `Record.version` identifies
|
|
823
842
|
historical content and is `None` for the current content. `Record.versions` contains refs usable for historical reads;
|
|
824
843
|
Provider lock and signature projections remain wire-only. Relation creation still checks returned data servers
|
|
825
|
-
internally to mitigate PVD-
|
|
844
|
+
internally to mitigate PVD-009.
|
|
826
845
|
|
|
827
846
|
Provider record-finalization and additional-signature mutations are intentionally outside the pinned Contract and SDK
|
|
828
847
|
interface. They require the account password to unlock a private key, combine version creation with signing, provide no
|
|
@@ -926,6 +945,6 @@ uv run python scripts/check_release.py dist/release/*.whl dist/release/*.tar.gz
|
|
|
926
945
|
```
|
|
927
946
|
|
|
928
947
|
Rebuilding the same commit with the same locked environment and `SOURCE_DATE_EPOCH` must produce
|
|
929
|
-
byte-identical wheel and source distribution hashes. The
|
|
930
|
-
`
|
|
931
|
-
`
|
|
948
|
+
byte-identical wheel and source distribution hashes. The SDK Contract pin is immutable `matelab-spec v0.5.0`, commit
|
|
949
|
+
`4f2959472933da47d1ea3e275552884d51d4fdd9`, and OpenAPI SHA-256
|
|
950
|
+
`dee14f76e24b2d7c3d97a6f30a9369ac093d615d132db85836ab86671eadcf18`.
|