firmwareloop 0.5.0__tar.gz → 0.6.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.
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/PKG-INFO +5 -3
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/README.md +4 -2
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/firmwareloop.egg-info/PKG-INFO +5 -3
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/firmwareloop.egg-info/SOURCES.txt +3 -1
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/pyproject.toml +1 -1
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/__init__.py +1 -1
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/doctor.ps1 +87 -5
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/fw_mcp_server.py +526 -65
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/lib/ndtdbg.py +99 -7
- firmwareloop-0.6.1/tools/lib/serial_assistant.py +954 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/ndtdbg_bridge.ps1 +6 -2
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/ndtdbg_cli.py +589 -515
- firmwareloop-0.6.1/tools/serial_cli.py +415 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/setup-agent-mcp.ps1 +2 -2
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/LICENSE +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/firmwareloop.egg-info/dependency_links.txt +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/firmwareloop.egg-info/entry_points.txt +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/firmwareloop.egg-info/requires.txt +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/firmwareloop.egg-info/top_level.txt +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/setup.cfg +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/acceptance-scenario.ps1 +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/build.ps1 +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/can.ps1 +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/check-qoder-mcp.ps1 +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/common/build-backends.psm1 +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/common/fw.psm1 +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/common/uart_probe.py +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/flash.ps1 +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/instrument_cli.py +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/lib/__init__.py +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/lib/instruments.py +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/logic_capture.ps1 +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/logic_decode.ps1 +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/reset.ps1 +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/sigrok_csv_to_fwloop.py +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/test-backends.ps1 +0 -0
- {firmwareloop-0.5.0 → firmwareloop-0.6.1}/tools/test.ps1 +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: firmwareloop
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.6.1
|
|
4
4
|
Summary: AI Agent Firmware Development and Lab Automation Platform (Dual-Tier MCP Server)
|
|
5
5
|
Author-email: WeilinZhang <19523330249@163.com>
|
|
6
6
|
License: MIT
|
|
@@ -59,6 +59,7 @@ FirmwareLoop 为 AI Agent 暴露了开箱即用的 MCP 工具,涵盖 5 大核
|
|
|
59
59
|
|---|---|---|
|
|
60
60
|
| **构建与体检** | `fw_doctor` <br> `fw_build` | 环境诊断;编译固件并提取诊断日志。 |
|
|
61
61
|
| **硬件与探针** | `fw_scan_hardware` <br> `fw_flash` <br> `fw_reset` | 扫描探针与串口;烧录固件、复位芯片。 |
|
|
62
|
+
| **串口助手** | `fw_serial_status` <br> `fw_serial_open` <br> `fw_serial_send` <br> `fw_serial_read` <br> `fw_serial_parse` <br> `fw_serial_capture` <br> `fw_serial_close` | 长驻会话串口收发(HEX/ASCII);发送序列(delay/loop);帧解析;窗口采集 CSV。 |
|
|
62
63
|
| **总线与协议** | `fw_logic_capture` <br> `fw_logic_decode` | 逻辑分析仪抓取并解码 I2C / SPI / UART。 |
|
|
63
64
|
| **测试与测量** | `fw_run_hil_test` <br> `fw_measure` <br> `fw_acceptance_scenario` | 运行 HIL 自动化测试;读取示波器 / 程控电源测量值。 |
|
|
64
65
|
| **工程与脚手架** | `fw_init_project` <br> `fw_configure_lab` <br> `fw_get_evidence` | 生成多 Agent 指南;修改台架配置;提取审计证据。 |
|
|
@@ -381,7 +382,7 @@ claude mcp remove --scope user agentic-hil
|
|
|
381
382
|
├── demo-firmware/ 示例固件(CMake;宿主编译模拟 MCU,闭环验证载体)
|
|
382
383
|
├── demo-make/ 示例固件(Make;构建测试载体)
|
|
383
384
|
├── docs/ DEPENDENCY_MATRIX / REUSE_PLAN / V0.0.2_GAP_VERIFICATION
|
|
384
|
-
├── pyproject.toml 标准 Python 包配置与 CLI 入口声明 (v0.
|
|
385
|
+
├── pyproject.toml 标准 Python 包配置与 CLI 入口声明 (v0.6.1)
|
|
385
386
|
├── .mcp.example.json 双层 MCP 配置模板(firmwareloop + agentic-hil)
|
|
386
387
|
├── AGENTS.md 通用智能体规范(Antigravity / Qoder / Cursor 等)
|
|
387
388
|
├── CLAUDE.md Claude Code CLI 指南
|
|
@@ -391,7 +392,7 @@ claude mcp remove --scope user agentic-hil
|
|
|
391
392
|
|
|
392
393
|
---
|
|
393
394
|
|
|
394
|
-
## 能力验证状态(v0.
|
|
395
|
+
## 能力验证状态(v0.6.1)
|
|
395
396
|
|
|
396
397
|
> 状态定义:`Implemented`(已实现)/ `Simulator Validated`(模拟验证)/
|
|
397
398
|
> `Real Hardware Validated`(真机验证)/ `Experimental` / `Not Implemented`
|
|
@@ -399,6 +400,7 @@ claude mcp remove --scope user agentic-hil
|
|
|
399
400
|
| 能力 | 状态 |
|
|
400
401
|
|---|---|
|
|
401
402
|
| 双层 MCP 服务(13 个工作流与硬件工具) | Implemented + Protocol Validated(31/31 测试通过) |
|
|
403
|
+
| 串口助手工具族(fw_serial_* 七工具, 长驻会话/发送序列/帧解析/窗口采集) | Implemented + Simulator Validated(48 例单测)-> Real Hardware Validated 待 DUT |
|
|
402
404
|
| 一键多 Agent 脚手架(fwloop init / fw_init_project) | Implemented + Multi-Agent Validated |
|
|
403
405
|
| 自定义/私有调试工具接入 Skill(fwloop-adapter) | Implemented + Multi-Skill Validated |
|
|
404
406
|
| 一键终端更新(fwloop update) | Implemented + Auto-updater Validated |
|
|
@@ -31,6 +31,7 @@ FirmwareLoop 为 AI Agent 暴露了开箱即用的 MCP 工具,涵盖 5 大核
|
|
|
31
31
|
|---|---|---|
|
|
32
32
|
| **构建与体检** | `fw_doctor` <br> `fw_build` | 环境诊断;编译固件并提取诊断日志。 |
|
|
33
33
|
| **硬件与探针** | `fw_scan_hardware` <br> `fw_flash` <br> `fw_reset` | 扫描探针与串口;烧录固件、复位芯片。 |
|
|
34
|
+
| **串口助手** | `fw_serial_status` <br> `fw_serial_open` <br> `fw_serial_send` <br> `fw_serial_read` <br> `fw_serial_parse` <br> `fw_serial_capture` <br> `fw_serial_close` | 长驻会话串口收发(HEX/ASCII);发送序列(delay/loop);帧解析;窗口采集 CSV。 |
|
|
34
35
|
| **总线与协议** | `fw_logic_capture` <br> `fw_logic_decode` | 逻辑分析仪抓取并解码 I2C / SPI / UART。 |
|
|
35
36
|
| **测试与测量** | `fw_run_hil_test` <br> `fw_measure` <br> `fw_acceptance_scenario` | 运行 HIL 自动化测试;读取示波器 / 程控电源测量值。 |
|
|
36
37
|
| **工程与脚手架** | `fw_init_project` <br> `fw_configure_lab` <br> `fw_get_evidence` | 生成多 Agent 指南;修改台架配置;提取审计证据。 |
|
|
@@ -353,7 +354,7 @@ claude mcp remove --scope user agentic-hil
|
|
|
353
354
|
├── demo-firmware/ 示例固件(CMake;宿主编译模拟 MCU,闭环验证载体)
|
|
354
355
|
├── demo-make/ 示例固件(Make;构建测试载体)
|
|
355
356
|
├── docs/ DEPENDENCY_MATRIX / REUSE_PLAN / V0.0.2_GAP_VERIFICATION
|
|
356
|
-
├── pyproject.toml 标准 Python 包配置与 CLI 入口声明 (v0.
|
|
357
|
+
├── pyproject.toml 标准 Python 包配置与 CLI 入口声明 (v0.6.1)
|
|
357
358
|
├── .mcp.example.json 双层 MCP 配置模板(firmwareloop + agentic-hil)
|
|
358
359
|
├── AGENTS.md 通用智能体规范(Antigravity / Qoder / Cursor 等)
|
|
359
360
|
├── CLAUDE.md Claude Code CLI 指南
|
|
@@ -363,7 +364,7 @@ claude mcp remove --scope user agentic-hil
|
|
|
363
364
|
|
|
364
365
|
---
|
|
365
366
|
|
|
366
|
-
## 能力验证状态(v0.
|
|
367
|
+
## 能力验证状态(v0.6.1)
|
|
367
368
|
|
|
368
369
|
> 状态定义:`Implemented`(已实现)/ `Simulator Validated`(模拟验证)/
|
|
369
370
|
> `Real Hardware Validated`(真机验证)/ `Experimental` / `Not Implemented`
|
|
@@ -371,6 +372,7 @@ claude mcp remove --scope user agentic-hil
|
|
|
371
372
|
| 能力 | 状态 |
|
|
372
373
|
|---|---|
|
|
373
374
|
| 双层 MCP 服务(13 个工作流与硬件工具) | Implemented + Protocol Validated(31/31 测试通过) |
|
|
375
|
+
| 串口助手工具族(fw_serial_* 七工具, 长驻会话/发送序列/帧解析/窗口采集) | Implemented + Simulator Validated(48 例单测)-> Real Hardware Validated 待 DUT |
|
|
374
376
|
| 一键多 Agent 脚手架(fwloop init / fw_init_project) | Implemented + Multi-Agent Validated |
|
|
375
377
|
| 自定义/私有调试工具接入 Skill(fwloop-adapter) | Implemented + Multi-Skill Validated |
|
|
376
378
|
| 一键终端更新(fwloop update) | Implemented + Auto-updater Validated |
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: firmwareloop
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.6.1
|
|
4
4
|
Summary: AI Agent Firmware Development and Lab Automation Platform (Dual-Tier MCP Server)
|
|
5
5
|
Author-email: WeilinZhang <19523330249@163.com>
|
|
6
6
|
License: MIT
|
|
@@ -59,6 +59,7 @@ FirmwareLoop 为 AI Agent 暴露了开箱即用的 MCP 工具,涵盖 5 大核
|
|
|
59
59
|
|---|---|---|
|
|
60
60
|
| **构建与体检** | `fw_doctor` <br> `fw_build` | 环境诊断;编译固件并提取诊断日志。 |
|
|
61
61
|
| **硬件与探针** | `fw_scan_hardware` <br> `fw_flash` <br> `fw_reset` | 扫描探针与串口;烧录固件、复位芯片。 |
|
|
62
|
+
| **串口助手** | `fw_serial_status` <br> `fw_serial_open` <br> `fw_serial_send` <br> `fw_serial_read` <br> `fw_serial_parse` <br> `fw_serial_capture` <br> `fw_serial_close` | 长驻会话串口收发(HEX/ASCII);发送序列(delay/loop);帧解析;窗口采集 CSV。 |
|
|
62
63
|
| **总线与协议** | `fw_logic_capture` <br> `fw_logic_decode` | 逻辑分析仪抓取并解码 I2C / SPI / UART。 |
|
|
63
64
|
| **测试与测量** | `fw_run_hil_test` <br> `fw_measure` <br> `fw_acceptance_scenario` | 运行 HIL 自动化测试;读取示波器 / 程控电源测量值。 |
|
|
64
65
|
| **工程与脚手架** | `fw_init_project` <br> `fw_configure_lab` <br> `fw_get_evidence` | 生成多 Agent 指南;修改台架配置;提取审计证据。 |
|
|
@@ -381,7 +382,7 @@ claude mcp remove --scope user agentic-hil
|
|
|
381
382
|
├── demo-firmware/ 示例固件(CMake;宿主编译模拟 MCU,闭环验证载体)
|
|
382
383
|
├── demo-make/ 示例固件(Make;构建测试载体)
|
|
383
384
|
├── docs/ DEPENDENCY_MATRIX / REUSE_PLAN / V0.0.2_GAP_VERIFICATION
|
|
384
|
-
├── pyproject.toml 标准 Python 包配置与 CLI 入口声明 (v0.
|
|
385
|
+
├── pyproject.toml 标准 Python 包配置与 CLI 入口声明 (v0.6.1)
|
|
385
386
|
├── .mcp.example.json 双层 MCP 配置模板(firmwareloop + agentic-hil)
|
|
386
387
|
├── AGENTS.md 通用智能体规范(Antigravity / Qoder / Cursor 等)
|
|
387
388
|
├── CLAUDE.md Claude Code CLI 指南
|
|
@@ -391,7 +392,7 @@ claude mcp remove --scope user agentic-hil
|
|
|
391
392
|
|
|
392
393
|
---
|
|
393
394
|
|
|
394
|
-
## 能力验证状态(v0.
|
|
395
|
+
## 能力验证状态(v0.6.1)
|
|
395
396
|
|
|
396
397
|
> 状态定义:`Implemented`(已实现)/ `Simulator Validated`(模拟验证)/
|
|
397
398
|
> `Real Hardware Validated`(真机验证)/ `Experimental` / `Not Implemented`
|
|
@@ -399,6 +400,7 @@ claude mcp remove --scope user agentic-hil
|
|
|
399
400
|
| 能力 | 状态 |
|
|
400
401
|
|---|---|
|
|
401
402
|
| 双层 MCP 服务(13 个工作流与硬件工具) | Implemented + Protocol Validated(31/31 测试通过) |
|
|
403
|
+
| 串口助手工具族(fw_serial_* 七工具, 长驻会话/发送序列/帧解析/窗口采集) | Implemented + Simulator Validated(48 例单测)-> Real Hardware Validated 待 DUT |
|
|
402
404
|
| 一键多 Agent 脚手架(fwloop init / fw_init_project) | Implemented + Multi-Agent Validated |
|
|
403
405
|
| 自定义/私有调试工具接入 Skill(fwloop-adapter) | Implemented + Multi-Skill Validated |
|
|
404
406
|
| 一键终端更新(fwloop update) | Implemented + Auto-updater Validated |
|
|
@@ -21,6 +21,7 @@ tools/logic_decode.ps1
|
|
|
21
21
|
tools/ndtdbg_bridge.ps1
|
|
22
22
|
tools/ndtdbg_cli.py
|
|
23
23
|
tools/reset.ps1
|
|
24
|
+
tools/serial_cli.py
|
|
24
25
|
tools/setup-agent-mcp.ps1
|
|
25
26
|
tools/sigrok_csv_to_fwloop.py
|
|
26
27
|
tools/test-backends.ps1
|
|
@@ -30,4 +31,5 @@ tools/common/fw.psm1
|
|
|
30
31
|
tools/common/uart_probe.py
|
|
31
32
|
tools/lib/__init__.py
|
|
32
33
|
tools/lib/instruments.py
|
|
33
|
-
tools/lib/ndtdbg.py
|
|
34
|
+
tools/lib/ndtdbg.py
|
|
35
|
+
tools/lib/serial_assistant.py
|
|
@@ -129,28 +129,110 @@ Add-FwCheck 'pyvisa' {
|
|
|
129
129
|
}
|
|
130
130
|
|
|
131
131
|
# COM ports present (UART candidates) - informational, never hardcoded.
|
|
132
|
-
#
|
|
132
|
+
# P2-1: agentic-hil 优先, 兜底改用 pyserial comports (SetupAPI, 覆盖 CH341/CP210x/
|
|
133
|
+
# FTDI 等 USB 适配器; Win32_SerialPort 在 Windows 上常漏报 USB CDC/厂商适配器,
|
|
134
|
+
# 实战漏掉真实 DUT 口 COM3 (USB-SERIAL CH341) 导致 agent 误开蓝牙虚拟口)。
|
|
135
|
+
# 输出带 description 并对蓝牙/虚拟口打标记排序 (真实口在前, 防 agent 首选错口)。
|
|
133
136
|
Add-FwCheck 'com_ports' {
|
|
134
137
|
$comPorts = @()
|
|
138
|
+
$portDetails = @()
|
|
139
|
+
$source = 'none'
|
|
135
140
|
$ahil = if ($venvBin) { Join-Path $venvBin 'agentic-hil.exe' } else { $null }
|
|
136
141
|
if ($ahil -and (Test-Path -LiteralPath $ahil)) {
|
|
137
142
|
try {
|
|
138
143
|
$raw = & $ahil com-ports 2>$null | Out-String
|
|
139
144
|
$parsed = $raw | ConvertFrom-Json -ErrorAction SilentlyContinue
|
|
140
145
|
if ($parsed -and $parsed.ports) {
|
|
141
|
-
$
|
|
146
|
+
$portDetails = @($parsed.ports | ForEach-Object {
|
|
147
|
+
[pscustomobject]@{ device = [string]$_.device; description = [string]$_.description }
|
|
148
|
+
} | Where-Object { $_.device })
|
|
149
|
+
$comPorts = @($portDetails | ForEach-Object { $_.device })
|
|
150
|
+
$source = 'agentic-hil'
|
|
151
|
+
}
|
|
152
|
+
} catch { }
|
|
153
|
+
}
|
|
154
|
+
if ($comPorts.Count -eq 0 -and $python) {
|
|
155
|
+
try {
|
|
156
|
+
$pyCode = "import json; from serial.tools.list_ports import comports; print(json.dumps([{'device': p.device, 'description': (p.description or '')} for p in comports()]))"
|
|
157
|
+
$raw = & $python -c $pyCode 2>$null | Out-String
|
|
158
|
+
$parsed = $raw | ConvertFrom-Json -ErrorAction SilentlyContinue
|
|
159
|
+
if ($parsed) {
|
|
160
|
+
$portDetails = @($parsed | ForEach-Object {
|
|
161
|
+
[pscustomobject]@{ device = [string]$_.device; description = [string]$_.description }
|
|
162
|
+
} | Where-Object { $_.device })
|
|
163
|
+
$comPorts = @($portDetails | ForEach-Object { $_.device })
|
|
164
|
+
$source = 'pyserial'
|
|
142
165
|
}
|
|
143
166
|
} catch { }
|
|
144
167
|
}
|
|
145
168
|
if ($comPorts.Count -eq 0) {
|
|
146
169
|
try {
|
|
147
170
|
$comPorts = @((Get-CimInstance Win32_SerialPort -ErrorAction SilentlyContinue | Select-Object -ExpandProperty DeviceID))
|
|
171
|
+
$source = 'wmi'
|
|
148
172
|
} catch { }
|
|
149
173
|
}
|
|
174
|
+
# 虚拟/蓝牙口标记 + 真实口优先排序
|
|
175
|
+
$isVirtual = { param($d) $d -match '(?i)bluetooth|蓝牙|virtual|modem|debug port' }
|
|
176
|
+
$real = @($portDetails | Where-Object { -not (& $isVirtual $_.description) })
|
|
177
|
+
$virt = @($portDetails | Where-Object { & $isVirtual $_.description })
|
|
178
|
+
$ordered = @(@($real | ForEach-Object { $_.device }) + @($virt | ForEach-Object { $_.device }))
|
|
179
|
+
if ($ordered.Count -gt 0) { $comPorts = $ordered }
|
|
180
|
+
[pscustomobject]@{
|
|
181
|
+
status = if ($comPorts.Count -gt 0) { 'ok' } else { 'none' }
|
|
182
|
+
source = $source
|
|
183
|
+
ports = $comPorts
|
|
184
|
+
port_details = @($portDetails)
|
|
185
|
+
virtual_ports = @($virt | ForEach-Object { $_.device })
|
|
186
|
+
note = '排序: 真实串口在前; 蓝牙/虚拟口仅供参考 (无法访问 DUT)'
|
|
187
|
+
}
|
|
188
|
+
}
|
|
189
|
+
|
|
190
|
+
# P1-4: lab.yaml 配置链透明度——枚举全局/项目两层 ndtdbg 段存在性与
|
|
191
|
+
# write_allowed 状态; 任何层 write_allowed: true 输出 WARNING
|
|
192
|
+
# (global 层常驻 true 属危险默认; 项目层 false 不代表安全——合并链会回退全局层)。
|
|
193
|
+
Add-FwCheck 'lab_yaml' {
|
|
194
|
+
if (-not $python) {
|
|
195
|
+
return [pscustomobject]@{ status = 'missing'; detail = 'no python' }
|
|
196
|
+
}
|
|
197
|
+
$pyCode = @'
|
|
198
|
+
import json, os
|
|
199
|
+
try:
|
|
200
|
+
import yaml
|
|
201
|
+
except ImportError:
|
|
202
|
+
yaml = None
|
|
203
|
+
def sec(p):
|
|
204
|
+
try:
|
|
205
|
+
with open(p, encoding="utf-8") as fh:
|
|
206
|
+
d = (yaml.safe_load(fh) if yaml else json.load(fh)) or {}
|
|
207
|
+
except Exception:
|
|
208
|
+
return {"parse_error": True}
|
|
209
|
+
s = d.get("ndtdbg") if isinstance(d, dict) else None
|
|
210
|
+
return s if isinstance(s, dict) else {}
|
|
211
|
+
out = []
|
|
212
|
+
ad = os.environ.get("APPDATA")
|
|
213
|
+
if ad:
|
|
214
|
+
p = os.path.join(ad, "FirmwareLoop", "lab.yaml")
|
|
215
|
+
n = sec(p)
|
|
216
|
+
out.append({"layer": "global", "path": p, "exists": os.path.isfile(p),
|
|
217
|
+
"ndtdbg": bool(n), "write_allowed": n.get("write_allowed")})
|
|
218
|
+
pp = os.path.join(os.getcwd(), "lab", "lab.yaml")
|
|
219
|
+
n2 = sec(pp)
|
|
220
|
+
out.append({"layer": "project", "path": pp, "exists": os.path.isfile(pp),
|
|
221
|
+
"ndtdbg": bool(n2), "write_allowed": n2.get("write_allowed")})
|
|
222
|
+
print(json.dumps(out))
|
|
223
|
+
'@
|
|
224
|
+
$raw = & $python -c $pyCode 2>$null | Out-String
|
|
225
|
+
$layers = @($raw | ConvertFrom-Json -ErrorAction SilentlyContinue)
|
|
226
|
+
$warned = @($layers | Where-Object { $_.write_allowed -eq $true })
|
|
150
227
|
[pscustomobject]@{
|
|
151
|
-
status = if ($
|
|
152
|
-
|
|
153
|
-
|
|
228
|
+
status = if ($warned.Count -gt 0) { 'warn' } else { 'ok' }
|
|
229
|
+
detail = if ($warned.Count -gt 0) {
|
|
230
|
+
($warned | ForEach-Object {
|
|
231
|
+
$tip = if ($_.layer -eq 'global') { '常驻 true 属危险默认 (会话级临时态, 用完即关)' } else { '项目层开启须用完即关' }
|
|
232
|
+
"$($_.layer) 层 write_allowed=true ($tip)"
|
|
233
|
+
}) -join '; '
|
|
234
|
+
} else { '任何层均未开启 write_allowed (写保护生效)' }
|
|
235
|
+
layers = @($layers)
|
|
154
236
|
}
|
|
155
237
|
}
|
|
156
238
|
|