docket-client 0.3.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.
- docket_client-0.3.2/.gitignore +26 -0
- docket_client-0.3.2/PKG-INFO +233 -0
- docket_client-0.3.2/README.md +202 -0
- docket_client-0.3.2/docket/__init__.py +8 -0
- docket_client-0.3.2/docket/api/__init__.py +1 -0
- docket_client-0.3.2/docket/api/access/__init__.py +1 -0
- docket_client-0.3.2/docket/api/access/add_principal.py +193 -0
- docket_client-0.3.2/docket/api/access/archive_role_assignment.py +182 -0
- docket_client-0.3.2/docket/api/access/create_api_token.py +198 -0
- docket_client-0.3.2/docket/api/access/create_application_principal.py +188 -0
- docket_client-0.3.2/docket/api/access/create_role_assignment.py +194 -0
- docket_client-0.3.2/docket/api/access/list_api_tokens.py +184 -0
- docket_client-0.3.2/docket/api/access/list_principals.py +184 -0
- docket_client-0.3.2/docket/api/access/list_role_assignments.py +200 -0
- docket_client-0.3.2/docket/api/access/revoke_api_token.py +173 -0
- docket_client-0.3.2/docket/api/identity/__init__.py +1 -0
- docket_client-0.3.2/docket/api/identity/create_my_api_token.py +206 -0
- docket_client-0.3.2/docket/api/identity/get_me.py +127 -0
- docket_client-0.3.2/docket/api/identity/list_my_api_tokens.py +151 -0
- docket_client-0.3.2/docket/api/identity/revoke_my_api_token.py +178 -0
- docket_client-0.3.2/docket/api/recurring_acquisitions/__init__.py +1 -0
- docket_client-0.3.2/docket/api/recurring_acquisitions/archive_recurring_acquisition.py +207 -0
- docket_client-0.3.2/docket/api/recurring_acquisitions/create_recurring_acquisition.py +218 -0
- docket_client-0.3.2/docket/api/recurring_acquisitions/get_recurring_acquisition.py +163 -0
- docket_client-0.3.2/docket/api/recurring_acquisitions/list_recurring_acquisitions.py +248 -0
- docket_client-0.3.2/docket/api/recurring_acquisitions/preview_recurring_acquisition.py +187 -0
- docket_client-0.3.2/docket/api/recurring_acquisitions/preview_split_recurring_acquisition.py +232 -0
- docket_client-0.3.2/docket/api/recurring_acquisitions/split_recurring_acquisition.py +258 -0
- docket_client-0.3.2/docket/api/runs/__init__.py +1 -0
- docket_client-0.3.2/docket/api/runs/get_run.py +160 -0
- docket_client-0.3.2/docket/api/runs/list_runs.py +180 -0
- docket_client-0.3.2/docket/api/runs/report_run_outcome.py +206 -0
- docket_client-0.3.2/docket/api/scheduled_acquisitions/__init__.py +1 -0
- docket_client-0.3.2/docket/api/scheduled_acquisitions/archive_scheduled_acquisition.py +203 -0
- docket_client-0.3.2/docket/api/scheduled_acquisitions/create_scheduled_acquisition.py +185 -0
- docket_client-0.3.2/docket/api/scheduled_acquisitions/get_resolved_settings.py +169 -0
- docket_client-0.3.2/docket/api/scheduled_acquisitions/get_scheduled_acquisition.py +159 -0
- docket_client-0.3.2/docket/api/scheduled_acquisitions/list_active_acquisitions.py +297 -0
- docket_client-0.3.2/docket/api/scheduled_acquisitions/list_runs_for_scheduled_acquisition.py +191 -0
- docket_client-0.3.2/docket/api/scheduled_acquisitions/list_scheduled_acquisitions.py +332 -0
- docket_client-0.3.2/docket/api/scheduled_acquisitions/preview_scheduled_acquisition_edit.py +224 -0
- docket_client-0.3.2/docket/api/scheduled_acquisitions/set_planning_status.py +199 -0
- docket_client-0.3.2/docket/api/scheduled_acquisitions/start_run.py +221 -0
- docket_client-0.3.2/docket/api/scheduled_acquisitions/update_scheduled_acquisition.py +226 -0
- docket_client-0.3.2/docket/api/settings/__init__.py +1 -0
- docket_client-0.3.2/docket/api/settings/list_behavior_curriculum_discriminator_values.py +188 -0
- docket_client-0.3.2/docket/api/settings/list_behavior_curriculum_settings.py +199 -0
- docket_client-0.3.2/docket/api/settings/list_fip_discriminator_values.py +184 -0
- docket_client-0.3.2/docket/api/settings/list_fip_settings.py +195 -0
- docket_client-0.3.2/docket/api/settings/list_live_behavior_curriculum_settings.py +233 -0
- docket_client-0.3.2/docket/api/settings/list_live_fip_settings.py +225 -0
- docket_client-0.3.2/docket/api/settings/preview_behavior_curriculum_settings.py +191 -0
- docket_client-0.3.2/docket/api/settings/preview_fip_settings.py +177 -0
- docket_client-0.3.2/docket/api/settings/push_behavior_curriculum_settings.py +222 -0
- docket_client-0.3.2/docket/api/settings/push_fip_settings.py +206 -0
- docket_client-0.3.2/docket/api/templates/__init__.py +1 -0
- docket_client-0.3.2/docket/api/templates/archive_template.py +203 -0
- docket_client-0.3.2/docket/api/templates/create_template.py +206 -0
- docket_client-0.3.2/docket/api/templates/get_template.py +159 -0
- docket_client-0.3.2/docket/api/templates/list_templates.py +174 -0
- docket_client-0.3.2/docket/api/templates/update_template.py +234 -0
- docket_client-0.3.2/docket/api/vocabulary/__init__.py +1 -0
- docket_client-0.3.2/docket/api/vocabulary/list_instruments.py +165 -0
- docket_client-0.3.2/docket/api/vocabulary/list_persons.py +132 -0
- docket_client-0.3.2/docket/api/vocabulary/list_projects.py +132 -0
- docket_client-0.3.2/docket/api/vocabulary/list_subjects.py +132 -0
- docket_client-0.3.2/docket/api/vocabulary/lookup_person.py +166 -0
- docket_client-0.3.2/docket/api/vocabulary/lookup_subject.py +166 -0
- docket_client-0.3.2/docket/api/vocabulary/sync_vocabulary.py +148 -0
- docket_client-0.3.2/docket/client.py +272 -0
- docket_client-0.3.2/docket/errors.py +16 -0
- docket_client-0.3.2/docket/models/__init__.py +221 -0
- docket_client-0.3.2/docket/models/access_role.py +12 -0
- docket_client-0.3.2/docket/models/access_role_nullable_type_1.py +12 -0
- docket_client-0.3.2/docket/models/access_role_nullable_type_2_type_1.py +12 -0
- docket_client-0.3.2/docket/models/access_role_nullable_type_3_type_1.py +12 -0
- docket_client-0.3.2/docket/models/acquisition_variable.py +72 -0
- docket_client-0.3.2/docket/models/acquisition_warning.py +126 -0
- docket_client-0.3.2/docket/models/add_principal_request.py +83 -0
- docket_client-0.3.2/docket/models/api_token_response.py +271 -0
- docket_client-0.3.2/docket/models/api_token_status.py +10 -0
- docket_client-0.3.2/docket/models/archive_recurring_acquisition_request.py +77 -0
- docket_client-0.3.2/docket/models/archive_recurring_acquisition_response.py +83 -0
- docket_client-0.3.2/docket/models/archive_scheduled_acquisition_request.py +78 -0
- docket_client-0.3.2/docket/models/archive_template_request.py +66 -0
- docket_client-0.3.2/docket/models/auth_mode.py +10 -0
- docket_client-0.3.2/docket/models/behavior_curriculum_push_settings_request.py +85 -0
- docket_client-0.3.2/docket/models/behavior_curriculum_settings.py +55 -0
- docket_client-0.3.2/docket/models/behavior_curriculum_settings_preview_response.py +102 -0
- docket_client-0.3.2/docket/models/behavior_curriculum_settings_preview_response_promoted.py +50 -0
- docket_client-0.3.2/docket/models/behavior_curriculum_settings_version_response.py +160 -0
- docket_client-0.3.2/docket/models/behavior_curriculum_settings_version_response_promoted.py +50 -0
- docket_client-0.3.2/docket/models/caller_kind.py +11 -0
- docket_client-0.3.2/docket/models/create_api_token_request.py +97 -0
- docket_client-0.3.2/docket/models/create_application_principal_request.py +65 -0
- docket_client-0.3.2/docket/models/create_personal_api_token_request.py +167 -0
- docket_client-0.3.2/docket/models/create_recurring_acquisition_request.py +269 -0
- docket_client-0.3.2/docket/models/create_role_assignment_request.py +99 -0
- docket_client-0.3.2/docket/models/create_scheduled_acquisition_request.py +265 -0
- docket_client-0.3.2/docket/models/create_template_request.py +323 -0
- docket_client-0.3.2/docket/models/created_api_token_response.py +82 -0
- docket_client-0.3.2/docket/models/effective_status.py +15 -0
- docket_client-0.3.2/docket/models/fip_color.py +13 -0
- docket_client-0.3.2/docket/models/fip_fiber.py +93 -0
- docket_client-0.3.2/docket/models/fip_mode.py +9 -0
- docket_client-0.3.2/docket/models/fip_push_settings_request.py +82 -0
- docket_client-0.3.2/docket/models/fip_settings.py +91 -0
- docket_client-0.3.2/docket/models/fip_settings_preview_response.py +97 -0
- docket_client-0.3.2/docket/models/fip_settings_preview_response_promoted.py +50 -0
- docket_client-0.3.2/docket/models/fip_settings_version_response.py +155 -0
- docket_client-0.3.2/docket/models/fip_settings_version_response_promoted.py +50 -0
- docket_client-0.3.2/docket/models/future_occurrences.py +9 -0
- docket_client-0.3.2/docket/models/get_resolved_settings_response_200.py +65 -0
- docket_client-0.3.2/docket/models/held_role_response.py +116 -0
- docket_client-0.3.2/docket/models/http_validation_problem_details.py +204 -0
- docket_client-0.3.2/docket/models/http_validation_problem_details_errors.py +59 -0
- docket_client-0.3.2/docket/models/instrument_response.py +91 -0
- docket_client-0.3.2/docket/models/kept_occurrence.py +85 -0
- docket_client-0.3.2/docket/models/kept_occurrence_reason.py +10 -0
- docket_client-0.3.2/docket/models/list_active_acquisitions_effective_status_item.py +15 -0
- docket_client-0.3.2/docket/models/list_scheduled_acquisitions_planning_status.py +11 -0
- docket_client-0.3.2/docket/models/me_caller.py +118 -0
- docket_client-0.3.2/docket/models/me_permission.py +98 -0
- docket_client-0.3.2/docket/models/me_response.py +158 -0
- docket_client-0.3.2/docket/models/me_role.py +75 -0
- docket_client-0.3.2/docket/models/occurrence_preview.py +121 -0
- docket_client-0.3.2/docket/models/occurrence_summary.py +126 -0
- docket_client-0.3.2/docket/models/occurrence_warnings.py +91 -0
- docket_client-0.3.2/docket/models/permission_action.py +12 -0
- docket_client-0.3.2/docket/models/person_assignment.py +74 -0
- docket_client-0.3.2/docket/models/person_lookup_response.py +131 -0
- docket_client-0.3.2/docket/models/person_response.py +103 -0
- docket_client-0.3.2/docket/models/person_role.py +9 -0
- docket_client-0.3.2/docket/models/personal_token_limits.py +92 -0
- docket_client-0.3.2/docket/models/planning_status.py +11 -0
- docket_client-0.3.2/docket/models/principal_kind.py +9 -0
- docket_client-0.3.2/docket/models/principal_response.py +216 -0
- docket_client-0.3.2/docket/models/problem_details.py +177 -0
- docket_client-0.3.2/docket/models/project_response.py +75 -0
- docket_client-0.3.2/docket/models/recurrence_exception_kind.py +13 -0
- docket_client-0.3.2/docket/models/recurrence_exception_response.py +103 -0
- docket_client-0.3.2/docket/models/recurrence_frequency.py +9 -0
- docket_client-0.3.2/docket/models/recurrence_preview_response.py +101 -0
- docket_client-0.3.2/docket/models/recurrence_rule.py +207 -0
- docket_client-0.3.2/docket/models/recurring_acquisition_created_response.py +123 -0
- docket_client-0.3.2/docket/models/recurring_acquisition_detail_response.py +105 -0
- docket_client-0.3.2/docket/models/recurring_acquisition_response.py +326 -0
- docket_client-0.3.2/docket/models/report_run_outcome_request.py +89 -0
- docket_client-0.3.2/docket/models/resolution_mode.py +10 -0
- docket_client-0.3.2/docket/models/resolved_settings.py +73 -0
- docket_client-0.3.2/docket/models/role_assignment_response.py +157 -0
- docket_client-0.3.2/docket/models/role_origin.py +10 -0
- docket_client-0.3.2/docket/models/role_source_kind.py +10 -0
- docket_client-0.3.2/docket/models/run_origin.py +9 -0
- docket_client-0.3.2/docket/models/run_outcome.py +9 -0
- docket_client-0.3.2/docket/models/run_response.py +181 -0
- docket_client-0.3.2/docket/models/run_settings_snapshot.py +72 -0
- docket_client-0.3.2/docket/models/run_start_response.py +91 -0
- docket_client-0.3.2/docket/models/run_start_response_settings.py +65 -0
- docket_client-0.3.2/docket/models/run_status.py +11 -0
- docket_client-0.3.2/docket/models/scheduled_acquisition_edit_preview_response.py +150 -0
- docket_client-0.3.2/docket/models/scheduled_acquisition_response.py +366 -0
- docket_client-0.3.2/docket/models/set_planning_status_request.py +90 -0
- docket_client-0.3.2/docket/models/settings_selector.py +138 -0
- docket_client-0.3.2/docket/models/skipped_occurrence.py +85 -0
- docket_client-0.3.2/docket/models/split_preview_response.py +129 -0
- docket_client-0.3.2/docket/models/split_recurring_acquisition_request.py +261 -0
- docket_client-0.3.2/docket/models/split_recurring_acquisition_response.py +159 -0
- docket_client-0.3.2/docket/models/start_run_request.py +73 -0
- docket_client-0.3.2/docket/models/subject_lookup_response.py +149 -0
- docket_client-0.3.2/docket/models/subject_response.py +128 -0
- docket_client-0.3.2/docket/models/sync_counts.py +80 -0
- docket_client-0.3.2/docket/models/sync_response.py +81 -0
- docket_client-0.3.2/docket/models/template_response.py +302 -0
- docket_client-0.3.2/docket/models/update_scheduled_acquisition_request.py +235 -0
- docket_client-0.3.2/docket/models/update_template_request.py +279 -0
- docket_client-0.3.2/docket/models/weekday.py +14 -0
- docket_client-0.3.2/docket/types.py +54 -0
- docket_client-0.3.2/docket_auth/__init__.py +239 -0
- docket_client-0.3.2/docket_mcp/__init__.py +6 -0
- docket_client-0.3.2/docket_mcp/api.py +207 -0
- docket_client-0.3.2/docket_mcp/config.py +57 -0
- docket_client-0.3.2/docket_mcp/server.py +78 -0
- docket_client-0.3.2/docket_mcp/signin.py +155 -0
- docket_client-0.3.2/docket_mcp/slots.py +80 -0
- docket_client-0.3.2/docket_mcp/times.py +160 -0
- docket_client-0.3.2/docket_mcp/tools.py +1202 -0
- docket_client-0.3.2/examples/downstream_usage.py +193 -0
- docket_client-0.3.2/pyproject.toml +50 -0
- docket_client-0.3.2/tests/docs_fake.py +282 -0
- docket_client-0.3.2/tests/fake_docket.py +161 -0
- docket_client-0.3.2/tests/test_docket_auth.py +173 -0
- docket_client-0.3.2/tests/test_docs_snippets.py +127 -0
- docket_client-0.3.2/tests/test_docs_tools.py +89 -0
- docket_client-0.3.2/tests/test_mcp_integration.py +173 -0
- docket_client-0.3.2/tests/test_mcp_review.py +483 -0
- docket_client-0.3.2/tests/test_mcp_stdio.py +113 -0
- docket_client-0.3.2/tests/test_mcp_times.py +188 -0
- docket_client-0.3.2/tests/test_mcp_tools.py +915 -0
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
__pycache__/
|
|
2
|
+
build/
|
|
3
|
+
dist/
|
|
4
|
+
*.egg-info/
|
|
5
|
+
.pytest_cache/
|
|
6
|
+
|
|
7
|
+
# pyenv
|
|
8
|
+
.python-version
|
|
9
|
+
|
|
10
|
+
# Environments
|
|
11
|
+
.env
|
|
12
|
+
.venv
|
|
13
|
+
|
|
14
|
+
# mypy
|
|
15
|
+
.mypy_cache/
|
|
16
|
+
.dmypy.json
|
|
17
|
+
dmypy.json
|
|
18
|
+
|
|
19
|
+
# JetBrains
|
|
20
|
+
.idea/
|
|
21
|
+
|
|
22
|
+
/coverage.xml
|
|
23
|
+
/.coverage
|
|
24
|
+
|
|
25
|
+
# ruff cache — generated during openapi-python-client runs
|
|
26
|
+
.ruff_cache/
|
|
@@ -0,0 +1,233 @@
|
|
|
1
|
+
Metadata-Version: 2.5
|
|
2
|
+
Name: docket-client
|
|
3
|
+
Version: 0.3.2
|
|
4
|
+
Summary: Typed Python client for the docket scheduling API
|
|
5
|
+
Project-URL: Homepage, https://github.com/AllenNeuralDynamics/docket
|
|
6
|
+
Project-URL: Repository, https://github.com/AllenNeuralDynamics/docket
|
|
7
|
+
Project-URL: Bug Tracker, https://github.com/AllenNeuralDynamics/docket/issues
|
|
8
|
+
Project-URL: Changelog, https://github.com/AllenNeuralDynamics/docket/releases
|
|
9
|
+
Author: Allen Institute for Neural Dynamics
|
|
10
|
+
License-Expression: MIT
|
|
11
|
+
Classifier: Development Status :: 3 - Alpha
|
|
12
|
+
Classifier: Intended Audience :: Developers
|
|
13
|
+
Classifier: Intended Audience :: Science/Research
|
|
14
|
+
Classifier: Operating System :: OS Independent
|
|
15
|
+
Classifier: Programming Language :: Python :: 3
|
|
16
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
17
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
18
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
19
|
+
Classifier: Topic :: Scientific/Engineering
|
|
20
|
+
Requires-Python: >=3.11
|
|
21
|
+
Requires-Dist: attrs>=22.2.0
|
|
22
|
+
Requires-Dist: httpx<0.29.0,>=0.23.1
|
|
23
|
+
Provides-Extra: auth
|
|
24
|
+
Requires-Dist: msal<2,>=1.31; extra == 'auth'
|
|
25
|
+
Provides-Extra: mcp
|
|
26
|
+
Requires-Dist: mcp<2,>=1.30; extra == 'mcp'
|
|
27
|
+
Requires-Dist: msal<2,>=1.31; extra == 'mcp'
|
|
28
|
+
Requires-Dist: tzdata>=2024.1; (sys_platform == 'win32') and extra == 'mcp'
|
|
29
|
+
Requires-Dist: tzlocal<6,>=5; extra == 'mcp'
|
|
30
|
+
Description-Content-Type: text/markdown
|
|
31
|
+
|
|
32
|
+
# docket
|
|
33
|
+
|
|
34
|
+
A typed Python client for the **docket** scheduling API.
|
|
35
|
+
|
|
36
|
+
## Installation
|
|
37
|
+
|
|
38
|
+
```bash
|
|
39
|
+
pip install docket-client
|
|
40
|
+
# the unreleased version, from the repository:
|
|
41
|
+
pip install "docket-client @ git+https://github.com/AllenNeuralDynamics/docket#subdirectory=client"
|
|
42
|
+
# or, from the repo root during development:
|
|
43
|
+
pip install ./client
|
|
44
|
+
```
|
|
45
|
+
|
|
46
|
+
## Usage
|
|
47
|
+
|
|
48
|
+
```python
|
|
49
|
+
from docket import Client
|
|
50
|
+
|
|
51
|
+
client = Client(base_url="http://localhost:8001")
|
|
52
|
+
```
|
|
53
|
+
|
|
54
|
+
For authenticated endpoints use `AuthenticatedClient`:
|
|
55
|
+
|
|
56
|
+
```python
|
|
57
|
+
from docket import AuthenticatedClient
|
|
58
|
+
|
|
59
|
+
client = AuthenticatedClient(base_url="https://api.example.com", token="SuperSecretToken")
|
|
60
|
+
```
|
|
61
|
+
|
|
62
|
+
Call any endpoint:
|
|
63
|
+
|
|
64
|
+
```python
|
|
65
|
+
from docket.api.scheduled_acquisitions import list_active_acquisitions
|
|
66
|
+
|
|
67
|
+
sessions = list_active_acquisitions.sync(
|
|
68
|
+
client=client,
|
|
69
|
+
instrument_id="BEH.B-Box1",
|
|
70
|
+
before_minutes=15,
|
|
71
|
+
effective_status=["scheduled", "ongoing"],
|
|
72
|
+
)
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
Every endpoint module exposes four variants:
|
|
76
|
+
|
|
77
|
+
| Function | Behaviour |
|
|
78
|
+
| --- | --- |
|
|
79
|
+
| `sync` | Blocking — returns the parsed response body or `None` |
|
|
80
|
+
| `sync_detailed` | Blocking — always returns a `Response` object with status code, headers, and `parsed` |
|
|
81
|
+
| `asyncio` | Async equivalent of `sync` |
|
|
82
|
+
| `asyncio_detailed` | Async equivalent of `sync_detailed` |
|
|
83
|
+
|
|
84
|
+
See [examples/downstream_usage.py](examples/downstream_usage.py) for a
|
|
85
|
+
full end-to-end walkthrough.
|
|
86
|
+
|
|
87
|
+
## MCP server (`docket-mcp`)
|
|
88
|
+
|
|
89
|
+
`docket-mcp` lets an AI assistant (Claude Code, Claude Desktop, any MCP client) look at the
|
|
90
|
+
schedule and change it, through the same API as everyone else. It runs **locally over stdio**:
|
|
91
|
+
the client starts it on your machine, so it reaches Docket over your own network or VPN and
|
|
92
|
+
nothing new is hosted. It is the `docket_mcp` package here, next to `docket_auth`.
|
|
93
|
+
|
|
94
|
+
### Install
|
|
95
|
+
|
|
96
|
+
```bash
|
|
97
|
+
pip install "docket-client[mcp]"
|
|
98
|
+
# or as an isolated tool (puts `docket-mcp` on your PATH):
|
|
99
|
+
uv tool install "docket-client[mcp]"
|
|
100
|
+
# from a checkout:
|
|
101
|
+
uv tool install "./client[mcp]"
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
### Add it to your assistant
|
|
105
|
+
|
|
106
|
+
Claude Code:
|
|
107
|
+
|
|
108
|
+
```bash
|
|
109
|
+
claude mcp add docket -e DOCKET_API_URL=http://localhost:8001 -e DOCKET_TIME_ZONE=America/Los_Angeles -- docket-mcp
|
|
110
|
+
# with an API token (see "Sign-in"):
|
|
111
|
+
claude mcp add docket -e DOCKET_API_URL=https://docket.example.org -e DOCKET_API_TOKEN=dkt_... -- docket-mcp
|
|
112
|
+
# straight from a checkout, without installing:
|
|
113
|
+
claude mcp add docket -e DOCKET_API_URL=http://localhost:8001 -- uv run --project ./client --extra mcp docket-mcp
|
|
114
|
+
```
|
|
115
|
+
|
|
116
|
+
Claude Desktop (`claude_desktop_config.json`):
|
|
117
|
+
|
|
118
|
+
```json
|
|
119
|
+
{
|
|
120
|
+
"mcpServers": {
|
|
121
|
+
"docket": {
|
|
122
|
+
"command": "docket-mcp",
|
|
123
|
+
"env": {
|
|
124
|
+
"DOCKET_API_URL": "http://localhost:8001",
|
|
125
|
+
"DOCKET_TIME_ZONE": "America/Los_Angeles",
|
|
126
|
+
"DOCKET_API_TOKEN": "dkt_..."
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
```
|
|
132
|
+
|
|
133
|
+
If `docket-mcp` is not on the app's `PATH`, give its full path as `command`.
|
|
134
|
+
|
|
135
|
+
### Configuration
|
|
136
|
+
|
|
137
|
+
All through environment variables:
|
|
138
|
+
|
|
139
|
+
| Variable | Meaning |
|
|
140
|
+
| --- | --- |
|
|
141
|
+
| `DOCKET_API_URL` | The API's address. Default `http://localhost:8001`. A frontend origin works too (`https://docket.example.org` or `…/api`), with its URL prefix if it has one (`https://host/docket`). |
|
|
142
|
+
| `DOCKET_TIME_ZONE` | IANA zone for the local times you give and get back. Default: this machine's zone. A tool's `time_zone` argument overrides it. |
|
|
143
|
+
| `DOCKET_API_TOKEN` | A Docket API token (`dkt_…`). Checked **first**; works in Tokens and Entra mode. |
|
|
144
|
+
| `DOCKET_AUTH_CLIENT_ID`, `DOCKET_AUTH_SCOPE`, `DOCKET_AUTH_TENANT_ID` (or `DOCKET_AUTH_AUTHORITY`) | Entra sign-in when there is no API token: the SPA's public client id, `api://…/access_as_user`, and the tenant (or another OIDC authority, such as the mock provider). |
|
|
145
|
+
| `DOCKET_AUTH_CLIENT_SECRET` | With the three above: sign in as an application (client credentials) instead of as a person. |
|
|
146
|
+
| `DOCKET_AUTH_CACHE_PATH` | Where the person's token cache lives. Default `~/.docket/mcp-token-cache.json` (holds refresh tokens: protect it). |
|
|
147
|
+
|
|
148
|
+
### Sign-in
|
|
149
|
+
|
|
150
|
+
Reads are anonymous. The server asks `/api/v1/me` once for `auth_mode`, and only **writes** carry a token.
|
|
151
|
+
|
|
152
|
+
- `auth_mode: disabled` (the default Docket): nothing to set up and you are never asked to sign in.
|
|
153
|
+
- `auth_mode: tokens`: set `DOCKET_API_TOKEN`. Ask an admin for a token from **Settings > Access**. Without one, write tools say so.
|
|
154
|
+
- `auth_mode: entra`: set `DOCKET_API_TOKEN` too (simplest), or sign in as yourself. The first write prints a URL and a code to stderr **and** returns them as the tool's error text (some clients hide stderr); open the URL, enter the code, then run the tool again. The token is cached afterwards. Set `DOCKET_AUTH_CLIENT_SECRET` for an unattended application.
|
|
155
|
+
|
|
156
|
+
Tokens are never logged or returned by a tool. `whoami` shows your auth mode, caller, roles (and where each came from) and grants: as yourself when a credential is available without interaction (an API token, client credentials or a cached sign-in), otherwise as anonymous (`signed_in: false`). It never starts a sign-in.
|
|
157
|
+
|
|
158
|
+
The device-code token cache holds refresh tokens. It is created owner-only (`chmod 600`) on Linux and macOS; on Windows `chmod` is a no-op and the file relies on your user profile's ACL, so keep it there (the default is `~/.docket/`).
|
|
159
|
+
|
|
160
|
+
### Tools
|
|
161
|
+
|
|
162
|
+
| Read | |
|
|
163
|
+
| --- | --- |
|
|
164
|
+
| `list_rigs`, `list_projects` | what you can book, with optional `search` |
|
|
165
|
+
| `lookup_subject`, `lookup_person` | check an id or username exists |
|
|
166
|
+
| `get_schedule` | sessions between two dates (rig, subject, person, archived filters) |
|
|
167
|
+
| `get_acquisition` | one session in full: people, notes, resolved settings, runs |
|
|
168
|
+
| `find_free_slots` | gaps on a rig long enough for a session, within daily bounds |
|
|
169
|
+
| `list_series`, `get_series` | recurring series and their rules |
|
|
170
|
+
| `list_templates`, `list_settings`, `list_runs`, `whoami` | |
|
|
171
|
+
|
|
172
|
+
| Write (all take `dry_run`, default **true**) | |
|
|
173
|
+
| --- | --- |
|
|
174
|
+
| `schedule_acquisition` | book one session (optionally from a template) |
|
|
175
|
+
| `move_acquisition` | change start, length or rig |
|
|
176
|
+
| `archive_acquisition` | archive a session (nothing is ever hard-deleted) |
|
|
177
|
+
| `create_series` | a finite daily/weekly series |
|
|
178
|
+
| `edit_series_from` | change a series from a date on (the old one ends, a new one starts) |
|
|
179
|
+
| `archive_series` | archive a series, keeping or archiving its upcoming sessions |
|
|
180
|
+
| `mark_outcome` | record succeeded / failed / cancelled by hand |
|
|
181
|
+
|
|
182
|
+
Not in v1: pushing settings, syncing vocabulary, managing templates and roles.
|
|
183
|
+
|
|
184
|
+
### Dry runs
|
|
185
|
+
|
|
186
|
+
Every write tool previews by default and changes nothing: it returns what would happen,
|
|
187
|
+
including overlap warnings, skipped (daylight-saving) dates and which sessions a series edit
|
|
188
|
+
would replace or keep. The tool descriptions tell the assistant to show you the preview and
|
|
189
|
+
repeat the call with `dry_run=false` only once you agree. Series and moves use the server's own
|
|
190
|
+
preview endpoints; for a single session the API has none, so the preview checks the schedule
|
|
191
|
+
itself with the server's overlap rule (same rig only; the same subject on another rig is listed
|
|
192
|
+
as `advisory`) and the server checks again when it creates it.
|
|
193
|
+
|
|
194
|
+
Each preview returns what the confirmation needs, under `confirm_with`: the `expected_version`
|
|
195
|
+
of what it looked at (moves, archives, outcomes, series edits and archives) and an
|
|
196
|
+
`idempotency_key` (new sessions, series and series edits). Repeat the call with
|
|
197
|
+
`dry_run=false` and those values. If the session or series changed in between, the call is
|
|
198
|
+
refused with "changed since your preview; preview again" and nothing is written. A retry
|
|
199
|
+
after a timeout with the same key cannot book or create twice.
|
|
200
|
+
|
|
201
|
+
### Times
|
|
202
|
+
|
|
203
|
+
Give local wall-clock times such as `2026-03-08T09:30`, never offsets. Results show the local
|
|
204
|
+
time (with its offset) and UTC. A time that does not exist (a spring-forward gap) is refused;
|
|
205
|
+
a repeated one (fall back) takes the first occurrence and says so.
|
|
206
|
+
|
|
207
|
+
### Example prompts
|
|
208
|
+
|
|
209
|
+
- "What is on rig `BEH.A` next week, and which afternoons are free for a 90-minute session?"
|
|
210
|
+
- "Book subject 812345 on `BEH.A` under project `Vision` tomorrow at 10:00 for an hour, with me as experimenter." (it previews first)
|
|
211
|
+
- "Move session 412 to Thursday at 14:00."
|
|
212
|
+
- "Set up a weekly series, Mondays and Thursdays at 09:00 for eight sessions, for subject 812345."
|
|
213
|
+
- "From 2026-11-02, shift that series to 10:30." / "Cancel the rest of series 17 but keep what already ran."
|
|
214
|
+
- "Did anything fail on the FIP rigs this week?"
|
|
215
|
+
|
|
216
|
+
### Developing
|
|
217
|
+
|
|
218
|
+
```bash
|
|
219
|
+
uv sync --group dev
|
|
220
|
+
uv run pytest client/tests # unit tests + the stdio smoke test
|
|
221
|
+
uv run pytest client/tests -m integration # schedule -> move -> archive on a real server
|
|
222
|
+
```
|
|
223
|
+
|
|
224
|
+
The integration test builds the server image and starts its own Compose project
|
|
225
|
+
(`docket-mcp-it`, API on port 8020, static vocabulary, nothing from the institute) and removes
|
|
226
|
+
it afterwards; set `DOCKET_IT_URL` to use a server that is already running instead.
|
|
227
|
+
|
|
228
|
+
## Building / publishing
|
|
229
|
+
|
|
230
|
+
```bash
|
|
231
|
+
# from the repo root
|
|
232
|
+
uv build --package docket-client # → dist/docket_client-*.whl
|
|
233
|
+
```
|
|
@@ -0,0 +1,202 @@
|
|
|
1
|
+
# docket
|
|
2
|
+
|
|
3
|
+
A typed Python client for the **docket** scheduling API.
|
|
4
|
+
|
|
5
|
+
## Installation
|
|
6
|
+
|
|
7
|
+
```bash
|
|
8
|
+
pip install docket-client
|
|
9
|
+
# the unreleased version, from the repository:
|
|
10
|
+
pip install "docket-client @ git+https://github.com/AllenNeuralDynamics/docket#subdirectory=client"
|
|
11
|
+
# or, from the repo root during development:
|
|
12
|
+
pip install ./client
|
|
13
|
+
```
|
|
14
|
+
|
|
15
|
+
## Usage
|
|
16
|
+
|
|
17
|
+
```python
|
|
18
|
+
from docket import Client
|
|
19
|
+
|
|
20
|
+
client = Client(base_url="http://localhost:8001")
|
|
21
|
+
```
|
|
22
|
+
|
|
23
|
+
For authenticated endpoints use `AuthenticatedClient`:
|
|
24
|
+
|
|
25
|
+
```python
|
|
26
|
+
from docket import AuthenticatedClient
|
|
27
|
+
|
|
28
|
+
client = AuthenticatedClient(base_url="https://api.example.com", token="SuperSecretToken")
|
|
29
|
+
```
|
|
30
|
+
|
|
31
|
+
Call any endpoint:
|
|
32
|
+
|
|
33
|
+
```python
|
|
34
|
+
from docket.api.scheduled_acquisitions import list_active_acquisitions
|
|
35
|
+
|
|
36
|
+
sessions = list_active_acquisitions.sync(
|
|
37
|
+
client=client,
|
|
38
|
+
instrument_id="BEH.B-Box1",
|
|
39
|
+
before_minutes=15,
|
|
40
|
+
effective_status=["scheduled", "ongoing"],
|
|
41
|
+
)
|
|
42
|
+
```
|
|
43
|
+
|
|
44
|
+
Every endpoint module exposes four variants:
|
|
45
|
+
|
|
46
|
+
| Function | Behaviour |
|
|
47
|
+
| --- | --- |
|
|
48
|
+
| `sync` | Blocking — returns the parsed response body or `None` |
|
|
49
|
+
| `sync_detailed` | Blocking — always returns a `Response` object with status code, headers, and `parsed` |
|
|
50
|
+
| `asyncio` | Async equivalent of `sync` |
|
|
51
|
+
| `asyncio_detailed` | Async equivalent of `sync_detailed` |
|
|
52
|
+
|
|
53
|
+
See [examples/downstream_usage.py](examples/downstream_usage.py) for a
|
|
54
|
+
full end-to-end walkthrough.
|
|
55
|
+
|
|
56
|
+
## MCP server (`docket-mcp`)
|
|
57
|
+
|
|
58
|
+
`docket-mcp` lets an AI assistant (Claude Code, Claude Desktop, any MCP client) look at the
|
|
59
|
+
schedule and change it, through the same API as everyone else. It runs **locally over stdio**:
|
|
60
|
+
the client starts it on your machine, so it reaches Docket over your own network or VPN and
|
|
61
|
+
nothing new is hosted. It is the `docket_mcp` package here, next to `docket_auth`.
|
|
62
|
+
|
|
63
|
+
### Install
|
|
64
|
+
|
|
65
|
+
```bash
|
|
66
|
+
pip install "docket-client[mcp]"
|
|
67
|
+
# or as an isolated tool (puts `docket-mcp` on your PATH):
|
|
68
|
+
uv tool install "docket-client[mcp]"
|
|
69
|
+
# from a checkout:
|
|
70
|
+
uv tool install "./client[mcp]"
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
### Add it to your assistant
|
|
74
|
+
|
|
75
|
+
Claude Code:
|
|
76
|
+
|
|
77
|
+
```bash
|
|
78
|
+
claude mcp add docket -e DOCKET_API_URL=http://localhost:8001 -e DOCKET_TIME_ZONE=America/Los_Angeles -- docket-mcp
|
|
79
|
+
# with an API token (see "Sign-in"):
|
|
80
|
+
claude mcp add docket -e DOCKET_API_URL=https://docket.example.org -e DOCKET_API_TOKEN=dkt_... -- docket-mcp
|
|
81
|
+
# straight from a checkout, without installing:
|
|
82
|
+
claude mcp add docket -e DOCKET_API_URL=http://localhost:8001 -- uv run --project ./client --extra mcp docket-mcp
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
Claude Desktop (`claude_desktop_config.json`):
|
|
86
|
+
|
|
87
|
+
```json
|
|
88
|
+
{
|
|
89
|
+
"mcpServers": {
|
|
90
|
+
"docket": {
|
|
91
|
+
"command": "docket-mcp",
|
|
92
|
+
"env": {
|
|
93
|
+
"DOCKET_API_URL": "http://localhost:8001",
|
|
94
|
+
"DOCKET_TIME_ZONE": "America/Los_Angeles",
|
|
95
|
+
"DOCKET_API_TOKEN": "dkt_..."
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
```
|
|
101
|
+
|
|
102
|
+
If `docket-mcp` is not on the app's `PATH`, give its full path as `command`.
|
|
103
|
+
|
|
104
|
+
### Configuration
|
|
105
|
+
|
|
106
|
+
All through environment variables:
|
|
107
|
+
|
|
108
|
+
| Variable | Meaning |
|
|
109
|
+
| --- | --- |
|
|
110
|
+
| `DOCKET_API_URL` | The API's address. Default `http://localhost:8001`. A frontend origin works too (`https://docket.example.org` or `…/api`), with its URL prefix if it has one (`https://host/docket`). |
|
|
111
|
+
| `DOCKET_TIME_ZONE` | IANA zone for the local times you give and get back. Default: this machine's zone. A tool's `time_zone` argument overrides it. |
|
|
112
|
+
| `DOCKET_API_TOKEN` | A Docket API token (`dkt_…`). Checked **first**; works in Tokens and Entra mode. |
|
|
113
|
+
| `DOCKET_AUTH_CLIENT_ID`, `DOCKET_AUTH_SCOPE`, `DOCKET_AUTH_TENANT_ID` (or `DOCKET_AUTH_AUTHORITY`) | Entra sign-in when there is no API token: the SPA's public client id, `api://…/access_as_user`, and the tenant (or another OIDC authority, such as the mock provider). |
|
|
114
|
+
| `DOCKET_AUTH_CLIENT_SECRET` | With the three above: sign in as an application (client credentials) instead of as a person. |
|
|
115
|
+
| `DOCKET_AUTH_CACHE_PATH` | Where the person's token cache lives. Default `~/.docket/mcp-token-cache.json` (holds refresh tokens: protect it). |
|
|
116
|
+
|
|
117
|
+
### Sign-in
|
|
118
|
+
|
|
119
|
+
Reads are anonymous. The server asks `/api/v1/me` once for `auth_mode`, and only **writes** carry a token.
|
|
120
|
+
|
|
121
|
+
- `auth_mode: disabled` (the default Docket): nothing to set up and you are never asked to sign in.
|
|
122
|
+
- `auth_mode: tokens`: set `DOCKET_API_TOKEN`. Ask an admin for a token from **Settings > Access**. Without one, write tools say so.
|
|
123
|
+
- `auth_mode: entra`: set `DOCKET_API_TOKEN` too (simplest), or sign in as yourself. The first write prints a URL and a code to stderr **and** returns them as the tool's error text (some clients hide stderr); open the URL, enter the code, then run the tool again. The token is cached afterwards. Set `DOCKET_AUTH_CLIENT_SECRET` for an unattended application.
|
|
124
|
+
|
|
125
|
+
Tokens are never logged or returned by a tool. `whoami` shows your auth mode, caller, roles (and where each came from) and grants: as yourself when a credential is available without interaction (an API token, client credentials or a cached sign-in), otherwise as anonymous (`signed_in: false`). It never starts a sign-in.
|
|
126
|
+
|
|
127
|
+
The device-code token cache holds refresh tokens. It is created owner-only (`chmod 600`) on Linux and macOS; on Windows `chmod` is a no-op and the file relies on your user profile's ACL, so keep it there (the default is `~/.docket/`).
|
|
128
|
+
|
|
129
|
+
### Tools
|
|
130
|
+
|
|
131
|
+
| Read | |
|
|
132
|
+
| --- | --- |
|
|
133
|
+
| `list_rigs`, `list_projects` | what you can book, with optional `search` |
|
|
134
|
+
| `lookup_subject`, `lookup_person` | check an id or username exists |
|
|
135
|
+
| `get_schedule` | sessions between two dates (rig, subject, person, archived filters) |
|
|
136
|
+
| `get_acquisition` | one session in full: people, notes, resolved settings, runs |
|
|
137
|
+
| `find_free_slots` | gaps on a rig long enough for a session, within daily bounds |
|
|
138
|
+
| `list_series`, `get_series` | recurring series and their rules |
|
|
139
|
+
| `list_templates`, `list_settings`, `list_runs`, `whoami` | |
|
|
140
|
+
|
|
141
|
+
| Write (all take `dry_run`, default **true**) | |
|
|
142
|
+
| --- | --- |
|
|
143
|
+
| `schedule_acquisition` | book one session (optionally from a template) |
|
|
144
|
+
| `move_acquisition` | change start, length or rig |
|
|
145
|
+
| `archive_acquisition` | archive a session (nothing is ever hard-deleted) |
|
|
146
|
+
| `create_series` | a finite daily/weekly series |
|
|
147
|
+
| `edit_series_from` | change a series from a date on (the old one ends, a new one starts) |
|
|
148
|
+
| `archive_series` | archive a series, keeping or archiving its upcoming sessions |
|
|
149
|
+
| `mark_outcome` | record succeeded / failed / cancelled by hand |
|
|
150
|
+
|
|
151
|
+
Not in v1: pushing settings, syncing vocabulary, managing templates and roles.
|
|
152
|
+
|
|
153
|
+
### Dry runs
|
|
154
|
+
|
|
155
|
+
Every write tool previews by default and changes nothing: it returns what would happen,
|
|
156
|
+
including overlap warnings, skipped (daylight-saving) dates and which sessions a series edit
|
|
157
|
+
would replace or keep. The tool descriptions tell the assistant to show you the preview and
|
|
158
|
+
repeat the call with `dry_run=false` only once you agree. Series and moves use the server's own
|
|
159
|
+
preview endpoints; for a single session the API has none, so the preview checks the schedule
|
|
160
|
+
itself with the server's overlap rule (same rig only; the same subject on another rig is listed
|
|
161
|
+
as `advisory`) and the server checks again when it creates it.
|
|
162
|
+
|
|
163
|
+
Each preview returns what the confirmation needs, under `confirm_with`: the `expected_version`
|
|
164
|
+
of what it looked at (moves, archives, outcomes, series edits and archives) and an
|
|
165
|
+
`idempotency_key` (new sessions, series and series edits). Repeat the call with
|
|
166
|
+
`dry_run=false` and those values. If the session or series changed in between, the call is
|
|
167
|
+
refused with "changed since your preview; preview again" and nothing is written. A retry
|
|
168
|
+
after a timeout with the same key cannot book or create twice.
|
|
169
|
+
|
|
170
|
+
### Times
|
|
171
|
+
|
|
172
|
+
Give local wall-clock times such as `2026-03-08T09:30`, never offsets. Results show the local
|
|
173
|
+
time (with its offset) and UTC. A time that does not exist (a spring-forward gap) is refused;
|
|
174
|
+
a repeated one (fall back) takes the first occurrence and says so.
|
|
175
|
+
|
|
176
|
+
### Example prompts
|
|
177
|
+
|
|
178
|
+
- "What is on rig `BEH.A` next week, and which afternoons are free for a 90-minute session?"
|
|
179
|
+
- "Book subject 812345 on `BEH.A` under project `Vision` tomorrow at 10:00 for an hour, with me as experimenter." (it previews first)
|
|
180
|
+
- "Move session 412 to Thursday at 14:00."
|
|
181
|
+
- "Set up a weekly series, Mondays and Thursdays at 09:00 for eight sessions, for subject 812345."
|
|
182
|
+
- "From 2026-11-02, shift that series to 10:30." / "Cancel the rest of series 17 but keep what already ran."
|
|
183
|
+
- "Did anything fail on the FIP rigs this week?"
|
|
184
|
+
|
|
185
|
+
### Developing
|
|
186
|
+
|
|
187
|
+
```bash
|
|
188
|
+
uv sync --group dev
|
|
189
|
+
uv run pytest client/tests # unit tests + the stdio smoke test
|
|
190
|
+
uv run pytest client/tests -m integration # schedule -> move -> archive on a real server
|
|
191
|
+
```
|
|
192
|
+
|
|
193
|
+
The integration test builds the server image and starts its own Compose project
|
|
194
|
+
(`docket-mcp-it`, API on port 8020, static vocabulary, nothing from the institute) and removes
|
|
195
|
+
it afterwards; set `DOCKET_IT_URL` to use a server that is already running instead.
|
|
196
|
+
|
|
197
|
+
## Building / publishing
|
|
198
|
+
|
|
199
|
+
```bash
|
|
200
|
+
# from the repo root
|
|
201
|
+
uv build --package docket-client # → dist/docket_client-*.whl
|
|
202
|
+
```
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"""Contains methods for accessing the API"""
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"""Contains endpoint functions for accessing the API"""
|
|
@@ -0,0 +1,193 @@
|
|
|
1
|
+
from http import HTTPStatus
|
|
2
|
+
from typing import Any, cast
|
|
3
|
+
from urllib.parse import quote
|
|
4
|
+
|
|
5
|
+
import httpx
|
|
6
|
+
|
|
7
|
+
from ...client import AuthenticatedClient, Client
|
|
8
|
+
from ...types import Response, UNSET
|
|
9
|
+
from ... import errors
|
|
10
|
+
|
|
11
|
+
from ...models.add_principal_request import AddPrincipalRequest
|
|
12
|
+
from ...models.http_validation_problem_details import HttpValidationProblemDetails
|
|
13
|
+
from ...models.principal_response import PrincipalResponse
|
|
14
|
+
from ...models.problem_details import ProblemDetails
|
|
15
|
+
from typing import cast
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
def _get_kwargs(
|
|
19
|
+
*,
|
|
20
|
+
body: AddPrincipalRequest,
|
|
21
|
+
) -> dict[str, Any]:
|
|
22
|
+
headers: dict[str, Any] = {}
|
|
23
|
+
|
|
24
|
+
_kwargs: dict[str, Any] = {
|
|
25
|
+
"method": "post",
|
|
26
|
+
"url": "/api/v1/access/principals",
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
_kwargs["json"] = body.to_dict()
|
|
30
|
+
|
|
31
|
+
headers["Content-Type"] = "application/json"
|
|
32
|
+
|
|
33
|
+
_kwargs["headers"] = headers
|
|
34
|
+
return _kwargs
|
|
35
|
+
|
|
36
|
+
|
|
37
|
+
def _parse_response(
|
|
38
|
+
*, client: AuthenticatedClient | Client, response: httpx.Response
|
|
39
|
+
) -> HttpValidationProblemDetails | PrincipalResponse | ProblemDetails | None:
|
|
40
|
+
if response.status_code == 201:
|
|
41
|
+
response_201 = PrincipalResponse.from_dict(response.json())
|
|
42
|
+
|
|
43
|
+
return response_201
|
|
44
|
+
|
|
45
|
+
if response.status_code == 401:
|
|
46
|
+
response_401 = ProblemDetails.from_dict(response.json())
|
|
47
|
+
|
|
48
|
+
return response_401
|
|
49
|
+
|
|
50
|
+
if response.status_code == 403:
|
|
51
|
+
response_403 = ProblemDetails.from_dict(response.json())
|
|
52
|
+
|
|
53
|
+
return response_403
|
|
54
|
+
|
|
55
|
+
if response.status_code == 409:
|
|
56
|
+
response_409 = ProblemDetails.from_dict(response.json())
|
|
57
|
+
|
|
58
|
+
return response_409
|
|
59
|
+
|
|
60
|
+
if response.status_code == 422:
|
|
61
|
+
response_422 = HttpValidationProblemDetails.from_dict(response.json())
|
|
62
|
+
|
|
63
|
+
return response_422
|
|
64
|
+
|
|
65
|
+
if client.raise_on_unexpected_status:
|
|
66
|
+
raise errors.UnexpectedStatus(response.status_code, response.content)
|
|
67
|
+
else:
|
|
68
|
+
return None
|
|
69
|
+
|
|
70
|
+
|
|
71
|
+
def _build_response(
|
|
72
|
+
*, client: AuthenticatedClient | Client, response: httpx.Response
|
|
73
|
+
) -> Response[HttpValidationProblemDetails | PrincipalResponse | ProblemDetails]:
|
|
74
|
+
return Response(
|
|
75
|
+
status_code=HTTPStatus(response.status_code),
|
|
76
|
+
content=response.content,
|
|
77
|
+
headers=response.headers,
|
|
78
|
+
parsed=_parse_response(client=client, response=response),
|
|
79
|
+
)
|
|
80
|
+
|
|
81
|
+
|
|
82
|
+
def sync_detailed(
|
|
83
|
+
*,
|
|
84
|
+
client: AuthenticatedClient,
|
|
85
|
+
body: AddPrincipalRequest,
|
|
86
|
+
) -> Response[HttpValidationProblemDetails | PrincipalResponse | ProblemDetails]:
|
|
87
|
+
"""Register a principal by Entra object id before it has signed in (how rig applications with an Entra
|
|
88
|
+
registration are added). Admin only.
|
|
89
|
+
|
|
90
|
+
Args:
|
|
91
|
+
body (AddPrincipalRequest): Registers a principal before it has signed in (how rig
|
|
92
|
+
applications are added).
|
|
93
|
+
|
|
94
|
+
Raises:
|
|
95
|
+
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
|
|
96
|
+
httpx.TimeoutException: If the request takes longer than Client.timeout.
|
|
97
|
+
|
|
98
|
+
Returns:
|
|
99
|
+
Response[HttpValidationProblemDetails | PrincipalResponse | ProblemDetails]
|
|
100
|
+
"""
|
|
101
|
+
|
|
102
|
+
kwargs = _get_kwargs(
|
|
103
|
+
body=body,
|
|
104
|
+
)
|
|
105
|
+
|
|
106
|
+
response = client.get_httpx_client().request(
|
|
107
|
+
**kwargs,
|
|
108
|
+
)
|
|
109
|
+
|
|
110
|
+
return _build_response(client=client, response=response)
|
|
111
|
+
|
|
112
|
+
|
|
113
|
+
def sync(
|
|
114
|
+
*,
|
|
115
|
+
client: AuthenticatedClient,
|
|
116
|
+
body: AddPrincipalRequest,
|
|
117
|
+
) -> HttpValidationProblemDetails | PrincipalResponse | ProblemDetails | None:
|
|
118
|
+
"""Register a principal by Entra object id before it has signed in (how rig applications with an Entra
|
|
119
|
+
registration are added). Admin only.
|
|
120
|
+
|
|
121
|
+
Args:
|
|
122
|
+
body (AddPrincipalRequest): Registers a principal before it has signed in (how rig
|
|
123
|
+
applications are added).
|
|
124
|
+
|
|
125
|
+
Raises:
|
|
126
|
+
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
|
|
127
|
+
httpx.TimeoutException: If the request takes longer than Client.timeout.
|
|
128
|
+
|
|
129
|
+
Returns:
|
|
130
|
+
HttpValidationProblemDetails | PrincipalResponse | ProblemDetails
|
|
131
|
+
"""
|
|
132
|
+
|
|
133
|
+
return sync_detailed(
|
|
134
|
+
client=client,
|
|
135
|
+
body=body,
|
|
136
|
+
).parsed
|
|
137
|
+
|
|
138
|
+
|
|
139
|
+
async def asyncio_detailed(
|
|
140
|
+
*,
|
|
141
|
+
client: AuthenticatedClient,
|
|
142
|
+
body: AddPrincipalRequest,
|
|
143
|
+
) -> Response[HttpValidationProblemDetails | PrincipalResponse | ProblemDetails]:
|
|
144
|
+
"""Register a principal by Entra object id before it has signed in (how rig applications with an Entra
|
|
145
|
+
registration are added). Admin only.
|
|
146
|
+
|
|
147
|
+
Args:
|
|
148
|
+
body (AddPrincipalRequest): Registers a principal before it has signed in (how rig
|
|
149
|
+
applications are added).
|
|
150
|
+
|
|
151
|
+
Raises:
|
|
152
|
+
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
|
|
153
|
+
httpx.TimeoutException: If the request takes longer than Client.timeout.
|
|
154
|
+
|
|
155
|
+
Returns:
|
|
156
|
+
Response[HttpValidationProblemDetails | PrincipalResponse | ProblemDetails]
|
|
157
|
+
"""
|
|
158
|
+
|
|
159
|
+
kwargs = _get_kwargs(
|
|
160
|
+
body=body,
|
|
161
|
+
)
|
|
162
|
+
|
|
163
|
+
response = await client.get_async_httpx_client().request(**kwargs)
|
|
164
|
+
|
|
165
|
+
return _build_response(client=client, response=response)
|
|
166
|
+
|
|
167
|
+
|
|
168
|
+
async def asyncio(
|
|
169
|
+
*,
|
|
170
|
+
client: AuthenticatedClient,
|
|
171
|
+
body: AddPrincipalRequest,
|
|
172
|
+
) -> HttpValidationProblemDetails | PrincipalResponse | ProblemDetails | None:
|
|
173
|
+
"""Register a principal by Entra object id before it has signed in (how rig applications with an Entra
|
|
174
|
+
registration are added). Admin only.
|
|
175
|
+
|
|
176
|
+
Args:
|
|
177
|
+
body (AddPrincipalRequest): Registers a principal before it has signed in (how rig
|
|
178
|
+
applications are added).
|
|
179
|
+
|
|
180
|
+
Raises:
|
|
181
|
+
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
|
|
182
|
+
httpx.TimeoutException: If the request takes longer than Client.timeout.
|
|
183
|
+
|
|
184
|
+
Returns:
|
|
185
|
+
HttpValidationProblemDetails | PrincipalResponse | ProblemDetails
|
|
186
|
+
"""
|
|
187
|
+
|
|
188
|
+
return (
|
|
189
|
+
await asyncio_detailed(
|
|
190
|
+
client=client,
|
|
191
|
+
body=body,
|
|
192
|
+
)
|
|
193
|
+
).parsed
|