msdev 0.10.0__tar.gz → 0.10.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.
Files changed (89) hide show
  1. {msdev-0.10.0 → msdev-0.10.1}/PKG-INFO +66 -121
  2. {msdev-0.10.0 → msdev-0.10.1}/README.md +64 -120
  3. {msdev-0.10.0 → msdev-0.10.1}/pyproject.toml +2 -1
  4. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/__init__.py +1 -1
  5. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/cli.py +148 -485
  6. msdev-0.10.1/src/msdev/core/__init__.py +1 -0
  7. msdev-0.10.1/src/msdev/core/compat.py +182 -0
  8. msdev-0.10.1/src/msdev/core/config.py +373 -0
  9. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/container_helper.py +13 -6
  10. msdev-0.10.1/src/msdev/core/env_transfer.py +364 -0
  11. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/host_mutations.py +1 -1
  12. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/limits.py +2 -2
  13. msdev-0.10.1/src/msdev/core/local_rpc.py +85 -0
  14. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/resources.py +4 -2
  15. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/services/__init__.py +10 -22
  16. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/services/capabilities.py +3 -23
  17. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/services/context.py +0 -2
  18. msdev-0.10.1/src/msdev/core/services/environment.py +331 -0
  19. msdev-0.10.1/src/msdev/core/ssh_tunnel.py +552 -0
  20. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/stream_server.py +14 -4
  21. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/stream_transport.py +21 -14
  22. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/transport.py +283 -88
  23. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/daemon.py +112 -176
  24. {msdev-0.10.0 → msdev-0.10.1}/src/msdev.egg-info/PKG-INFO +66 -121
  25. {msdev-0.10.0 → msdev-0.10.1}/src/msdev.egg-info/SOURCES.txt +11 -13
  26. {msdev-0.10.0 → msdev-0.10.1}/tests/test_cli.py +1 -303
  27. {msdev-0.10.0 → msdev-0.10.1}/tests/test_cli_only_architecture.py +4 -7
  28. msdev-0.10.1/tests/test_compat.py +45 -0
  29. {msdev-0.10.0 → msdev-0.10.1}/tests/test_config.py +82 -1
  30. {msdev-0.10.0 → msdev-0.10.1}/tests/test_daemon.py +76 -59
  31. {msdev-0.10.0 → msdev-0.10.1}/tests/test_daemon_container_stream.py +1 -0
  32. {msdev-0.10.0 → msdev-0.10.1}/tests/test_docker_stream_dispatch.py +7 -2
  33. msdev-0.10.1/tests/test_env_put_get_scenario.py +134 -0
  34. msdev-0.10.1/tests/test_env_read_write_scenario.py +134 -0
  35. msdev-0.10.1/tests/test_env_transfer.py +61 -0
  36. msdev-0.10.1/tests/test_exec_default_timeout_scenario.py +134 -0
  37. {msdev-0.10.0 → msdev-0.10.1}/tests/test_model_services.py +0 -2
  38. {msdev-0.10.0 → msdev-0.10.1}/tests/test_msdev_cli_skill.py +9 -9
  39. {msdev-0.10.0 → msdev-0.10.1}/tests/test_multiplex.py +12 -3
  40. msdev-0.10.1/tests/test_node_env_services.py +187 -0
  41. {msdev-0.10.0 → msdev-0.10.1}/tests/test_request_client.py +10 -4
  42. msdev-0.10.1/tests/test_ssh_tunnel.py +57 -0
  43. {msdev-0.10.0 → msdev-0.10.1}/tests/test_stream_server.py +10 -3
  44. {msdev-0.10.0 → msdev-0.10.1}/tests/test_stream_transport.py +9 -4
  45. {msdev-0.10.0 → msdev-0.10.1}/tests/test_target_exec_services.py +0 -3
  46. {msdev-0.10.0 → msdev-0.10.1}/tests/test_transport.py +210 -17
  47. msdev-0.10.1/tests/test_windows_local_scenario.py +87 -0
  48. msdev-0.10.0/src/msdev/core/__init__.py +0 -1
  49. msdev-0.10.0/src/msdev/core/config.py +0 -193
  50. msdev-0.10.0/src/msdev/core/services/environment.py +0 -84
  51. msdev-0.10.0/src/msdev/core/services/workspace.py +0 -567
  52. msdev-0.10.0/src/msdev/core/workspace/__init__.py +0 -43
  53. msdev-0.10.0/src/msdev/core/workspace/access.py +0 -1216
  54. msdev-0.10.0/src/msdev/core/workspace/client.py +0 -329
  55. msdev-0.10.0/src/msdev/core/workspace/paths.py +0 -65
  56. msdev-0.10.0/src/msdev/core/workspace/registry.py +0 -189
  57. msdev-0.10.0/src/msdev/session/__init__.py +0 -13
  58. msdev-0.10.0/src/msdev/session/export.py +0 -190
  59. msdev-0.10.0/src/msdev/session/log.py +0 -269
  60. msdev-0.10.0/tests/test_cli_session.py +0 -202
  61. msdev-0.10.0/tests/test_node_env_services.py +0 -63
  62. msdev-0.10.0/tests/test_workspace.py +0 -855
  63. msdev-0.10.0/tests/test_workspace_client.py +0 -321
  64. msdev-0.10.0/tests/test_workspace_services.py +0 -414
  65. {msdev-0.10.0 → msdev-0.10.1}/LICENSE +0 -0
  66. {msdev-0.10.0 → msdev-0.10.1}/setup.cfg +0 -0
  67. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/guides.py +0 -0
  68. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/helper_deploy.py +0 -0
  69. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/host_files.py +0 -0
  70. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/inventory.py +0 -0
  71. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/multiplex.py +0 -0
  72. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/request_client.py +0 -0
  73. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/services/execution.py +0 -0
  74. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/services/model.py +0 -0
  75. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/services/node.py +0 -0
  76. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/services/npu.py +0 -0
  77. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/services/results.py +0 -0
  78. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/stream_limits.py +0 -0
  79. {msdev-0.10.0 → msdev-0.10.1}/src/msdev/core/streamproto.py +0 -0
  80. {msdev-0.10.0 → msdev-0.10.1}/src/msdev.egg-info/dependency_links.txt +0 -0
  81. {msdev-0.10.0 → msdev-0.10.1}/src/msdev.egg-info/entry_points.txt +0 -0
  82. {msdev-0.10.0 → msdev-0.10.1}/src/msdev.egg-info/top_level.txt +0 -0
  83. {msdev-0.10.0 → msdev-0.10.1}/tests/test_container_helper.py +0 -0
  84. {msdev-0.10.0 → msdev-0.10.1}/tests/test_helper_deploy.py +0 -0
  85. {msdev-0.10.0 → msdev-0.10.1}/tests/test_inventory.py +0 -0
  86. {msdev-0.10.0 → msdev-0.10.1}/tests/test_model_cli.py +0 -0
  87. {msdev-0.10.0 → msdev-0.10.1}/tests/test_node_env_config.py +0 -0
  88. {msdev-0.10.0 → msdev-0.10.1}/tests/test_streamproto.py +0 -0
  89. {msdev-0.10.0 → msdev-0.10.1}/tests/test_target_guides.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: msdev
