vault backup: 2026-08-17 17:11:21

This commit is contained in:
windyboy
2026-08-17 17:11:21 +08:00
parent 2790f281c5
commit 3f67e180e7
5 changed files with 572 additions and 0 deletions
@@ -0,0 +1,336 @@
# Matrix 设备认证(SAS)— 知识沉淀
> 本文档是 `ha-matrix-e2e``custom_components/matrix_e2ee`,基于 matrix-nio 0.26.0 + vodozemac)在
> Matrix 设备验证方面**全部已知知识的汇总**,范围:官方规范、官方文档/实现偏差、认证流程、代码定位、
> 注意事项。目的:避免重复排查、重复实现、重复踩坑。
>
> 配套文档:[`docs/DEVICE_VERIFICATION.md`](DEVICE_VERIFICATION.md)(人话操作指南 + 源码级流程)、
> [`SECURITY.md`](../SECURITY.md)(信任模型与威胁边界)、[`docs/DEVELOPMENT.md`](DEVELOPMENT.md)(测试纪律)。
>
> 维护约定:完成/发现新的验证相关 issue 后,把结论同步到本文档对应章节和「Issue 索引表」,不要只留在 Linear。
---
## 1. 官方规范(Matrix Spec
规范来源:matrix-spec `content/client-server-api/modules/end_to_end_encryption.md`(注意:**不是**
`sas_verification.md`,后者 404)。涉及两个机制:**验证框架**(`m.key.verification.request/ready/start/.../done/cancel`
**SAS 方法**`m.sas.v1`)。
### 1.1 验证框架
- **消息通道**:同一账号内验证用 **to-device** 消息;不同用户之间建议用 **in-room** 消息。本项目(bot 验证自己的
另一台设备)走 to-device。
- **Session ID**to-device 用 `transaction_id`in-room 用 event ID。
- **流程**`request`(发起方声明支持的 methods)→ 对方提示接受 → `ready`(接受方回 methods 交集)→ 用户选方法 →
`start` → 方法内交换 → `done`。**任意时点**任一方都可发 `cancel`(带 code)。
- **多设备广播**to-device 的 `request` 广播到对方所有设备(同一 txn)。其中一台接受后,对其他设备发 `cancel`
code `m.accepted`);用户在另一台拒绝则 code `m.user`。in-room 只发一次 request,无 cancel-to-others。
- **提示自动消失**to-device 按 `timestamp`in-room 按 `origin_server_ts`)起 **10 分钟**,或收到后 **2 分钟**
先到为准。拒绝请求**必须**发 `cancel`code=`m.user`
### 1.2 SAS 方法 `m.sas.v1` — 安全原理
灵感来自 **ZRTP hash commitment**responder 在 `accept` 里先发**自己公钥的 hashcommitment**initiator 收到
commitment 后才发自己的公钥。攻击者只有一次猜的机会:验证 n bit 则成功率 `1/2^n`SAS 全 40+ bit → ~1/10^12)。
分两个阶段:
1. **密钥协商**:双方各生成临时 Curve25519 密钥对,交换公钥(带 commitment 保护),ECDH 得共享秘密。
2. **密钥验证**:用共享秘密派生 HMAC,互相认证各自的设备 ed25519 key。
### 1.3 SAS 全流程(18 步,initiator = Alice / responder = Bob
| # | 动作 | 消息 | 内容要点 |
|---|---|---|---|
| 1 | 线下安全会面 | — | 双方对照设备显示内容 |
| 2 | 开始验证 | — | 任一方发起 |
| 3 | Alice 发 start | `m.key.verification.start` | **必须先拿到 Bob 设备 key**;含 key_agreement/hash/mac_method/short_authentication_string |
| 4 | Bob 选算法 | — | 从 Alice 支持列表里挑 key agreement/hash/MAC/SAS 方法 |
| 5 | Bob 需已持 Alice 设备 key | — | 否则先 key query |
| 6 | Bob 生成临时 Curve25519 对 | — | 对公钥做 SHA-256 |
| 7 | Bob 回 accept | `m.key.verification.accept` | 含 `commitment`(自己公钥的 hash |
| 8 | Alice 存 commitment | — | 后续校验 |
| 9 | Alice 生成临时对、发 key | `m.key.verification.key` | **只发公钥** |
| 10 | Bob 发自己 key | `m.key.verification.key` | 已无 commitment 保护风险 |
| 11 | Alice 校验 commitment | — | `commitment == hash(Bob 公钥 + Alice 的 start content)` |
| 12 | 双方 ECDH | — | 临时密钥 → 共享秘密 |
| 13 | 双方显示 SAS | — | emoji/decimal(多方法时用户选) |
| 14 | 用户比对 | — | 两边一致才继续 |
| 15 | 算 MAC | — | 对每个要验证的 key + key ID 列表 |
| 16 | 双方发 mac | `m.key.verification.mac` | |
| 17 | 校验对方 MAC | — | 每个 key 的 MAC + key 列表 MAC 全对 → 设备已验证 |
| 18 | 双方发 done | `m.key.verification.done` | |
**要验证哪些 key**:本设备的 ed25519 key + master signing key(跨用户时**应**含 MSK;「验证他人单设备」的做法已废弃)。
### 1.4 错误处理与 cancel code
- 随时可 cancel**10 分钟超时**txn 闲置 10min 也过期)。
- 同一设备多次发起 → recipient 全部 cancel。
- **未知 txn → cancel**(入站 `start`/`cancel` 除外)。
- 无共同方法 → cancelSAS 不符 → cancel;乱序 → cancel。
- SAS 专属 cancel code`m.unknown_method``m.mismatched_commitment``m.mismatched_sas`
- 框架层 code`m.user`(用户拒绝)、`m.accepted``m.timeout``m.unexpected_message``m.key_mismatch`
### 1.5 MAC 计算(wire 格式,容易错)
- **HKDF 参数**HKDF-SHA256IKM = 共享秘密,**无 salt**。
- **MAC info 串**(逐字节拼接,无分隔符):
`MATRIX_KEY_VERIFICATION_MAC` + 发 MAC 方 `user_id` + `device_id` + 对方 `user_id` + `device_id` + `transaction_id`
+ `key_id`(单个 key);对 key 列表用字符串 `KEY_IDS`
- **HMAC 对象**
- 单个 key → **unpadded base64** 编码的公钥;
- key 列表 → 字典序排序、**逗号连接、无空格**的 `alg:id` 列表,例如
`ed25519:Cross+Signing+Key,ed25519:DEVICEID`
- MAC 值 base64 编码后放进 `mac` 消息的 `mac``keys` 字段。
- **版本(关键)**:规范要求「所有当前实现都应用 `hkdf-hmac-sha256.v2`」。legacy `hkdf-hmac-sha256`v1)因 libolm
原始实现 bug 使用了**错误 base64 编码**,v2 修正;**v1 已废弃,双方都支持 v2 时 MUST NOT 用 v1**。
### 1.6 SAS 派生
- **HKDF info`curve25519-hkdf-sha256`**
`MATRIX_KEY_VERIFICATION_SAS|` + start 发起方 `user_id|` + `device_id|` + start 方公钥(unpadded base64`|`
+ accept 方 `user_id|` + `device_id|` + accept 方公钥(unpadded base64`|` + `transaction_id`
废弃的 `curve25519` 方法:无 `|` 分隔、不含公钥。
- **decimal**:取 5 字节 → 3 个 13-bit 数(08191)各 +1000 → 三个 10009191 的数。
位运算:`(B0<<5|B1>>3)+1000``((B1&0x7)<<10|B2<<2|B3>>6)+1000``((B3&0x3F)<<7|B4>>1)+1000`
- **emoji**:取 6 字节 → 前 42 bit → 7 组 6-bit → 7 个 063 索引 → 查 64 格 emoji 表
JSON 在 `matrix-org/matrix-spec` 仓库 `data-definitions/sas-emoji.json`)。
### 1.7 Cross-signing(本项目的「不做」依据)
三把 ed25519 对:**MSK**master signing key,签 USK/SSK,代表用户身份)、**USK**user-signing key,只自己可见,
签他人 MSK)、**SSK**self-signing key,签自己的设备 key)。作用:只需验证一次 MSK 即可信任该用户所有设备。
本集成因 **nio 0.26 不支持自签 cross-signing key**,且自签会把 cross-signing 权威放到 HA 主机上(违背信任边界),
故**不做** SSSS / Key Backup 导入(W1N-147 结论)。可对他人设备验证其 MSK,但 bot 自身无法 bootstrap 新设备。
---
## 2. 官方规范 vs nio 0.26 的偏差(文档/实现漂移 — 最容易重复踩)
| # | 规范/预期 | nio 0.26.0 实际 | 修复 | 出处 |
|---|---|---|---|---|
| 1 | `request → ready` 由框架处理 | **没有实现**request 被解析为 `UnknownToDeviceEvent` 丢弃 → Element 端显示取消 | 集成自建 `_handle_verification_request` + `_send_verification_ready` | W1N-173, PR #25 |
| 2 | 会话有 10 分钟活动窗口 | `Sas._last_event_time` 只在 `__init__` 赋值、**从不刷新** → `timed_out` 60s 后必真;`clear_verifications()` 每 sync 取消 | monkeypatch `Sas.timed_out`:只留 5min `_max_age`;集成超时 240s 先行触发 | W1N-172, PR #23 |
| 3 | commitment 为 **unpadded base64** | 迁移 vodozemac 后发 **hexdigest**Element 拒收(`m.key_mismatch` | `_apply_sas_commitment_patch``from_key_verification_start` + `_check_commitment` 都改回 unpadded base64 | PR #28, v0.2.8 |
| 4 | emoji 索引由底层算出 | vodozemac 已返回 7 个最终索引,nio 仍按 libolm 时代 bit-slicing **二次转换** → 两端 emoji 不一致、`m.mismatched_sas` | monkeypatch `_generate_emoji` 直接用 indices | W1N-175, PR #29 |
| 5 | 协商 `hkdf-hmac-sha256`(v1) 时 wire 用 libolm **invalid base64** | nio 用标准 `calculate_mac` → MAC 阶段失败 | monkeypatch `get_mac` + `receive_mac_event`,按 `chosen_mac_method``calculate_mac_invalid_base64`libolm-compat feature | W1N-177, PR #30 |
| 6 | 应优先/只用 `.v2` MAC | nio 0.26 **只协商 v1,不提供 `.v2`** | 保持 v1 + invalid_base64 与 rust-sdk/Element 互操作;**不要**自己加 `.v2`(会扩大协商面但 nio 没实现) | W1N-177 |
| 7 | `keys_query` 应覆盖会话各方 | 只取「共享加密房间用户」→ bot 与自身设备不共享房间 → **永不查询自己** → 入站 SAS 建不起来 | 登录/恢复后把自身 `user_id` 加进 `users_for_key_query` 并预热 | W1N-166, PR #18 |
| 8 | 收到 start 前应有设备 key | 新设备首次 start 命中 device_store KeyError → 丢弃 + 不建 SAS | `_repair_dropped_start`:查 key 后把同一 start 重喂给 `nio.olm.handle_key_verification` | W1N-170, PR #23 |
| 9 | 校验失败应发 `m.key_mismatch` cancel | `receive_mac_event`「无已验证设备」分支置 canceled 后**缺 return**,下一行覆盖为 `mac_received` | 上游 bug**Backlog**W1N-179 | W1N-179 |
另:nio 的 `Sas.verified = (state == mac_received) ∧ sas_accepted``get_mac()``sas_accepted=False` 时抛
`LocalProtocolError`——集成代码曾因裸调 get_mac 被 `except Exception` 吞掉而卡死(W1N-142)。
---
## 3. 认证流程(本项目实际路径)
### 3.1 对外接口(已定型)
**服务(admin-only 用 `async_register_admin_service` 强制,W1N-150**
| 服务 | 权限 | 说明 |
|---|---|---|
| `start_verification` | **admin** | bot 发起 SAS(入站由 Element 发起时无需调用) |
| `confirm_verification` | **admin** | 人工比对 emoji 后确认;内部 = `accept_sas` + `get_mac`verified 时再 `verify_device` |
| `cancel_verification` | **admin** | 取消 |
| `verify_device_by_fingerprint` | **admin** | 单向信任;`user_id` + `device_id` + `ed25519` **精确匹配**,否则 `fingerprint_mismatch` |
| `reauthenticate` | **admin** | Config Flow reauth |
| `get_fingerprint` | 普通注册 | 只读;返回 bot 的 `ed25519`/`curve25519` |
| `send_message` | 普通注册 | 发消息 |
**事件**
- `matrix_e2ee_verification` — 各 `stage``started` / `sas`(含 `emojis`/ `done` / `canceled`,带 `expires_at`
W1N-145 `VerificationPrompt``transaction_id/user_id/device_id/emojis/expires_at`)。
- `matrix_e2ee_fingerprint` — 启动后 emit bot 指纹。
- `matrix_e2ee_command` / `matrix_e2ee_error` — 命令事件(仅 `verified=True` 且 allowlist 命中才触发)。
**错误码**`const.py`):`verification_peer_denied`(发起者非 bot 自身账号或 `allowed_users`)、`verification_timeout`
(集成超时 4min)、`fingerprint_mismatch``invalid_transaction``device_missing`
### 3.2 双向流程(wire 时序)
**方向 AElement 发起(入站)** — 由 `handle_to_device_event` + `_handle_verification_request` 驱动:
```
Element HA bot (matrix_e2ee)
│ m.key.verification.request {txn, methods:[m.sas.v1], timestamp}
│ ──────────────────────────────────────────────► _handle_verification_request
│ 校验: sender 允许 / from_device、txn 非空 /
│ methods 含 m.sas.v1 / timestamp 界内
│ ◄────────────────────────────────────────────── m.key.verification.ready {methods:[m.sas.v1]}
│ m.key.verification.start {txn, ...}
│ ──────────────────────────────────────────────► handle_to_device_event (start 分支)
│ _get_sas==None → _repair_dropped_start(查 key 重喂)
│ accept_key_verification(txn) → emit started
│ ◄────────────────────────────────────────────── m.key.verification.acceptnio 内部,含 commitment
│ m.key.verification.key ... key 交换 → 双方显示 emoji
│ ──────────────────────────────────────────────► (key 分支) emit sas {emojis, expires_at}
│ HA 侧人工比对 emoji → confirm_verification(txn)
│ confirm_short_auth_string(txn)
│ = accept_sas + get_mac + (verified→verify_device)
│ ◄────────────────────────────────────────────── m.key.verification.mac(只发一次, W1N-169
│ m.key.verification.mac → (mac 分支) sas.verified → emit done
```
**方向 Bbot 发起(出站)**`start_verification(user_id, device_id)``nio.start_key_verification(device)` 发出
start;后续 accept/key/emoji 同方向 A;比对后同样 `confirm_verification` 完成。key 的发送**完全由 nio 内部负责**
`handle_key_verification``if not sas.we_started_it: share_key()`),集成不再手动 `share_key()`W1N-169)。
**状态机要点**
- 集成只在 start 分支记录 monotonic 时间(`_mark_sas_started`);超时判断 = `sas.timed_out` **或**
monotonic 差 ≥ 240s`_sas_is_timed_out`),超时 → `_timeout_verification`cancel + emit `verification_timeout`
- `confirm_verification` 是**唯一**完成验证的路径:先查超时,再 `nio.confirm_short_auth_string(txn)``sas.verified`
→ emit `done`,否则 emit `sas`(等用户再次 confirm)。
- 入站门控:所有分支(start/key/mac/cancel)统一 `_bootstrap_allowed(sender)`——`sender == session.user_id`
**或** `sender ∈ allowed_users`,否则 emit `verification_peer_denied`W1N-143)。
### 3.3 路径二:单向指纹验证(降级/备选)
`get_fingerprint` 取 bot 指纹 → Element「Manually Verify by Text」;信任对端用 `verify_device_by_fingerprint`
(精确匹配后 `nio.olm.verify_device`,**本地单向信任,不是 SAS,不产生 SAS 事件**)。
---
## 4. 代码地图(`custom_components/matrix_e2ee/`
### client.py1525 行;无 models.py,模型在此文件)
**nio 补丁区(160398**
| 函数 | 行 | 作用 |
|---|---|---|
| `_apply_sas_timeout_patch` | 164 | monkeypatch `Sas.timed_out`verified/canceled→False`now-creation ≥ _max_age(5min)`→canceled+`_timeout_error`+True。**忽略 nio 60s 事件超时 bug** |
| `_sas_commitment(pubkey, canonical)` | 197 | SHA-256(pubkey+canonical) 的 unpadded base64 |
| `_apply_sas_commitment_patch` | 208 | patch `from_key_verification_start`accept commitment+ `_check_commitment`initiator 校验)→ unpadded base64 |
| `_apply_sas_emoji_patch` | 256 | `_generate_emoji` 直接用 `established_sas.bytes(info).emoji_indices` 映射,不做 bit-slicing |
| `_apply_sas_mac_patch` | 286 | 见下 |
| `_select_mac_func` | 304 | `chosen_mac_method=="hkdf-hmac-sha256"``calculate_mac_invalid_base64`,否则 `calculate_mac` |
| `get_mac`patch | 309 | `sas_accepted=False`/canceled 抛 `LocalProtocolError`;按规范拼 info、`ed25519:{own_device}` + `KEY_IDS` |
| `receive_mac_event`patch | 339 | verified→return`state!=key_received`→canceledKEY_IDS 校验→`_key_mismatch_error`;逐 key device_id 匹配 + MAC 校验 → verified_devices;空→canceled**缺 return,复刻 W1N-179 bug** |
| `_patch_nio_sas_timeout/_commitment/_emoji/_mac` | 188/246/277/390 | `try: from nio … except Exception: return`(测试无 nio 时 no-op |
**验证服务(9361525**
| 函数 | 行 | 作用 |
|---|---|---|
| `enable_verification_callbacks` | 936 | 注册 `handle_to_device_event`KeyVerificationEvent+ `_handle_verification_request`ToDeviceEvent |
| `_emit_verification(stage, **extra)` | 947 | fire `matrix_e2ee_verification` + warning log |
| `_verification_expires_at` | 953 | now UTC + `_verification_timeout` ISO 串 |
| `_lookup_device` / `_get_sas` | 959 / 972 | device_store 查设备 / `nio.key_verifications.get(txn)` |
| `_sas_party` / `_sas_emojis` | 978 / 990 | 提取对端 (user,device) / `sas.get_emoji()`(异常吞掉→None`list[list[str]]` |
| `_mark_sas_started` / `_sas_is_timed_out` | 1006 / 1009 | monotonic 记录 / 超时判断 |
| `async_start_verification` | 1018 | 拒软登出;查设备→`nio.start_key_verification`emit `started` |
| `async_verify_device_by_fingerprint` | 1060 | `actual.strip()!=ed25519.strip()` 精确等值(W1N-159)→`fingerprint_mismatch``nio.olm.verify_device` |
| `async_confirm_verification` | 1090 | 超时检查→`nio.confirm_short_auth_string(txn)`verified→emit `done`,否则 emit `sas`。**唯一验设备路径** |
| `async_cancel_verification` | 1139 | `nio.cancel_key_verification(txn, reject=False)` → emit `canceled` |
| `_timeout_verification` | 1169 | cancel + emit `verification_timeout` + `timeout` |
| `_bootstrap_allowed(sender)` | 1187 | `sender==session.user_id``sender in allowed_users`W1N-143 门控) |
| `_repair_dropped_start` | 1196 | `_query_device_keys(sender)` 后重喂 `nio.olm.handle_key_verification(event)`W1N-170 |
| `_handle_verification_request` | 1222 | 解析 request;校验 sender/txn/methods/timestamp → `_send_verification_ready`**不建 SAS 状态**W1N-173 |
| `_send_verification_ready` | 1283 | 回 `ready` {from_device: own, methods:[m.sas.v1], transaction_id} |
| `handle_to_device_event` | 1314 | 主分发:门控→cancel→timeout→startemoji 检查/repair/accept/emit)→keyemit sas)→macverified→emit done |
| `_verification_kind` | 1458 | 类名/type 串 → start/key/mac/cancel |
| `_request_timestamp_valid` | 1447 | 未来≤5min 且 age≤10min |
| `_transaction_id_from_verifications` | 1480 | 匹配 other user+device;唯一则兜底 |
| `_verification_error_code` | 1496 | timeout→`verification_timeout`LocalProtocolError/does not exist→`invalid_transaction`unverified→`unverified_device`;否则 `send_failed` |
### const.py79 行)
`SERVICE_START/CONFIRM/CANCEL_VERIFICATION``SERVICE_VERIFY_DEVICE_BY_FINGERPRINT``ATTR_ED25519/TRANSACTION_ID/
USER_ID/DEVICE_ID``EVENT_VERIFICATION`/`EVENT_FINGERPRINT`;错误码见 §3.1`VERIFICATION_TIMEOUT_SECONDS=240`
`VERIFICATION_REQUEST_MAX_FUTURE_MS`/`MAX_AGE_MS``SAS_METHOD_V1="m.sas.v1"``VERIFICATION_REQUEST/READY/START/
ACCEPT/KEY/MAC/DONE/CANCEL` 类型串。
### __init__.py
`_register_services`(136) 服务→client 方法映射;`_fire_event`(123)`_options`(126) 读 `allowed_users/allowed_rooms`
`async_setup_entry`(268)/`async_unload_entry`(321)。
---
## 5. 注意的问题(Checklist / 教训)
**协议 / wire 层**
1. **MAC 生成与校验必须一起改**`get_mac` + `receive_mac_event` 同步 monkeypatch),只改一边 = 互不兼容。
2. **`.v2` 不要自己加**nio 不提供 `_mac_v2`,不要扩大协商面。
3. **accept/key/mac 的发送权要分清**key 归 nio 内部(`we_started_it` 判断),mac 只由 `confirm_verification` 发;
集成只做事件映射与人工 confirm 触发(W1N-169 双发教训)。
4. commitment 必须 unpadded base64(不是 hexdigest);emoji 索引不得二次转换;legacy MAC 用 invalid base64。
5. SAS HKDF info / MAC info 都是**无分隔符逐字节拼接**,字段顺序(发起方在前)与方向不能错。
**nio 状态机坑**
6. `Sas.timed_out` 被 nio 60s bug 污染 → 必须 monkeypatch,用 240s 集成超时先行。
7. `get_mac()``sas_accepted=False` 抛异常 → 必须走 `confirm_short_auth_string`,别裸调。
8. 入站 start 需设备 key`_get_sas==None` 时先 `_repair_dropped_start`(查 key 重喂),不要直接放弃。
9. `keys_query` 默认不含 bot 自己 → 登录/恢复后主动预热自身 keys。
**信任 / 安全**
10. **无自动信任**:同账号 ≠ 可信,包括 `@bot` 自身设备(W1N-153)。
11. 指纹比较**必须精确等值**,禁 `casefold()`unpadded base64 大小写敏感,W1N-159)。
12. 验证/指纹/reauth 服务必须 admin-onlyW1N-150);入站所有分支统一门控 `_bootstrap_allowed`W1N-143)。
13. request 的 timestamp 校验:未来≤5min、age≤10minW1N-173)。
14. fail-closed:未验证设备不触发命令事件、不回退明文、`ignore_unverified_devices` 永不开启、日志不落 secretW1N-136)。
**运维 / 测试**
15. 设备 ID 变了 = store 丢失 → 按 runbook 重新验证,不静默新建设备(W1N-134/138)。
16. 测试只用 FakeNio/FakeSas**协议级问题单测不可见** → 缺真实 homeserver e2eW1N-171 Backlog)。
17. 上游 nio `receive_mac_event` 缺 return bug 已复刻到我们的 patch 里(W1N-179 Backlog),改上游时同步改。
---
## 6. Issue 索引表(Linear → 知识)
状态:✅ Done ⏳ Backlog
| Issue | 主题 | 知识章节 | 状态 |
|---|---|---|---|
| W1N-134 | M2 E2EE 登录/原子 session/恢复同一设备 | §5-15 | ✅ |
| W1N-135 | M2 加密收发 + sync tokens(消费验证状态) | §3 | ✅ |
| W1N-136 | M2 fail-closed、allowlist、不记录 secret | §5-14 | ✅ |
| W1N-137 | M3 SAS 服务/事件 + verified-device 策略 | §3.1 | ✅ |
| W1N-138 | M4 软登出/store 丢失恢复/diagnostics | §5-15 | ✅ |
| W1N-141 | 集成设备安全验证指南(parent of AF | — | ✅ |
| W1N-142 | A SAS auto-completion(修 get_mac 卡死)→ 后被 W1N-153 撤销自动分支 | §2 / §5-7 | ✅ |
| W1N-143 | B 入站 SAS 发起者门控 | §3.2 / §5-12 | ✅ |
| W1N-144 | C 单向指纹验证(get_fingerprint / verify_device | §3.3 | ✅ |
| W1N-145 | D VerificationPrompt 模型 + expires_at | §3.1 | ✅ |
| W1N-147 | F SECURITY.md + SAS/指纹指南(cross-signing 不做 SSSS | §1.7 | ✅ |
| W1N-149 | 安全加固总纲(P0 自动确认 / P0 admin-only / P1 指纹门控) | §5 | ✅ |
| W1N-150 | B admin-only 强制 | §3.1 / §5-12 | ✅ |
| W1N-151 | C verify_device_by_fingerprinted25519 精确门控) | §3.3 | ✅ |
| W1N-153 | A 删除同账号 SAS 自动确认 | §5-10 | ✅ |
| W1N-154 | E 文档改为手动确认 + 新指纹服务名 | — | ✅ |
| W1N-156 | 加固跟进:allowlist 拆分 + P2 质量(**未做** | §8 | ⏳ |
| W1N-157 | F 人话版验证指南(docs/DEVICE_VERIFICATION.md | — | ✅ |
| W1N-158 | M5 Config Flowreauth/设备验证 UI 路径动机) | — | ✅ |
| W1N-159 | casefold 指纹比较 bug → 精确匹配 | §5-11 | ✅ |
| W1N-162 | Config Flow reconfigure + reauth | — | ✅ |
| W1N-165 | 文档更新 + release 0.2.0SAS 保持 service/event-based | §8 | ✅ |
| W1N-166 | keys_query 不查同账号 → 预热 own device keys | §2-7 / §5-9 | ✅ |
| W1N-169 | key/mac 双发(协议正确性) | §5-3 | ✅ |
| W1N-170 | 启动后新增设备首次 start 被丢 → 自动查 key 重喂 | §2-8 / §5-8 | ✅ |
| W1N-171 | 缺真实 homeserver 端到端 SAS 测试 | §5-16 | ⏳ |
| W1N-172 | nio 60s 必死超时(_last_event_time 不刷新) | §2-2 / §5-6 | ✅ |
| W1N-173 | request → ready 桥接(nio 缺框架) | §2-1 / §5-13 | ✅ |
| W1N-174/176 | 部署 matrix_e2ee(e) 到 hass.windy.lan | — | ✅ |
| W1N-175 | emoji 双转换(vodozemac indices | §2-4 | ✅ |
| W1N-177 | legacy MAC invalid-base64 | §2-5/6 / §5-1/2 | ✅ |
| W1N-178 | 部署 v0.2.10(含 legacy MAC 修复) | — | ✅ |
| W1N-179 | receive_mac_event 缺 return 覆盖 canceled**未做** | §2-9 / §5-17 | ⏳ |
---
## 7. 当前版本状态与待办
- 已发布至 **v0.2.10**wire 修复线:commitment v0.2.8 → emoji v0.2.9 → legacy MAC v0.2.10,均已部署
hass.windy.lan)。
- SAS 保持 **service/event-based**v0.2.x);HA 内 live SAS emoji UI 延后到 v0.3W1N-165 / SECURITY.md)。
**Backlog(避免重复工作,动手前先查这 3 条)**
1. **W1N-156** — 拆分 `allowed_users` 为「命令权限」与「SAS 验证权限」两组;SAS 不支持算法显式 cancel;
setup/stop/reauth async lock;事务绑定(存预期 user/device/创建时间);CI manifest 依赖校验;ruff。
2. **W1N-179** — nio `receive_mac_event` 缺 return(上游 + 我们的 monkeypatch 同步修,加单测)。
3. **W1N-171** — 真实 homeserver 端到端 SAS 测试(docker Synapse 或人工 runbook)。
@@ -0,0 +1,67 @@
# 低打印量黑白激光一体机:采购决策树(2026-08)
## 结论
对于“打印量很小、20 页/分钟足够、不需要 ADF”的需求,不应为 34 页/分钟、250 页纸盒或双面 ADF 付费。它们解决的是连续文档处理,而不是偶尔打印。优先级应为:**不被耗材/账号绑定、稳定的局域网打印、平板扫描、紧凑尺寸和可获得的原装耗材**。
首选是 **Brother DCP-L1638W 或 DCP-L1848W**:两者都是传统鼓粉分离路线,20 ppm、150 页纸盒、百兆有线网口及 2.4/5 GHz Wi-Fi;官方资料不能证实 1848 相比 1638 有实质功能升级,因此按正规渠道的含税到手价和保修选较便宜、在售的一台即可。[L1638W 官方参数表](https://www.brother.cn/-/media/ap/cn/products/pdf-file/prt/ESL-done/DCP-L1628L1638W.ashx)[L1848W 官方参数表](https://www.brother.cn/-/media/ap/cn/products/pdf-file/prt/ESL_DCP-L1848W.ashx)
不把 Brother DCP-11W 作为默认首选。它是 Brother 当前标为新品的同级机器,却是“云充”按页模式:激活后含 700 页,页数用完要通过绑定的微信账户购买套餐才能继续打印;粉仓和硒鼓由官方免费提供。这适合愿意换取三年保修和明确按页预算的人,不适合希望长期离线、自主选择耗材的人。[新品发布](https://www.brother.cn/info/news/20250613)[云充规则](https://www.brother.cn/minisite/sppackage/esl/)
## 先按需求分流,而不是按品牌或 ppm
```text
需要批量扫描/复印多页原稿?
├─ 是 → 本指南不适用;选择带 ADF 的 L2648DW 等级,双面原稿高频则看双 CIS 机型。
└─ 否
└─ 需要自动双面打印?
├─ 是 → 选择 B7628DW 等带 duplex 的型号;这是功能升级,不是速度升级。
└─ 否
└─ 必须有有线网口或 5 GHz Wi-Fi
├─ 是 → Brother L1638W/L1848W 为基准选择。
└─ 否 / 接受仅 2.4 GHz Wi-Fi
└─ 是否接受按页充值并绑定微信?
├─ 是 → Brother DCP-11W(先比较套餐与传统耗材总价)。
└─ 否 → L1638W/L1848W;或比较下列 Canon/HP/Pantum。
```
### 采购前的一票否决项
- 需要 macOS、iPhone/iPad:确认 AirPrint;不要假定“Wi-Fi”就等于无需驱动。
- 打印机准备接交换机:确认具体 SKU 有 **Ethernet**,不能把 Wi-Fi Direct 当作局域网网口。HP MFP 1188w 的中国规格仅列 USB 和 2.4 GHz Wi-Fi,不列有线网口。
- 偶尔使用也建议选激光,但纸张要长期放在干燥、封闭处;低使用量时,受潮纸和旧粉盒造成的底灰、掉粉或卡纸比 20/22 ppm 差异更常见。
- 需要自动双面打印、ADF、双面扫描时,直接跳级;入门平板机硬凑这些功能没有性价比。
## 候选机型:仅保留与需求相符者
| 机型 | 联网 / 移动打印 | 核心纸路与扫描 | 耗材结构 | 面向本需求的判断 |
|---|---|---|---|---|
| **Brother DCP-L1638W / L1848W** | USB、100M Ethernet、2.4/5 GHz Wi-FiAirPrint、Mopria、Wireless Direct、Brother Mobile Connect | 20 ppm、150 页进/50 页出、平板 CIS;无 ADF、无自动双面 | TN118 约 1,500 页 + DR118 约 10,000 页,鼓粉分离 | **首选**:功能刚好够用,网络规格最好,自主耗材路径最清晰。两台按价格/现货择一。 |
| **Brother DCP-11W** | USB、100M Ethernet、2.4/5 GHz Wi-Fi / Wi-Fi Direct | 20 ppm、150 页纸盒、平板扫描;未列 ADF 或自动双面 | 云充按页;耗材由官方供给 | 只有明确接受微信充值、看重三年保修时才选;不是“便宜传统激光机”。 |
| **Pantum M6509NW** | USB、100M Ethernet、2.4 GHz 802.11b/g/n Wi-Fi;自带热点 | 22 ppm、150 页进/100 页出、平板扫描;手动双面 | 鼓粉一体 PD-219,官方标称 1,600 页 | **价格明显更低时的可比替代**。接口齐全,支持扫 PC/邮件/FTP/移动端,但机身较宽、仅 2.4 GHz,且鼓粉一体意味着每次换耗材同时更换感光组件。 |
| **HP Laser MFP 1188w** | USB、2.4 GHz 802.11b/g/n、Wi-Fi Direct、AirPrint/Mopria/HP 应用;**无 Ethernet** | 22 ppm、150 页进/100 页出、平板扫描;手动双面 | 一体式黑色硒鼓;随机约 1,500 页 | 仅无线且 2.4 GHz 能满足时再比价。优点是 AirPrint/Mopria 明确、首张页快;不符合“网口或双频”优先条件。 |
| **Canon iC MF232w** | Ethernet、2.4 GHz Wi-Fi、AirPrint、网络/移动扫描 | 23 ppm、250 页纸盒、平板扫描;无自动双面 | CRG337 一体式硒鼓 2,400 页 | 纸盒需求确实较大才考虑。官方建议价较高,且产品规格呈现的是较老的 IPv4 / 2.4 GHz 组合,不是本需求下的优先解。 |
| **Canon iC MF272dw** | Ethernet、2.4 GHz Wi-Fi、AirPrint/Mopria | 29 ppm、150 页纸盒、平板扫描、自动双面打印 | CRG071700 页随机、1,200/2,500 页商品硒鼓 | 功能不错但属于为自动双面打印升级;官方建议价 ¥3,838,不适合低量、单面为主时以性价比为目标的采购。 |
Brother 规格与耗材页数以官方参数表为准;Pantum 的接口、PD-219 和建议月印量 2502,000 页见[官方产品页](https://www.pantum.cn/product-center/1487019260672548865.html)。HP 的 22 ppm、150 页、仅 Wi-Fi/USB、手动双面和一年保修见[中国官方规格](https://support.hp.com/cn-zh/product/product-specs/hp/2101513893)。Canon MF232w 的 23 ppm、250 页、CRG337、IPv4 和接口见[官方规格](https://www.canon.com.cn/product/icmf232w/spec.html)MF272dw 的 29 ppm、自动双面、接口及 CRG071 页数见[官方规格](https://www.canon.com.cn/product/icmf272dw/spec.html)。
## 耗材与锁定:应怎样理解
**不要只用“每页成本”决定低量用户。** 一年只打印几十到几百页时,机器差价、过期/存放不当的耗材风险和购买便利性,通常超过高容量粉盒带来的单位页优势。页产量也是 ISO 覆盖率下的额定值,不等于实际能稳定打印的页数。
- **传统耗材(Brother L1638W/L1848W**:粉盒和硒鼓分开,硒鼓寿命远高于单盒粉量;这是长期低量使用中最可预测的结构。原装 TN118 / DR118 的料号和页数已由 Brother 公布。第三方粉盒或灌粉可以降低成本,但不属于厂商性能/保修承诺;低量用户省下的钱很有限,反而更容易把故障归因变复杂。建议首个生命周期使用原装或可靠授权渠道耗材。
- **云充(DCP-11W)**:这里的锁定不是“第三方粉盒风险”,而是服务依赖:打印资格、套餐和耗材供给都依赖绑定的微信/官方流程。购买前应把预计三年页数代入套餐,确认账号更换、迁移、停服或转让场景的处理规则;并接受双面一张按两页计。
- **一体式硒鼓(Pantum、HP、Canon)**:换粉即换鼓,维护动作简单;缺点是无法像鼓粉分离机那样只更换粉盒。不要据此推断“第三方一定不能用”或“必然会被固件锁死”——厂商公开资料通常只承诺原装耗材效果/保修,兼容耗材的芯片兼容性、质量和售后由销售方承担,应按批次验证。
## 最终推荐与购买动作
1. **默认买 Brother DCP-L1638W 或 DCP-L1848W**:选到手价更低、可开票、有本地退换/保修的那个;功能层面无需为 1848 付溢价。
2. 若二者断货或溢价过大,**Pantum M6509NW** 是功能不降级的对照品;要求 5 GHz Wi-Fi 时排除它。
3. 若只用手机/2.4 GHz Wi-Fi,且 HP 的即时价格有明显优势,才纳入 **HP 1188w**;它没有网口,不能接入现有有线网络。
4. **不要因为“最新”买 DCP-11W**,除非云充模式本身是主动选择。对低量家庭用户,耗材自主权通常比三年保修更重要。
到货后先完成一次有线或基础 Wi-Fi 配网、AirPrint/Windows/macOS 实测、扫描为 PDF、睡眠唤醒和一张双面手动测试;保留试机页与发票。将设备放在受信任 LAN;如果启用 Wi-Fi Direct,设置强口令,平时不需要则关闭。
## 调研边界
本表只比较中国市场仍可由厂商官方页面/支持页核实的代表 SKU,价格、实际库存和促销会实时变化,未把电商标价写入结论。所谓“最新”以 Brother 中国目录/公告为准,而非“功能最强”或“最适合”。资料核查日期:2026-08-11。
@@ -0,0 +1,158 @@
# 希力威视 SR-S25G3218F 调查(2026-08-08
**结论:** 若需求是大量 2.5G 终端、少量 10G 光上联,`SR-S25G3218F` 的端口密度
更合适;厂商已公开该型号的固件页,但仍缺少完整规格书、管理手册与兼容矩阵。若需求是 8 条全部可协商
1/2.5/5/10G 的铜缆链路,且希望有可查的 L3 能力和固件入口,兮克
`SKS8300-8T` 是资料更完整、风险更低的选择;它的代价是主动风扇、外置 12 V 电源、
无 SFP+ 光口,且仍不应把消费级/SMB 设备当作安全边界或唯一核心。两者都应在
到货可退换期内完成实机验收。
本页为采购前资料调查,不代表已接入本地网络;检索日期为 2026-08-08。
## 已能核实的事项
| 项目 | 结论与证据强度 |
|---|---|
| 型号/端口 | 京东的希力威视商品标题称该 SKU 为 `SR-S25G3218F`,有 16 个 2.5G 电口和 2 个万兆光口,并宣传 VLAN、端口隔离与 LACP。该店铺被厂商官网列为可购买的「京东旗舰店」,因此可作为销售规格,非技术手册。[京东商品页](https://item.jd.com/100165071727.html)[厂商购买渠道说明](https://en.sirivision.com/contactus/) |
| 厂商身份 | 厂商官网为 Shenzhen/Guangdong Sirivision Communication;英文官网说明其自 2016 年起提供接入、汇聚和核心交换机方案。[厂商首页](https://en.sirivision.com/) |
| 公开的二手厂家资料 | 同一制造商名义的 Alibaba 出口页将精确型号写成 `16*2.5G+2*10G``120Gbps`,并列出 QoS、VLAN、SNMP、L3 与 stackable。这是制造商发布在平台上的销售资料,**不是**官网数据表;其中后五项不能据此视为已验收的功能承诺。[制造商平台页](https://www.alibaba.com/pla/SR-S25G3218F-QoS-Managed-SFP-Switch-1625G210G_1601494946214.html) |
| 固件入口 | 厂商已发布此精确型号的[固件页](https://www.sirivision.com/sr-s25g3218f%E5%9B%BA%E4%BB%B6/)。公开变更记录提到“光口自适应”和“增加 DAC 配置”;这证明厂商维护过该路径,**不**代表任意 SFP+/DAC/铜模块均兼容。 |
| 本机可计算的带宽 | 端口线速相加为单向 60 Gb/s16 × 2.5 + 2 × 10);若厂商所谓 `120Gbps` 是全双工交换容量,则数学上吻合。它**不**证明缓冲、PPS、表项规模或实际无阻塞性能。 |
## 网管/L2/L3 能力边界
京东标题足以支持把 VLAN、端口隔离、LACP 作为「卖家声称提供」的功能;不得由此推导出
ACL、IPv4/IPv6 静态路由、SVI 数量、DHCP relay、OSPF/RIP、VRRP、IGMP、ERPS、
802.1X、RADIUS/TACACS+、SSH/HTTPS 管理、SNMP 版本、日志/审计、配置备份或固件
安全维护一定存在。
尤其要注意:厂商官网把真正列出的 2.5G L3 产品标为
`SR-S25G3412F (8 × 2.5G + 4 × 10G SFP+)`;其 2.5G 类目只显示 7 个型号,
不含 `SR-S25G3218F`。官网也把 L2+、Web Smart、L3 分成不同产品类别。这个目录
差异**不是**证明 3218F 没有 L3,而是说明「三层」无法通过官网的精确型号文档确认。
[2.5G 产品目录](https://en.sirivision.com/product-category/products/2-5g-switches/)
[官网的 10G L3 目录](https://en.sirivision.com/product-category/products/10g-switches/10g-layer3-managed-switches/)
[官网的 L2+ 分类示例](https://en.sirivision.com/product-category/products/gigabit-switches/gigabit-layer2-managed-switches/)。
采购前请向京东/厂商索取**与机身 SKU、硬件 revision 和固件版本对应**的 PDF
数据表、管理手册和 release notes,并要求书面回答至少以下问题:
1. L3 是只有 VLAN Interface/IPv4 静态路由,还是另有 IPv6、ACL、动态路由、DHCP relay
等;每项的最大 VLAN、MAC、ARP、路由、ACL、LAG 数量分别是多少?
2. LACP 是否符合 802.3ad、一个 LAG 最多多少成员、能否跨两台设备(若销售页的
`stackable` 属实,堆叠的线缆/模块、最大成员、控制面和软件版本为何)?
3. 管理面是否支持 HTTPS/SSH、禁用 HTTP/Telnet、独立管理 VLAN、SNMPv3、syslog、NTP、
配置导出/回滚和已签名或可校验的固件;默认凭据首次登录是否强制修改?
## 供电、散热和光口:当前不能确认
针对该精确 SKU,厂商官网目录与公开搜索未找到说明书/数据表,所以以下均为**待确认,
不能猜测**
- 是否为内置 AC 电源、额定输入范围/最大功耗、是否带电源开关和接地端子;是否完全
不提供 PoE(本型号名和京东标题均未写 PoE,但这不足以替代规格书)。
- 风扇数量、常态/满载噪声、风向、环境温湿度、机架深度与安装耳;不要将「金属壳」
或产品照片等同于无风扇/静音。
- 两个槽是否均为 **10G SFP+**,是否可协商 1G SFP;支持的 SR/LR/BiDi 波长距离、
DAC/AOC 长度、第三方模块/EERPOM 兼容策略、10GBASE-T SFP+ 模块的功耗/温度限制,
以及是否支持 GPON/XPON ONU「猫棒」。
厂商确实单列「SFP Optical Modules」产品分类,但这不构成 3218F 的兼容清单。
[厂商产品导航](https://en.sirivision.com/)。购买光模块/直连线时,应要求厂商按这台
设备的硬件/固件 revision 出具兼容型号清单;没有书面清单时,先在可退换期实测两端的
链路、重启恢复、热插拔与长时间满载错误计数。
## 风险与建议验收
- **文档/生命周期风险(中到高):** 精确型号不在厂商当前官网 2.5G 目录,虽有固件下载页,
但未公开完整型号手册、明确 release notes 或兼容矩阵。官网的售后条款也要求按具体产品查询保修期,配件(含光纤头)
的保修条款与主机不同;不要把平台页的「3 年」当作中国零售 SKU 的已确认保修。
[厂商售后条款](https://en.sirivision.com/after-sale-protection/)
- **功能表述风险(高):** 页面将 L2 特性和「三层网管」并列;在命令/网页菜单、
手册和测试证明之前,将其当作 L2 VLAN/LACP 设备部署,跨 VLAN 路由仍由现有网关承担。
- **双 10G 上联约束(中):** 两个 SFP+ 可作双上联或一个二成员 LAG,但 LAG 增加的是
多流量总吞吐,单一 TCP/UDP 流通常仍受一条 10G 链路限制;上级设备也必须匹配 LACP
配置。
- **管理面风险(中到高):** 家用/低价网管设备常见明文管理、弱默认口令或不透明的固件
更新周期;采购后先置于受限管理 VLAN,改口令、升级已验证固件,且不将管理界面暴露
到 WAN/访客网。
最低验收应包括:逐口协商 100M/1G/2.5G、两只不同厂家 SFP+/DAC(仅在卖家承诺支持的
范围内)、VLAN trunk/access/PVID、STP/环路保护、LACP 故障切换、端口隔离、满载
双向 iperf3 与错误计数、冷启动后的配置保留,以及管理面的 HTTPS/SSH/SNMPv3/配置备份。
如无法提供与型号匹配的正式资料或其中任一关键项失败,应在退换期内退货,并选择公开
数据表、固件与兼容矩阵更完整的型号。
## 备选:兮克 SKS8300-8T 对比
### 已核实的厂商规格
兮克官网的精确型号页明确将 `SKS8300-8T` 定位为三层管理型 10G 全电口交换机,并列出:
- 8 × 1/2.5/5/10GBASE-T RJ45160 Gb/s 交换容量、119.05 Mpps、12 Mbit 缓存、
16K MAC、12 KB 巨帧、512 MB DRAM、32 MB Flash,尺寸 207 × 136 × 35 mm
- QoS、ACL、IP+MAC+端口绑定、流分类/优先级标记、多端口镜像、静态/灵活 QinQ、
sFlow,以及「基于策略的 IPv4/IPv6 单播路由」。
这些是厂商能力声明,并非对每一种路由协议或表项上限的承诺;但相对 3218F 的仅有
销售标题,它给出了精确型号、转发性能和 L3 范围。[兮克 SKS8300-8T
产品页](https://seekswan.com/user/custom-pages/SKS8300-8T.html)
独立的 OpenWrt 设备资料将其识别为 Realtek RTL9303、512 MB RAM,记录了原厂固件
下载入口和串口/TFTP 恢复路径;其硬件数据页列为 12 V / 4 A。这支持「可恢复、可替换
系统」的可操作性,但**不是**兮克对原厂功能的支持承诺。
[OpenWrt 设备页](https://openwrt.org/toh/xikestor/sks8300-8t)
[OpenWrt 硬件数据](https://openwrt.org/toh/hwdata/xikestor/xikestor_sks8300-8t)。
### 能力、物理与运维比较
| 维度 | 希力威视 SR-S25G3218F | 兮克 SKS8300-8T |
|---|---|---|
| 接口/典型用途 | 16 × 2.5G 电口 + 2 × 10G SFP+(销售规格);适合很多 2.5G 终端/NAS,以 10G 光或 DAC 上联。 | 8 × 1/2.5/5/10GBASE-T;适合 10G 铜缆设备、2.5/5G 多速率 NAS/主机。没有 SFP+,光纤上联必须经媒体转换或选另一型号。 |
| 可确认的三层范围 | 仅销售/平台资料称 L3;没有精确型号官方手册,不能确认静态路由以外的功能。 | 官网明确写策略型 IPv4/IPv6 单播路由、ACL/QoS/sFlow/QinQ;动态路由、VRRP、IPv6 ACL/SNMP/认证等仍须按当前固件手册确认。 |
| 冗余/二层 | 卖家声称 VLAN、端口隔离、LACP;STP/环网的实现与规格未知。 | 官网声明 L3 和多项转发特性,但未在产品页给出 STP/LACP/ERPS 的精确限制;购买前仍索取手册。 |
| 散热/噪声 | 无可核实的精确型号风扇、噪声、功耗或风向数据。 | 独立手册镜像和产品图均称智能温控风扇,但厂商产品页未给 dBA;应按「有风扇、可能听得见」规划,不能承诺静音。 |
| 供电 | 未找到精确型号官方输入/功耗资料。 | OpenWrt 硬件数据记录 12 V / 4 A;确认随附电源适配器的插头、余量和地区认证。官方产品页未给满载功耗。 |
| 固件/恢复 | 有精确型号官方固件页;公开记录包含光口自适应与 DAC 配置改动,但未找到完整 release notes、恢复步骤或兼容矩阵。 | 厂商产品页提供「相关下载」区,OpenWrt 还记录原厂固件入口、RJ45 串口和 U-Boot/TFTP 恢复;原厂镜像是否签名、漏洞修复 SLA、配置回退仍未知。 |
关于 8T 的风扇、满载功耗(常见转述为 ≤36 W)、温度范围、芯片型号等,本次未找到
相应的**厂商原始数据表**;不将第三方手册转录当作已核实规格。若噪声、UPS 容量或
机柜散热是购买约束,请先让卖家提供产品铭牌照片、适配器铭牌照片、额定/实测功耗和
dBA 测试条件。
### 选择与验收建议
-**3218F**:必须有 ≥12 个 2.5G 接入端、10G 光/DAC 上联、且 L3 留给现有路由器。
下单前先取得精确型号手册和 SFP+/DAC 兼容承诺;否则端口数量优势不足以抵消资料风险。
-**8T**:最多 8 个设备但需要多速率 10G RJ45、明确的 IPv4/IPv6 静态/策略路由和
以后自行维护/恢复的余地。不要把其 160 Gb/s 标称交换容量误解为 8 端口同时 10G
全双工的性能保证——该标称与端口总线速数学相等,但仍须以实测和厂商 PPS/缓冲说明为准。
- 两台都不应单独承担防火墙、访客/IoT 安全隔离或 WAN 暴露;VLAN 的跨网段策略和公网
边界留在受支持的网关/防火墙上。先为管理面创建专用 VLAN,仅从管理主机访问,禁用
未使用的远程管理协议,备份配置和原厂固件后再接入生产网络。
## 低功耗核心备选(8 × 2.5G + 2 × SFP+
如果核心只需接最多 8 台铜缆终端、上联/连接 NAS 使用 DAC 或光纤 10G,优先考虑没有
PoE 的以下两款。它们都满足 VLAN trunk、LACP 和至少两个 10G SFP+ 的需求;不要为
AP 选 PoE 版来承担核心,因为 PoE 预算、风扇和待机损耗都会明显增加。
| 型号 | 端口与管理能力(厂商声明) | 厂商功耗 / 噪声资料 | 对当前 LAN 的判断 |
|---|---|---|---|
| **TP-Link Omada SG3210X-M2** | 8 × 100M/1G/2.5G RJ45、2 × 10G SFP+,并有 RJ45 和 Micro-USB console。厂商规格列出 802.1Q VLAN、STP/RSTP/MSTP、静态 LAG 和 802.3ad LACP(最多 8 个聚合组、每组最多 8 端口);L3 是 32 个 IPv4/IPv6 接口、48 条静态路由。 | **无风扇**100240 V AC 内置电源。`UN 1.20` 数据表:待机最高 **6.0 W**220 V/50 Hz、25 °C),最高 **15.3 W**220 V)或 **15.0 W**110 V)。 | **首选低功耗方案。** 足以做 LAN66 核心、给 PVE/gfw 与 U6 Lite 做 VLAN 10 trunk,并以 SFP+ DAC/光口连接 10G NAS/主机;它不提供 5G/10G RJ4510G 铜缆需外置转换或 SFP+ 10GBASE-T 模块。 |
| **MikroTik CRS310-8G+2S+IN** | 8 × 2.5G RJ45、2 × 10G SFP+SFP+ 笼支持 1G/2.5G/10G。RouterOS v7(也可选 SwOS)支持 VLAN、链路聚合与 ACL。 | 18–57 V DC 外置供电;官方给出“无附件”最高 **21 W**、总体最高 **34 W**,且机内 **1 个风扇**。厂商没有在该页给出 dBA。 | 可用且软件/文档/恢复路径成熟,但不是本题的静音低功耗优先项:官方最大功耗显著高于 TP-Link,且有风扇。适合明确偏好 RouterOS/SwOS 与其可维护性时选。 |
功耗数字是各厂商的**上限/待机测试条件**,不是你实际墙插读数;SFP+ 光模块、DAC/AOC,尤其
10GBASE-T SFP+ 模块,会另增功耗和热量。对于本网络,用被动 DAC 或短距光模块连接 10G
设备,通常比全 RJ45 10G 核心更容易保持低温、低噪。
`SG3210X-M2` 的上表数据对应 TP-Link 的 `UN 1.20` 数据表;不同地区/硬件版本的包装、
认证和功耗标注可能不同,购买中国零售版本前应让卖家确认**准确硬件版本、保修渠道和固件地区**。
本次未找到 TP-Link 中国官网的该精确型号页,因此不能把海外官方页面当作大陆现货/售后承诺。
MikroTik 同样应通过其官方零售商查询渠道确认本地库存和保修。两台购买前还应确认所选
SFP+/DAC 的兼容清单。
来源:[TP-Link 产品规格](https://www.tp-link.com/uk/business-networking/omada-switch-access-pro/sg3210x-m2/)
[TP-Link `UN 1.20` 数据表](https://static.tp-link.com/upload/product-overview/2025/202512/20251224/SG3210X-M2%28UN%29%201.20_datasheet.pdf)
[MikroTik 产品页](https://mikrotik.com/product/crs310_8g_2s_in)
[MikroTik 用户手册](https://help.mikrotik.com/docs/spaces/UM/pages/214630429/CRS310-8G%2B2S%2BIN)。
@@ -0,0 +1,6 @@
# API keys
## pi
```
sk-WxUkJJ8kRv4hLDUV3utBws8NJZ3GyN1bed1VNs0WwWSJ671n
```
@@ -21,3 +21,8 @@ hermes :
```
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
```
pi:
```
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
```