# Service Party App - 分布式共管钱包桌面应用 ## 概述 Service Party App 是一个**跨平台 Electron 桌面应用**,用于参与分布式多方共管钱包的创建和签名过程。用户可以在各自的电脑上运行此应用,通过扫描邀请二维码或输入邀请码加入共管钱包创建会话,参与 TSS (Threshold Signature Scheme) 密钥生成协议。 ## 应用场景 ``` ┌─────────────────┐ ┌─────────────────┐ ┌─────────────────┐ │ Service Party │ │ Service Party │ │ Service Party │ │ App (用户A) │ │ App (用户B) │ │ App (用户C) │ └────────┬────────┘ └────────┬────────┘ └────────┬────────┘ │ │ │ │ 创建会话/生成邀请码 │ 输入邀请码加入 │ 输入邀请码加入 │ │ │ └───────────────────────┼───────────────────────┘ │ ┌────────────┴────────────┐ │ Account Service │ │ (HTTP API - 会话管理) │ └────────────┬────────────┘ │ ┌────────────┴────────────┐ │ Message Router │ │ (gRPC 消息路由) │ └────────────┬────────────┘ │ ┌────────────┴────────────┐ │ TSS Keygen/Sign │ │ (分布式密钥生成/签名) │ └─────────────────────────┘ ``` ### 典型使用流程 #### Keygen 流程 (密钥生成) 1. **发起方** 在 Service Party App 输入钱包名称和用户名称,创建共管钱包会话 2. **发起方** 获得邀请码 (格式: XXXX-XXXX-XXXX),分享给其他参与方 3. **参与方** 在各自电脑上打开 Service Party App,输入邀请码加入 4. **等待所有参与方就绪** (24小时超时) 5. **所有参与方到齐后**,自动开始 TSS 密钥生成协议 6. **完成后**,每个参与方在本地 SQLite 保存自己的加密 share #### Sign 流程 (签名) 1. **发起方** 从本地 SQLite 选择要签名的钱包 2. **发起方** 输入待签名的消息哈希,创建签名会话 3. **发起方** 获得签名邀请码,分享给其他参与方 (必须是 keygen 时的参与方) 4. **参与方** 输入邀请码加入签名会话 5. **等待足够数量的参与方** (threshold_t + 1 人,24小时超时) 6. **参与方到齐后**,自动开始 TSS 签名协议 7. **完成后**,返回签名结果,可用于广播交易 ## 目录结构 ``` backend/mpc-system/services/service-party-app/ ├── electron/ # Electron 主进程 │ ├── main.ts # 主进程入口 │ ├── preload.ts # 预加载脚本 (安全 IPC) │ └── modules/ │ ├── grpc-client.ts # gRPC 客户端 (连接 Message Router) │ ├── account-client.ts # HTTP 客户端 (连接 Account Service) │ ├── tss-handler.ts # TSS 协议处理器 │ ├── database.ts # 本地 SQLite 存储 (AES-256-GCM 加密) │ ├── address-derivation.ts # 地址派生 (多链支持) │ ├── kava-client.ts # Kava 区块链客户端 │ └── kava-tx-service.ts # Kava 交易构建服务 │ ├── src/ # React 前端 (渲染进程) │ ├── App.tsx # 应用入口 │ ├── pages/ │ │ ├── Home.tsx # 主页 - Share 列表 │ │ ├── Join.tsx # 加入会话页面 │ │ ├── Create.tsx # 创建会话页面 │ │ ├── Session.tsx # 会话进度页面 │ │ ├── Sign.tsx # 签名页面 │ │ └── Settings.tsx # 设置页面 │ ├── components/ # UI 组件 │ ├── stores/ │ │ └── appStore.ts # Zustand 状态管理 │ ├── types/ │ │ └── electron.d.ts # TypeScript 类型定义 │ └── utils/ │ └── address.ts # 地址工具函数 │ ├── tss-party/ # Go TSS 子进程 │ ├── main.go # TSS 协议执行程序 │ ├── go.mod # Go 模块定义 │ └── go.sum # 依赖锁定 │ ├── proto/ # gRPC Proto 文件 │ └── message_router.proto # Message Router 接口定义 │ ├── package.json # Node.js 依赖 ├── electron-builder.json # Electron 打包配置 ├── tsconfig.json # TypeScript 配置 ├── tsconfig.electron.json # Electron TypeScript 配置 ├── vite.config.ts # Vite 构建配置 └── build-windows.bat # Windows 一键编译脚本 ``` ## 技术架构 ### 技术栈 | 组件 | 技术 | 说明 | |------|------|------| | 桌面框架 | Electron 28+ | 跨平台支持 Windows/Mac/Linux | | 前端框架 | React 18 + TypeScript | 与 admin-web 保持一致 | | 构建工具 | Vite | 快速开发和构建 | | 状态管理 | Zustand | 轻量级状态管理 | | gRPC 客户端 | @grpc/grpc-js | Node.js gRPC 实现 (连接 Message Router) | | HTTP 客户端 | Fetch API | 连接 Account Service | | TSS 协议 | Go 子进程 | 使用 bnb-chain/tss-lib | | 本地存储 | sql.js (SQLite) | 纯 JavaScript SQLite 实现 | | 加密算法 | AES-256-GCM | Share 加密存储,PBKDF2 密钥派生 | | 打包工具 | electron-builder | 多平台打包 | ### 服务连接 ``` ┌─────────────────────────────────────────────────────────────┐ │ Service Party App │ │ ┌─────────────────────────────────────────────────────────┐│ │ │ main.ts ││ │ │ ┌──────────────┐ ┌──────────────┐ ┌──────────────┐ ││ │ │ │ grpcClient │ │accountClient │ │ database │ ││ │ │ │ (gRPC) │ │ (HTTP) │ │ (SQLite) │ ││ │ │ └──────┬───────┘ └──────┬───────┘ └──────────────┘ ││ │ │ │ │ ││ │ └─────────┼─────────────────┼──────────────────────────────┘│ └────────────┼─────────────────┼───────────────────────────────┘ │ │ │ gRPC (TLS) │ HTTPS ▼ ▼ ┌─────────────────┐ ┌─────────────────┐ │ Message Router │ │ Account Service │ │ (消息路由) │ │ (会话管理) │ └─────────────────┘ └─────────────────┘ ``` ### Account Service HTTP API Service Party App 通过 HTTP 调用 Account Service 管理会话: | 端点 | 方法 | 说明 | |------|------|------| | `/api/v1/co-managed/sessions` | POST | 创建 Keygen 会话 | | `/api/v1/co-managed/sessions/:sessionId/join` | POST | 加入会话 | | `/api/v1/co-managed/sessions/:sessionId` | GET | 获取会话状态 | | `/api/v1/co-managed/sessions/by-invite-code/:code` | GET | 通过邀请码查询会话 | | `/api/v1/co-managed/sign` | POST | 创建 Sign 会话 | | `/api/v1/co-managed/sign/by-invite-code/:code` | GET | 通过邀请码查询签名会话 | | `/health` | GET | 健康检查 | ### TSS 子进程架构 为什么使用 Go 子进程而不是 WASM? 1. **稳定性**: tss-lib 是复杂的密码学库,Go 原生执行比 WASM 更稳定 2. **性能**: 原生执行性能优于 WASM 3. **兼容性**: 避免 WASM 在不同平台的兼容性问题 4. **调试**: 更容易调试和排查问题 ``` ┌──────────────────────────────────────────────────────────────┐ │ Electron App (TypeScript) │ │ ┌────────────────────────────────────────────────────────┐ │ │ │ tss-handler.ts │ │ │ │ - 启动 Go 子进程 (spawn) │ │ │ │ - stdin/stdout JSON 消息通信 │ │ │ │ - 转发 gRPC 消息到子进程 │ │ │ │ - 接收子进程输出并处理 │ │ │ └───────────────────────┬────────────────────────────────┘ │ └──────────────────────────┼───────────────────────────────────┘ │ spawn + JSON IPC ▼ ┌──────────────────────────────────────────────────────────────┐ │ tss-party (Go 子进程) │ │ ┌────────────────────────────────────────────────────────┐ │ │ │ - 使用 bnb-chain/tss-lib v2 │ │ │ │ - 执行 GG20 Keygen 协议 (4 轮) │ │ │ │ - 执行 GG20 Signing 协议 │ │ │ │ - 通过 stdin 接收 MPC 消息 │ │ │ │ - 通过 stdout 发送 MPC 消息 │ │ │ │ - 完成后返回公钥 + 加密 share / 签名结果 │ │ │ └────────────────────────────────────────────────────────┘ │ └──────────────────────────────────────────────────────────────┘ ``` ### IPC 消息格式 Electron 主进程与 Go 子进程之间使用 JSON 消息通信: ```typescript // 发送给 Go 子进程的消息 interface IncomingMessage { type: 'incoming'; fromPartyIndex: number; isBroadcast: boolean; payload: string; // base64 encoded } // Go 子进程发出的消息 interface OutgoingMessage { type: 'outgoing' | 'result' | 'error' | 'progress'; isBroadcast?: boolean; toParties?: string[]; payload?: string; // base64 encoded publicKey?: string; // base64 encoded (keygen result) encryptedShare?: string; // base64 encoded (keygen result) signature?: string; // base64 encoded (sign result) partyIndex?: number; round?: number; totalRounds?: number; error?: string; } ``` ## 核心功能 ### 1. 加入会话 用户通过以下方式加入共管钱包创建/签名会话: - **输入邀请码**: 手动输入 12 位邀请码 (格式: XXXX-XXXX-XXXX) - **扫描二维码**: 使用摄像头扫描邀请二维码 (可选) - **粘贴邀请链接**: 手动粘贴邀请链接 (可选) ### 2. TSS 密钥生成 (Keygen) 参与 GG20 (Gennaro-Goldfeder 2020) 门限签名密钥生成协议: - 支持任意 T-of-N 阈值配置 - 4 轮消息交换 - 零知识证明保证安全性 - 每个参与方获得自己的 share,无需信任其他方 - 24 小时超时等待所有参与方 ### 3. TSS 签名 (Sign) 参与 GG20 门限签名协议: - 使用 Keygen 时保存的 share - 仅需 threshold_t + 1 个参与方即可签名 - 24 小时超时等待足够参与方 - 返回可用于广播的签名结果 ### 4. 本地 SQLite 存储 Share 使用 AES-256-GCM 加密后存储在本地 SQLite 数据库: ```typescript interface ShareRecord { id: string; // Share 唯一标识 (UUID) session_id: string; // Keygen 会话 ID wallet_name: string; // 钱包名称 party_id: string; // 参与方 ID party_index: number; // 参与方索引 threshold_t: number; // 签名阈值 threshold_n: number; // 总参与方数 public_key_hex: string; // 钱包公钥 (hex) encrypted_share: string; // AES-256-GCM 加密的 share created_at: string; // 创建时间 last_used_at: string | null; // 最后使用时间 participants_json: string; // JSON: 参与方列表 [{partyId, name}] } ``` **重要**: `participants_json` 字段存储了 Keygen 时所有参与方的信息,Sign 时必须从这里选择参与方。 ### 5. 地址派生 支持从公钥派生多链地址: - **Kava** (主链) - **Cosmos** 系列链 - **Ethereum** 兼容链 ### 6. Kava 交易 支持构建和广播 Kava 交易: - 查询余额 - 构建转账交易 (待 TSS 签名) - 广播已签名交易 - 查询交易状态 ### 7. 备份与恢复 - **导出备份**: 将加密的 share 导出为文件 - **导入恢复**: 从备份文件恢复 share - **密码保护**: 备份文件使用用户密码加密 ## 编译与运行 ### 前置条件 - Node.js 18+ - Go 1.21+ - npm 或 pnpm ### Windows 一键编译 ```bash cd backend/mpc-system/services/service-party-app build-windows.bat ``` ### 编译 TSS 子进程 ```bash # Windows cd backend/mpc-system/services/service-party-app/tss-party go build -o ../bin/win32-x64/tss-party.exe . # macOS (Intel) GOOS=darwin GOARCH=amd64 go build -o ../bin/darwin-x64/tss-party . # macOS (Apple Silicon) GOOS=darwin GOARCH=arm64 go build -o ../bin/darwin-arm64/tss-party . # Linux GOOS=linux GOARCH=amd64 go build -o ../bin/linux-x64/tss-party . ``` ### 开发模式 ```bash cd backend/mpc-system/services/service-party-app # 安装依赖 npm install # 启动开发服务器 npm run dev ``` ### 生产构建 ```bash # 构建前端 + Electron npm run build # 打包 Windows 安装包 npm run build:win # 输出目录: release/ ``` ## 配置 ### 设置页面配置项 | 配置项 | 说明 | 默认值 | |--------|------|--------| | Message Router 地址 | gRPC 服务地址 | mpc-grpc.szaiai.com:443 | | Account 服务地址 | HTTP API 地址 | https://api.szaiai.com | | 自动备份 | 创建 share 后自动备份 | false | | 备份目录 | 自动备份文件保存位置 | (空) | ## 安全考虑 ### Share 安全 1. **本地加密**: Share 使用 AES-256-GCM 加密存储 2. **密钥派生**: 加密密钥由用户密码通过 PBKDF2 派生 (100,000 次迭代) 3. **内存保护**: Share 在内存中的时间尽量短 4. **安全删除**: 删除 share 时同时删除派生地址和签名历史 ### 网络安全 1. **TLS 加密**: 与 Message Router 的 gRPC 连接使用 TLS (端口 443) 2. **HTTPS**: 与 Account Service 的 HTTP 连接使用 HTTPS 3. **消息签名**: MPC 消息包含签名验证 4. **会话隔离**: 每个会话使用独立的密钥对 ### 应用安全 1. **代码签名**: 发布的应用经过代码签名 2. **沙箱隔离**: Electron 渲染进程在沙箱中运行 3. **Context Isolation**: preload 脚本使用 contextBridge 安全暴露 API ## 与现有系统的集成 ### 与 Message Router 的通信 (gRPC) ``` Service Party App │ │ gRPC (TLS) ▼ ┌─────────────────────┐ │ Message Router │ │ ┌───────────────┐ │ │ │ RegisterParty │ │ ← 注册为参与方 │ │ Heartbeat │ │ ← 心跳保活 (30秒) │ │ JoinSession │ │ ← 加入会话 │ │ Subscribe │ │ ← 订阅消息 │ │ RouteMessage │ │ ← 发送消息 │ │ ReportDone │ │ ← 报告完成 │ └───────────────┘ │ └─────────────────────┘ ``` ### 与 Account Service 的通信 (HTTP) ``` Service Party App │ │ HTTPS ▼ ┌─────────────────────┐ │ Account Service │ │ ┌───────────────┐ │ │ │ CreateSession │ │ ← 创建 Keygen/Sign 会话 │ │ JoinSession │ │ ← 加入会话 │ │ GetSession │ │ ← 查询会话状态 │ │ ByInviteCode │ │ ← 通过邀请码查询 │ └───────────────┘ │ └─────────────────────┘ ``` ### 数据流 1. **Keygen 创建**: - App → Account Service: 创建会话,获取 session_id + invite_code - App → Message Router: RegisterParty - App → Message Router: SubscribeSessionEvents - 等待其他参与方加入... 2. **Keygen 加入**: - App → Account Service: 通过 invite_code 查询 session_id - App → Message Router: RegisterParty - App → Account Service: JoinSession - 等待所有参与方就绪... 3. **Keygen 执行**: - Message Router 通知所有参与方开始 - 各 App 启动 TSS 子进程 - 通过 Message Router 交换 MPC 消息 - 完成后各自保存 share 到本地 SQLite 4. **Sign 创建**: - App → SQLite: 读取 share 和 participants_json - App → Account Service: 创建签名会话,指定参与方列表 - 分享 invite_code 给其他参与方 5. **Sign 执行**: - 足够参与方加入后自动开始 - 通过 Message Router 交换 MPC 消息 - 完成后返回签名结果 ## 相关文档 - [共管钱包实现计划](./co-managed-wallet-implementation-plan.md) - [MPC 系统架构](../backend/mpc-system/docs/01-architecture.md) - [API 参考](../backend/mpc-system/docs/02-api-reference.md)