3
- Version: 0.10.0
3
+ Version: 0.10.1
4
4
  Summary: Portable nodes and execution environments for msModelSlim development
5
5
  Author: msModelSlim Agent Contributors
6
6
  License-Expression: MulanPSL-2.0
@@ -15,6 +15,7 @@ Classifier: Programming Language :: Python :: 3.11
15
15
  Classifier: Programming Language :: Python :: 3.12
16
16
  Classifier: Programming Language :: Python :: 3.13
17
17
  Classifier: Operating System :: MacOS
18
+ Classifier: Operating System :: Microsoft :: Windows
18
19
  Classifier: Operating System :: POSIX :: Linux
19
20
  Classifier: Topic :: Software Development :: Build Tools
20
21
  Requires-Python: >=3.10
@@ -32,7 +33,6 @@ The CLI is intentionally stateless:
32
33
 
33
34
  - Node-scoped NPU/model operations name `--node` or use `--all`;
34
35
  - execution names `--env`;
35
- - every workspace operation names the registered workspace;
36
36
  - no harness conversation binding or implicit current Env exists;
37
37
  - MCP is not part of the architecture.
38
38
 
@@ -47,6 +47,34 @@ msdev --help
47
47
 
48
48
  The package installs `msdev` and `msdevd`.
49
49
 
