Metadata-Version: 2.4
Name: sdev
Version: 0.3.5
Summary: 串口控制器工具包
Home-page: https://github.com/klrc/sdev
Author: klrc
Author-email: klrc <144069824@qq.com>
License: MIT
Project-URL: Homepage, https://github.com/klrc/sdev
Project-URL: Repository, https://github.com/klrc/sdev
Project-URL: Bug Tracker, https://github.com/klrc/sdev/issues
Keywords: serial,controller,hardware,embedded
Classifier: Development Status :: 3 - Alpha
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: MIT License
Classifier: Operating System :: OS Independent
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.7
Classifier: Programming Language :: Python :: 3.8
Classifier: Programming Language :: Python :: 3.9
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Topic :: Software Development :: Libraries :: Python Modules
Classifier: Topic :: System :: Hardware
Requires-Python: >=3.7
Description-Content-Type: text/markdown
License-File: LICENSE
Requires-Dist: pyserial>=3.5
Requires-Dist: loguru>=0.6.0
Dynamic: author
Dynamic: home-page
Dynamic: license-file
Dynamic: requires-python

# SDEV

串口开发板控制器：后台按行读缓冲、按 flag 扫描与回显着色、执行命令、存活检测。

**注意**：同一串口同一时间只能被一个 sdev 进程使用。请勿并行执行多条 `sdev shell ...` 或快速连续执行，否则可能报「串口已被其他 sdev 进程占用」或挂死；需等前一条命令结束后再执行下一条。

## 安装

```bash
pip install sdev
```

## 命令行

安装后可使用 `sdev` 命令，在默认串口上执行单条命令并回显：

```bash
sdev shell "lsmod | grep -E 'mmz|nnp|vdsp'"
sdev -p /dev/ttyUSB1 -b 115200 shell "ls"
sdev --no-check-alive shell "echo hello"
```

- `-p` / `--port`：串口路径（默认取环境变量 `SDEV_PORT` 或 `/dev/ttyUSB0`）
- `-b` / `--baudrate`：波特率（默认取 `SDEV_BAUDRATE` 或 `115200`）
- `--flag`：提示符结束标志（默认 `" #"`）
- `--timeout`：等待输出超时秒数
- `--no-check-alive`：连接后不执行存活检测

## 快速使用（Python）

```python
from sdev import SerialDevice

with SerialDevice("/dev/ttyUSB0", 115200) as board:
    # connect 时默认会 check_alive(STABLE_FLAG)，未接串口会轮询等待
    out = board.execute_command("ls")  # 发命令并收到提示符为止，返回输出列表
    print(out)
```

不自动做存活检测时：

```python
board = SerialDevice("/dev/ttyUSB0", 115200, check_alive=False)
board.connect()
board.wait_for_flag("~ #", timeout=20)  # 可选：等到指定提示符
board.execute_command("ls")
board.disconnect()
```

## 主要接口

| 方法 / 属性 | 说明 |
|-------------|------|
| `SerialDevice.STABLE_FLAG` | 类常量 `" #"`，常用作稳定提示符 |
| `connect()` / `disconnect()` | 打开/关闭串口并启停后台读线程；`connect` 可选执行 `check_alive(STABLE_FLAG)` |
| `send(text)` | 发送一行（自动加换行）；`text` 不得含 `\n` / `\r` |
| `execute_command(cmd, flag=" #", stream=False, timeout=None)` | 清缓冲 → 发 `cmd` → 先等命令回显再等含 `flag` 的提示行；返回列表或生成器；`cmd=Ctrl+C` 时兼容 ^C 回显 |
| `check_alive(stable_flag)` | 有输出则 `wait_for_flag(stable_flag)` 后返回；否则发 Ctrl-C 再等；超时则打 warning 并轮询直到有输出 |
| `wait_for_flag(flag, timeout)` | 消费输出直到出现 `flag` 或超时 |
| `send_interrupt(timeout, end_flag=" #")` | 发 Ctrl-C 并等含 `end_flag` 的提示行；超时抛 `TimeoutError` |
| `clear()` | 清空读缓冲（保留 sentinel），一般由 `execute_command` 内部调用 |

- 回显：匹配到 flag 的行为绿色，命令回显行为青色，其余灰色；设备折行会拼行再判 flag。

## 依赖

- Python >= 3.7
- pyserial >= 3.5
- loguru >= 0.6.0
