本篇内容提取自 zdocker 调研笔记的附属章节(2026-05-22)。涉及个人设备的字段已脱敏。
一、整体架构
浏览器 / APP
│ Cookie: token=xxx 或 zenithtoken=xxx
▼
OpenResty (:80/:5055/:5056)
│ Lua auth 脚本
│ ├── auth.lua → /auth/token(普通用户)
│ ├── auth_master.lua → /auth/token + 校验 id==1(管理员)
│ ├── auth2.lua → /auth/tokenwithoauth(第三方登录)
│ └── auth_pwdcheck.lua → /auth/pwdcheck(密码校验)
│
│ POST http://127.0.0.1:5055/auth/token
▼
zbasic (Go 进程)
│ 读取 SQLite user.db
│ 查询 user 表
│ 返回 JSON {id, username, is_master, lan_only, ...}
│
│ → 注入 ngx.var.auth_response
│ → proxy_pass 向后端服务
二、用户数据库
用户数据存于 SQLite /zspace/system/db/user.db:
CREATE TABLE "user" (
id INTEGER PRIMARY KEY,
username TEXT, -- 用户名(通常是手机号格式 + 'd' 后缀)
password TEXT, -- 密码哈希
is_master INTEGER, -- 1=管理员(设备所有者)
disable INTEGER, -- 1=禁用
lan_only INTEGER, -- 1=仅局域网访问
actived INTEGER, -- 1=已激活
authorize INTEGER, -- 授权级别(2=完全授权?)
avatar TEXT, -- 头像
nickname TEXT, -- 昵称
repass INTEGER, -- 是否需要重置密码
col1~col5, col01~col05 -- 预留扩展字段
);
username 的模式是 手机号 + ’d’ 后缀(示例形态如 13800000000d)。这是极空间的设备绑定机制:每台极空间设备只能被一个手机号绑定,该手机号的用户自动成为 is_master=1 的管理员。
三、设备认证
设备表 /zspace/system/db/device.db:
CREATE TABLE device (
id INTEGER PRIMARY KEY,
user_id INTEGER, -- 关联 user.id
did TEXT, -- 设备唯一标识(MD5)
dname TEXT, -- 设备名(如 "iPhone xxx")
dua TEXT, -- User-Agent 完整字符串
plat TEXT, -- mobile / pc
is_trust INTEGER, -- 0=受信任(已知设备), 1=不受信任
created_at INTEGER,
updated_at INTEGER
);
实测设备上登记了两台受信任终端:一部手机(mobile, is_trust=0)和一台桌面客户端(pc, is_trust=0,Electron 应用)。
四、认证流程
标准认证链路(auth.lua / auth2.lua):
1. Cookie 校验
- 读取请求中的 Cookie
- auth.lua 兼容 zenithtoken → token 重写
2. POST /auth/token
- 将所有 Cookie 以 application/x-www-form-urlencoded 格式
- POST 到 http://127.0.0.1:5055/auth/token
- zbasic 处理:查 user.db,校验 token/password
3. 权限判定
- auth.lua: code==200 即可(任意有效用户)
- auth_master.lua: code==200 + id==1(必须是管理员)
- auth2.lua: 走 /auth/tokenwithoauth(第三方OAuth)
4. 注入 auth_response
- 成功后将用户 JSON 写入 ngx.var.auth_response
- 后端服务通过 Auth-Response 头获取用户信息
- 典型格式:{"id":1,"username":"<手机号>d","is_master":1,...}
密码校验(auth_pwdcheck.lua):
用于敏感操作(如删除文件、修改设置)的二次验证。先从 Cookie 取出 token,再从 POST body 取出密码,一起发给 /auth/pwdcheck。
五、设备绑定流程
极空间的设备没有传统的"注册账号"流程,核心是 设备绑定:
- 设备硬件身份:每台设备有一对 RSA 密钥(
/zspace/system/private/privkey+pubkey)和唯一序列号(如T020开头的 T2 序列号) - 服务器公钥:
/zspace/system/private/server_pubkey是极空间云端的 RSA 公钥,用来验证云端下发的指令 - 手机绑定:用户通过极空间 APP 扫描设备二维码,云端将用户手机号与设备序列号绑定
- 自动登录:绑定的手机 APP 通过
zenithtoken(极空间云端发放的 token)访问设备 - 多设备信任:同一用户可在多台终端登录(device.db 记录所有受信终端)
六、权限控制
| 权限层级 | 控制方式 | 位置 |
|---|---|---|
| 用户级别 | is_master:管理员 / 普通用户 | user.db |
| 网络限制 | lan_only:仅局域网 / 任意网络 | user.db |
| 路由级别 | auth_master.lua 仅允许 id==1 | OpenResty location |
| 操作级别 | auth_pwdcheck.lua 二次密码验证 | OpenResty location |
| 设备信任 | is_trust:新设备需短信验证 | device.db |
| 资源级别 | perms 表(相册共享权限等) | 各应用自己的 DB |
七、SSH root 与用户体系的关系
逆向分析用的 root SSH 登录和极空间的用户体系完全无关。root 是 Linux 系统级的超级用户,通过 SSH 直接登录,绕过了整个 OpenResty + zbasic 认证链。
- 极空间的用户体系运行在 应用层(Lua → zbasic → SQLite)
- root SSH 登录运行在 系统层(sshd → /etc/shadow → PAM)
- 两套体系互不干扰,root 可以看到 user.db 里的数据但不受它限制
正常流程下,极空间的普通用户(包括管理员)通过 APP/PC 客户端访问,走 Cookie → Lua → zbasic 这条链路,永远不会接触到 SSH 和 root。