50
+ ## Windows client
51
+
52
+ The typical setup is a **Windows laptop talking to Linux Nodes** via OpenSSH
53
+ (`C:\Windows\System32\OpenSSH\ssh.exe`). Native Windows OpenSSH does not
54
+ implement ControlMaster multiplexing, so msdev:
55
+
56
+ - omits `ControlMaster`/`ControlPath` on Windows (override with
57
+ `MSDEV_SSH_CONTROL_MASTER=1` only if your SSH client actually supports mux);
58
+ - starts a persistent `ssh -L` LocalForward tunnel automatically on the first
59
+ RPC (same role as ControlMaster). Explicit `msdev node connect NODE` is
60
+ optional; disable persist with `MSDEV_SSH_LOCAL_FORWARD_PERSIST=0`;
61
+ - reuses that tunnel for captured RPC and default streaming `msdev exec`;
62
+ `env put`/`get` stay on scp/ssh streams (file bytes do not go through JSON RPC);
63
+ - hides SSH console windows (`CREATE_NO_WINDOW`) and kills process trees with
64
+ `taskkill /T` on timeout or cancel;
65
+ - serves a TCP loopback endpoint for local `msdevd` when this Python build has
66
+ no `AF_UNIX` sockets.
67
+
68
+ Install with `python -m pip install -e .`. `install-user.py` writes
69
+ `msdev.cmd` / `msdevd.cmd` under `%USERPROFILE%\.local\bin`.
70
+
71
+ Remote paths inside a Linux Env remain POSIX (`/srv/...`). Local `env put`/`get`
72
+ on Windows accept Windows absolute paths (`C:\...`).
73
+
74
+ Local `exec` on Windows wraps Conda with `conda run` and venvs with
75
+ `Scripts\activate.bat` (remote Linux Nodes still use POSIX `sh`/`bash` wrappers).
76
+ If `ssh` is not on PATH, msdev looks in `%SystemRoot%\System32\OpenSSH\`.
77
+
50
78
  ## Nodes and execution environments
51
79
 
52
80
  Register a host from `~/.ssh/config`:
@@ -107,6 +135,33 @@ msdev env add dev-122-vllm \
107
135
  --layer venv:/srv/project/.venv
108
136
  ```
109
137
 
138
+ ## File put, get, read, and write
139
+
140
+ Bulk transfer copies a local file into an Env filesystem, or fetches one back:
141
+
142
+ ```bash
143
+ msdev env put dev-122 ./config.yaml /srv/project/config.yaml
144
+ msdev env get dev-122 /srv/project/config.yaml --output ./config.yaml
145
+ msdev env get dev-122 /srv/project/config.yaml > ./config.yaml
146
+ ```
147
+
148
+ Editing uses content-oriented read/write. Paths inside the Env must be
149
+ absolute. Host Envs use direct filesystem copy locally and ``scp``/``ssh``
150
+ streams remotely. Docker Envs stage through the node with ``docker cp``.
151
+ File bytes never pass through JSON RPC.
152
+
153
+ ```bash
154
+ msdev env read dev-122 /srv/project/config.yaml
155
+ msdev env read dev-122 /srv/project/config.yaml --json
156
+ msdev env write dev-122 /srv/project/note.md --file /tmp/note.md
157
+ msdev env write dev-122 /srv/project/note.md < /tmp/note.md
158
+ msdev env write dev-122 /srv/project/note.md --file /tmp/note.md \
159
+ --expected-sha256 <digest>
160
+ ```
161
+
162
+ Read before replacing an existing file. `--expected-sha256` is compare-and-swap
163
+ replacement that refuses to overwrite a changed remote file.
164
+
110
165
  ## NPU inventory
111
166
 
112
167
  ```bash
@@ -130,8 +185,8 @@ msdev exec \
130
185
  -- python3 run.py
131
186
  ```
132
187
 
133
- `--timeout-seconds` defaults to 300, accepts any positive finite duration, and
134
- uses `-1` for no deadline. A positive timeout kills the complete command
188
+ `--timeout-seconds` defaults to `-1` (no deadline). Any positive finite duration
189
+ is also accepted. A positive timeout kills the complete command
135
190
  process group and returns exit code 124. Cancelling the local CLI closes the RPC
