# X-Server Mobile 企业工具系统 ## 项目概述 一个基于飞书的企业内部H5移动工具平台,采用多租户架构,支持审批流程引擎和多种业务应用。 **技术栈:** - 前端:React 18 + TypeScript + Vite + Ant Design Mobile - 后端:PHP 8.5 + Webman 2.x + MySQL + Redis - 部署:Docker + OpenResty + frpc (开发环境) **支持语言:** - 🇨🇳 简体中文 (zh) - 🇬🇧 English (en) - 🇷🇺 Русский (ru) - 🇪🇸 Español (es) - 🇫🇷 Français (fr) ## 国际化 (i18n) ### 前端国际化 **位置:** `frontend/src/i18n/` **使用方式:** ```tsx import { useTranslation } from 'react-i18next' function MyComponent() { const { t } = useTranslation() return
{t('common.confirm')}
} ``` **切换语言:** ```tsx import { showLanguageSwitcher } from '@/components/LanguageSwitcher' // 显示语言选择弹窗 showLanguageSwitcher() ``` **语言存储:** 浏览器 localStorage,键名为 `i18nextLng` ### 后端国际化 **位置:** `backend/lang/` **使用方式:** ```php use App\Util\Lang; // 获取翻译 $message = Lang::get('common.confirm'); // 带参数的翻译 $message = Lang::get('approval.status', ['status' => 'pending']); // 检查翻译是否存在 if (Lang::has('common.submit')) { // ... } ``` **设置语言:** ```php // 从请求检测语言 $locale = Lang::detectFromRequest(); Lang::setLocale($locale); ``` ## 项目关键特性 ### 1. 多租户架构 - 用户全局唯一,关联多个公司 - 租户切换功能 - 公司级数据隔离 ### 2. 审批流程引擎 **支持节点类型:** - 单人审批 (single_approve) - 会签 (and_sign) - 所有人通过 - 或签 (or_sign) - 任一人通过 - 通知节点 (notify) **审批状态:** - pending: 待审批 - approved: 已通过 - rejected: 已拒绝 - cancelled: 已撤销 **关键文件:** - `backend/app/Service/ApprovalService.php` - 审批核心逻辑 - `backend/app/Model/ApprovalOrder.php` - 审批单模型 - `frontend/src/modules/approval/` - 前端审批模块 ### 3. 飞书集成 **飞书免登:** - 回调地址:`/api/v1/auth/feishu-login` - 配置项: - `FEISHU_APP_ID` - 飞书应用 ID - `FEISHU_APP_SECRET` - 飞书应用密钥 - `FEISHU_ENCRYPT_KEY` - 加密密钥 - `FEISHU_VERIFICATION_TOKEN` - 验证令牌 ### 4. 数据库设计 **核心表:** - `users` - 用户表(全局唯一) - `companies` - 公司表 - `user_company` - 用户公司关联表 - `approval_flows` - 审批流程定义 - `approval_nodes` - 审批节点 - `approval_orders` - 审批单 - `approval_records` - 审批记录 - `business_trips` - 出差申请 - `business_trip_items` - 出差明细 ## 目录结构 ``` x-server-mobile/ ├── frontend/ # React 前端 │ ├── src/ │ │ ├── i18n/ # 国际化配置 │ │ │ ├── locales/ # 翻译文件 │ │ │ └── index.ts │ │ ├── components/ # 通用组件 │ │ │ ├── layout/ # 布局组件 │ │ │ └── LanguageSwitcher/ │ │ ├── modules/ # 业务模块 │ │ │ └── approval/ # 审批模块 │ │ ├── pages/ # 页面组件 │ │ ├── stores/ # 状态管理 │ │ ├── router/ # 路由配置 │ │ └── utils/ # 工具函数 │ └── package.json ├── backend/ # PHP 后端 │ ├── app/ │ │ ├── Controller/ # 控制器 │ │ ├── Model/ # 数据模型 │ │ ├── Service/ # 业务逻辑 │ │ ├── Util/ # 工具类 │ │ │ ├── Lang.php # 国际化工具 │ │ │ └── Db.php # 数据库连接 │ │ └── Middleware/ # 中间件 │ ├── config/ # 配置文件 │ ├── lang/ # 语言文件 │ ├── database/migrations/ # 数据库迁移 │ ├── composer.json │ └── Dockerfile ├── docker-compose.yml # Docker 编排 ├── nginx/ # OpenResty 配置 ├── frpc/ # frpc 配置 └── IMPLEMENTATION_PLAN.md # 实现计划 ``` ## 开发环境设置 ### 端口分配 | 服务 | 端口 | |------|------| | Frontend (Vite) | 5173 | | Backend (Webman) | 8787 | | OpenResty | 8080 | | MySQL | 3306 | | Redis | 6379 | ### 环境变量 **前端 (frontend/.env):** ```env VITE_API_BASE_URL=http://localhost:8787/api/v1 ``` **后端 (backend/.env):** ```env DB_HOST=mysql DB_PORT=3306 DB_DATABASE=x_server_mobile DB_USERNAME=root DB_PASSWORD=mysql_xEsdPa REDIS_HOST=redis REDIS_PORT=6379 APP_DEBUG=true # 飞书配置 FEISHU_APP_ID=cli_xxxxxxxxxxxxx FEISHU_APP_SECRET=xxxxxxxxxxxxxxxxxxxx FEISHU_ENCRYPT_KEY=xxxxxxxxxxxxxxxxxxxx FEISHU_VERIFICATION_TOKEN=xxxxxxxxxxxxxxxxxxxx ``` ### 反向代理配置(开发环境) **frpc 配置:** `frpc/frpc-dev.ini` ```ini [common] server_addr = your-frp-server.com server_port = 7000 token = your-frp-token [x-server-api-dev] type = http local_ip = 127.0.0.1 local_port = 8080 custom_domains = api-dev.x-server.your-domain.com ``` **OpenResty 配置:** `nginx/x-server-api.conf` ```nginx server { listen 8080; server_name api.x-server.local; location /api/ { proxy_pass http://127.0.0.1:8787/api/; add_header Access-Control-Allow-Origin *; add_header Access-Control-Allow-Methods 'GET, POST, PUT, DELETE, OPTIONS'; add_header Access-Control-Allow-Headers 'DNT,X-Mx-ReqToken,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Authorization,X-Tenant-Key'; } } ``` ## API 接口 ### 认证接口 - `POST /api/v1/auth/login` - 用户名密码登录 - `POST /api/v1/auth/feishu-login` - 飞书免登 ### 用户接口 - `GET /api/v1/user/info` - 获取用户信息 - `GET /api/v1/user/menu` - 获取用户菜单 - `GET /api/v1/user/companies` - 获取公司列表 - `POST /api/v1/user/switch-company` - 切换公司 ### 审批接口 - `GET /api/v1/approval/list` - 审批列表 - `GET /api/v1/approval/detail/{id}` - 审批详情 - `POST /api/v1/approval/submit` - 提交审批 - `POST /api/v1/approval/approve/{id}` - 审批通过 - `POST /api/v1/approval/reject/{id}` - 审批拒绝 - `POST /api/v1/approval/cancel/{id}` - 撤销申请 ### 出差接口 - `GET /api/v1/business-trip/list` - 出差列表 - `GET /api/v1/business-trip/detail/{id}` - 出差详情 - `POST /api/v1/business-trip/apply` - 申请出差 - `PUT /api/v1/business-trip/{id}` - 更新申请 ## 开发指南 ### 前端开发 ```bash cd frontend npm install # 安装依赖 npm run dev # 启动开发服务器 npm run build # 构建生产版本 ``` ### 后端开发 ```bash cd backend composer install # 安装依赖 php start.php start # 启动 Webman php start.php stop # 停止 Webman ``` ### Docker 开发 ```bash # 启动所有服务 docker compose up -d # 仅启动后端 docker compose up -d backend # 查看日志 docker logs x-server-backend -f # 重启服务 docker compose restart backend ``` ## 常见问题 ### Q: 如何添加新的翻译文本? **前端:** 在 `frontend/src/i18n/locales/` 对应语言的 JSON 文件中添加 ```json { "myModule": { "myKey": "翻译文本" } } ``` **后端:** 在 `backend/lang/` 对应语言的 PHP 文件中添加 ```php return [ 'myModule' => [ 'myKey' => '翻译文本', ], ]; ``` ### Q: 如何添加新的应用模块? 1. 在 `frontend/src/pages/` 创建新页面 2. 在 `frontend/src/router/index.tsx` 添加路由 3. 在 `backend/app/Controller/` 创建控制器 4. 在 `backend/config/route.php` 添加 API 路由 ### Q: 数据库连接失败怎么办? 1. 检查 MySQL 容器是否运行:`docker ps | grep mysql` 2. 检查数据库配置:`backend/.env` 3. 检查网络连接:`docker network ls | grep 1panel-network` ### Q: 前端页面白屏? 1. 检查浏览器控制台错误 2. 检查 React 版本:确保是 18.3.1 3. 检查路由配置 4. 尝试清除缓存:`rm -rf frontend/node_modules/.vite` ## 安全建议 1. **生产环境务必使用 HTTPS** 2. **定期更新依赖包** 3. **配置防火墙规则** 4. **使用强密码** 5. **定期备份数据库** 6. **不要在代码中硬编码敏感信息** ## 更新日志 ### 2024-02-24 - ✅ 升级 PHP 到 8.5 - ✅ 添加 5 语言国际化支持 - ✅ 配置 Docker 开发环境 - ✅ 实现审批流程引擎基础框架 - ✅ 完成前端基础页面和路由