136
191
  connection, causing `msdevd` to kill and reap the remote process group. Finite
137
192
  SSH/Unix RPC deadlines include a short completion grace for output drain and
@@ -140,66 +195,6 @@ serialization.
140
195
  `--result-json` selects captured, non-streaming execution and prints one
141
196
  structured JSON result containing stdout and stderr.
142
197
 
143
- ## Remote workspaces
144
-
145
- A workspace gives a stable name to an Env and filesystem root:
146
-
147
- ```bash
148
- msdev workspace add project \
149
- --env dev-122 \
150
- --root /srv/project
151
-
152
- msdev workspace list
153
- msdev workspace inspect project
154
- ```
155
-
156
- Workspace operations are file- and Git-oriented. There is no
157
- `msdev workspace exec`; use `msdev exec --env ... --cwd ...` for commands.
158
-
159
- ### Read and inspect
160
-
161
- ```bash
162
- msdev workspace stat project README.md
163
- msdev workspace read project README.md
164
- msdev workspace read project weights.bin --output /tmp/weights.bin
165
- msdev workspace list project src --json
166
- msdev workspace glob project '**/*.py' --json
167
- msdev workspace search project 'TODO' src tests --json
168
- ```
169
-
170
- ### Write safely
171
-
172
- For non-trivial content, use stdin or `--file` rather than shell-escaped
173
- `--content`:
174
-
175
- ```bash
176
- msdev workspace write project docs/note.md < /tmp/note.md
177
- msdev workspace write project docs/note.md --file /tmp/note.md
178
- ```
179
-
180
- Compare-and-swap replacement prevents overwriting a changed remote file:
181
-
182
- ```bash
183
- msdev workspace apply-patch project docs/note.md \
184
- --file /tmp/note.md \
185
- --expected-sha256 <digest>
186
- ```
187
-
188
- Delete an explicit remote file:
189
-
190
- ```bash
191
- msdev workspace delete project docs/obsolete.md
192
- ```
193
-
194
- ### Git
195
-
196
- ```bash
197
- msdev workspace git-status project --result-json
198
- msdev workspace git-diff project --result-json -- --stat
199
- ```
200
-
201
- Git diff rejects options that can write files or invoke external diff helpers.
202
-
203
198
  ## Model inventory
204
199
 
205
200
  Examples:
@@ -216,59 +211,6 @@ msdev model audit --node dev-122
216
211
  Use `msdev model --help` and the individual subcommand help for register,
217
212
  update, replicas, refresh, verify, export, import, and rebind.
218
213
 
219
- ## Explicit CLI sessions and runbooks
220
-
221
- Create a session before a reproducible workflow:
222
-
223
- ```bash
224
- msdev session begin --name qwen3-quant --json
225
- ```
226
-
227
- Pass the returned ID explicitly or set it in a persistent terminal:
228
-
229
- ```bash
230
- export MSDEV_SESSION_ID=<session-id>
231
- ```
232
-
233
- Intent metadata is global and must appear before the subcommand:
234
-
235
- ```bash
236
- msdev \
237
- --session-id <session-id> \
238
- --intent-kind execution \
239
- --intent-summary 'Run Qwen3 quantization' \
240
- --intent-phase quantization \
241
- --intent-step-id quant-1 \
242
- exec --env dev-122 --timeout-seconds 1800 -- python3 quant.py
243
- ```
244
-
245
- Intent kinds:
246
-
247
- - `execution`: core reproduction step;
248
- - `verification`: optional confirmation;
249
- - `diagnostic`: troubleshooting, excluded from core steps;
250
- - `exploration`: discovery, excluded from core steps.
251
-
252
- Each invocation receives a unique `operation_id`. `session_id` groups CLI
253
- operations only; it never supplies a Node, Env, or workspace default.
254
-
255
- Logs are private JSONL files under:
256
-
257
- ```text
258
- ${XDG_STATE_HOME:-~/.local/state}/msdev/sessions/
259
- ```
260
-
261
- They retain sanitized logical arguments, preview, explicit resource, intent,
262
- exit code, and elapsed time. Command stdout/stderr and environment values are
263
- not duplicated into logs.
264
-
265
- ```bash
266
- msdev session list
267
- msdev session export --session-id <session-id> --output runbook.md
268
- msdev session export --latest --detail normal --output runbook.md
269
- msdev session export --input /path/to/session.jsonl --detail full
270
- ```
271
-
272
214
  ## Architecture
273
215
 
274
216
  ```text
@@ -276,15 +218,18 @@ msdev CLI
276
218
  -> typed core service
277
219
  -> UnixRpcTransport or SshRpcTransport
278
220
  -> per-user msdevd
279
- -> host/container command, workspace filesystem, NPU, or inventory
221
+ -> host/container command, env file transfer, NPU, or inventory
280
222
  ```
281
223
 
282
- Remote RPC responses and command output are bounded. Workspace paths are
283
- normalized under the registered root. Writes are atomic and support SHA-256
284
- compare-and-swap. Node/Env and workspace registries use locked atomic updates.
224
+ Remote RPC responses and command output are bounded. Node/Env registries use
225
+ locked atomic updates.
285
226
 
286
227
  ## Testing
287
228
 
288
229
  ```bash
289
230
  python3 -m unittest discover -s tests -v
290
231
  ```
232
+
233
+ Feature work must include at least one actual scenario test on the real
234
+ control path (`msdev` CLI → service → transport → `msdevd` → effect). Unit
235
+ tests alone are not sufficient.
@@ -8,7 +8,6 @@ The CLI is intentionally stateless:
8
8
 
9
9
  - Node-scoped NPU/model operations name `--node` or use `--all`;
10
10
  - execution names `--env`;
11
- - every workspace operation names the registered workspace;
12
11
  - no harness conversation binding or implicit current Env exists;
13
12
  - MCP is not part of the architecture.
14
13
 
@@ -23,6 +22,34 @@ msdev --help
23
22
 
24
23
  The package installs `msdev` and `msdevd`.
25
24
 
25
+ ## Windows client
26
+
27
+ The typical setup is a **Windows laptop talking to Linux Nodes** via OpenSSH
28
+ (`C:\Windows\System32\OpenSSH\ssh.exe`). Native Windows OpenSSH does not
29
+ implement ControlMaster multiplexing, so msdev:
30
+
31
+ - omits `ControlMaster`/`ControlPath` on Windows (override with
32
+ `MSDEV_SSH_CONTROL_MASTER=1` only if your SSH client actually supports mux);
33
+ - starts a persistent `ssh -L` LocalForward tunnel automatically on the first
34
+ RPC (same role as ControlMaster). Explicit `msdev node connect NODE` is
35
+ optional; disable persist with `MSDEV_SSH_LOCAL_FORWARD_PERSIST=0`;
36
+ - reuses that tunnel for captured RPC and default streaming `msdev exec`;
37
+ `env put`/`get` stay on scp/ssh streams (file bytes do not go through JSON RPC);
38
+ - hides SSH console windows (`CREATE_NO_WINDOW`) and kills process trees with
39
+ `taskkill /T` on timeout or cancel;
40
+ - serves a TCP loopback endpoint for local `msdevd` when this Python build has
41
+ no `AF_UNIX` sockets.
42
+
43
+ Install with `python -m pip install -e .`. `install-user.py` writes
44
+ `msdev.cmd` / `msdevd.cmd` under `%USERPROFILE%\.local\bin`.
45
+
46
+ Remote paths inside a Linux Env remain POSIX (`/srv/...`). Local `env put`/`get`
47
+ on Windows accept Windows absolute paths (`C:\...`).
48
+
49
+ Local `exec` on Windows wraps Conda with `conda run` and venvs with
50
+ `Scripts\activate.bat` (remote Linux Nodes still use POSIX `sh`/`bash` wrappers).
51
+ If `ssh` is not on PATH, msdev looks in `%SystemRoot%\System32\OpenSSH\`.
52
+
26
53
  ## Nodes and execution environments
27
54
 
28
55
  Register a host from `~/.ssh/config`:
@@ -83,6 +110,33 @@ msdev env add dev-122-vllm \
83
110
  --layer venv:/srv/project/.venv
84
111
  ```
85
112
 
113
+ ## File put, get, read, and write
114
+
115
+ Bulk transfer copies a local file into an Env filesystem, or fetches one back:
116
+
117
+ ```bash
118
+ msdev env put dev-122 ./config.yaml /srv/project/config.yaml
119
+ msdev env get dev-122 /srv/project/config.yaml --output ./config.yaml
120
+ msdev env get dev-122 /srv/project/config.yaml > ./config.yaml
121
+ ```
122
+
123
+ Editing uses content-oriented read/write. Paths inside the Env must be
124
+ absolute. Host Envs use direct filesystem copy locally and ``scp``/``ssh``
125
+ streams remotely. Docker Envs stage through the node with ``docker cp``.
126
+ File bytes never pass through JSON RPC.
127
+
128
+ ```bash
129
+ msdev env read dev-122 /srv/project/config.yaml
130
+ msdev env read dev-122 /srv/project/config.yaml --json
131
+ msdev env write dev-122 /srv/project/note.md --file /tmp/note.md
132
+ msdev env write dev-122 /srv/project/note.md < /tmp/note.md
133
+ msdev env write dev-122 /srv/project/note.md --file /tmp/note.md \
134
+ --expected-sha256 <digest>
135
+ ```
136
+
137
+ Read before replacing an existing file. `--expected-sha256` is compare-and-swap
138
+ replacement that refuses to overwrite a changed remote file.
139
+
86
140
  ## NPU inventory
87
141
 
88
142
  ```bash
@@ -106,8 +160,8 @@ msdev exec \
106
160
  -- python3 run.py
107
161
  ```
108
162
 
109
- `--timeout-seconds` defaults to 300, accepts any positive finite duration, and
110
- uses `-1` for no deadline. A positive timeout kills the complete command
163
+ `--timeout-seconds` defaults to `-1` (no deadline). Any positive finite duration
164
+ is also accepted. A positive timeout kills the complete command
111
165
  process group and returns exit code 124. Cancelling the local CLI closes the RPC
112
166
  connection, causing `msdevd` to kill and reap the remote process group. Finite
113
167
  SSH/Unix RPC deadlines include a short completion grace for output drain and
@@ -116,66 +170,6 @@ serialization.
116
170
  `--result-json` selects captured, non-streaming execution and prints one
117
171
  structured JSON result containing stdout and stderr.
118
172
 
119
- ## Remote workspaces
120
-
121
- A workspace gives a stable name to an Env and filesystem root:
122
-
123
- ```bash
124
- msdev workspace add project \
125
- --env dev-122 \
126
- --root /srv/project
127
-
128
- msdev workspace list
129
- msdev workspace inspect project
130
- ```
131
-
132
- Workspace operations are file- and Git-oriented. There is no
133
- `msdev workspace exec`; use `msdev exec --env ... --cwd ...` for commands.
134
-
135
- ### Read and inspect
136
-
137
- ```bash
138
- msdev workspace stat project README.md
139
- msdev workspace read project README.md
140
- msdev workspace read project weights.bin --output /tmp/weights.bin
141
- msdev workspace list project src --json
142
- msdev workspace glob project '**/*.py' --json
143
- msdev workspace search project 'TODO' src tests --json
144
- ```
145
-
146
- ### Write safely
147
-
148
- For non-trivial content, use stdin or `--file` rather than shell-escaped
149
- `--content`:
150
-
151
- ```bash
152
- msdev workspace write project docs/note.md < /tmp/note.md
153
- msdev workspace write project docs/note.md --file /tmp/note.md
154
- ```
155
-
156
- Compare-and-swap replacement prevents overwriting a changed remote file:
157
-
158
- ```bash
159
- msdev workspace apply-patch project docs/note.md \
160
- --file /tmp/note.md \
161
- --expected-sha256 <digest>
162
- ```
163
-
164
- Delete an explicit remote file:
165
-
166
- ```bash
167
- msdev workspace delete project docs/obsolete.md
168
- ```
169
-
170
- ### Git
171
-
172
- ```bash
173
- msdev workspace git-status project --result-json
174
- msdev workspace git-diff project --result-json -- --stat
175
- ```
176
-
177
- Git diff rejects options that can write files or invoke external diff helpers.
178
-
179
173
  ## Model inventory
180
174
 
181
175
  Examples:
@@ -192,59 +186,6 @@ msdev model audit --node dev-122
192
186
  Use `msdev model --help` and the individual subcommand help for register,
193
187
  update, replicas, refresh, verify, export, import, and rebind.
194
188
 
195
- ## Explicit CLI sessions and runbooks
196
-
197
- Create a session before a reproducible workflow:
198
-
199
- ```bash
200
- msdev session begin --name qwen3-quant --json
201
- ```
202
-
203
- Pass the returned ID explicitly or set it in a persistent terminal:
204
-
205
- ```bash
206
- export MSDEV_SESSION_ID=<session-id>
207
- ```
208
-
209
- Intent metadata is global and must appear before the subcommand:
210
-
211
- ```bash
212
- msdev \
213
- --session-id <session-id> \
214
- --intent-kind execution \
215
- --intent-summary 'Run Qwen3 quantization' \
216
- --intent-phase quantization \
217
- --intent-step-id quant-1 \
218
- exec --env dev-122 --timeout-seconds 1800 -- python3 quant.py
219
- ```
220
-
221
- Intent kinds:
222
-
223
- - `execution`: core reproduction step;
224
- - `verification`: optional confirmation;
225
- - `diagnostic`: troubleshooting, excluded from core steps;
226
- - `exploration`: discovery, excluded from core steps.
227
-
228
- Each invocation receives a unique `operation_id`. `session_id` groups CLI
229
- operations only; it never supplies a Node, Env, or workspace default.
230
-
231
- Logs are private JSONL files under:
232
-
233
- ```text
234
- ${XDG_STATE_HOME:-~/.local/state}/msdev/sessions/
235
- ```
236
-
237
- They retain sanitized logical arguments, preview, explicit resource, intent,
238
- exit code, and elapsed time. Command stdout/stderr and environment values are
239
- not duplicated into logs.
240
-
241
- ```bash
242
- msdev session list
243
- msdev session export --session-id <session-id> --output runbook.md
244
- msdev session export --latest --detail normal --output runbook.md
245
- msdev session export --input /path/to/session.jsonl --detail full
246
- ```
247
-
248
189
  ## Architecture
249
190
 
250
191
  ```text
@@ -252,15 +193,18 @@ msdev CLI
252
193
  -> typed core service
253
194
  -> UnixRpcTransport or SshRpcTransport
254
195
  -> per-user msdevd
255
- -> host/container command, workspace filesystem, NPU, or inventory
196
+ -> host/container command, env file transfer, NPU, or inventory
256
197
  ```
257
198
 
258
- Remote RPC responses and command output are bounded. Workspace paths are
259
- normalized under the registered root. Writes are atomic and support SHA-256
260
- compare-and-swap. Node/Env and workspace registries use locked atomic updates.
199
+ Remote RPC responses and command output are bounded. Node/Env registries use
200
+ locked atomic updates.
261
201
 
262
202
  ## Testing
263
203
 
264
204
  ```bash
265
205
  python3 -m unittest discover -s tests -v
266
206
  ```
207
+
208
+ Feature work must include at least one actual scenario test on the real
209
+ control path (`msdev` CLI → service → transport → `msdevd` → effect). Unit
210
+ tests alone are not sufficient.
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
4
4
 
5
5
  [project]
6
6
  name = "msdev"
7
- version = "0.10.0"
7
+ version = "0.10.1"
8
8
  description = "Portable nodes and execution environments for msModelSlim development"
9
9
  readme = "README.md"
10
10
  requires-python = ">=3.10"
@@ -23,6 +23,7 @@ classifiers = [
23
23
  "Programming Language :: Python :: 3.12",
24
24
  "Programming Language :: Python :: 3.13",
25
25
  "Operating System :: MacOS",
26
+ "Operating System :: Microsoft :: Windows",
26
27
  "Operating System :: POSIX :: Linux",
27
28
  "Topic :: Software Development :: Build Tools",
28
29
  ]
@@ -1,3 +1,3 @@
1
1
  """Portable node and execution-environment tooling for msModelSlim."""
2
2
 
3
- __version__ = "0.10.0"
3
+ __version__ = "0.10.1"