修复系统概览数据不准确的查询。修复交叉评查意见列表的数量查询。优化全局消息提示的层级。优化提交意见进行局部更新。
This commit is contained in:
@@ -0,0 +1,213 @@
|
||||
# 动态客户端配置使用指南
|
||||
|
||||
## 🎯 概述
|
||||
|
||||
本项目支持通过Nginx代理自动识别客户端,无需手动设置环境变量。Nginx会在请求头中传递 `X-Client-ID`,前端应用会自动读取并使用对应的配置。
|
||||
|
||||
## 🔧 工作原理
|
||||
|
||||
```
|
||||
用户访问 → Nginx代理 → 添加X-Client-ID头部 → 前端应用 → 动态获取配置
|
||||
```
|
||||
|
||||
### 端口映射
|
||||
|
||||
| 端口 | 客户端ID | 说明 |
|
||||
|------|----------|------|
|
||||
| 5174 | client-a | 客户端A |
|
||||
| 5175 | client-b | 客户端B |
|
||||
| 5176 | client-c | 客户端C |
|
||||
| 5177 | client-d | 客户端D |
|
||||
|
||||
## 📁 相关文件
|
||||
|
||||
### 核心配置文件
|
||||
- `app/config/api-config.ts` - API配置管理(已更新支持动态配置)
|
||||
- `nginx-ubuntu-optimized.conf` - Nginx配置文件
|
||||
|
||||
### 新增工具文件
|
||||
- `app/utils/client-detection.ts` - 客户端检测工具函数
|
||||
- `app/examples/dynamic-config-usage.ts` - 使用示例
|
||||
- `app/routes/test.client-config.tsx` - 配置测试页面
|
||||
|
||||
## 🚀 使用方法
|
||||
|
||||
### 1. 在Remix Loader中使用
|
||||
|
||||
```typescript
|
||||
import type { LoaderFunctionArgs } from '@remix-run/node';
|
||||
import { getApiConfig, getApiBaseUrl } from '~/config/api-config';
|
||||
|
||||
export async function loader({ request }: LoaderFunctionArgs) {
|
||||
// 方法1: 获取完整配置
|
||||
const config = getApiConfig(request);
|
||||
|
||||
// 方法2: 获取特定配置项
|
||||
const baseUrl = getApiBaseUrl(request);
|
||||
|
||||
// 使用动态配置进行API调用
|
||||
const response = await fetch(`${baseUrl}/api/data`);
|
||||
const data = await response.json();
|
||||
|
||||
return { data };
|
||||
}
|
||||
```
|
||||
|
||||
### 2. 在Action中使用
|
||||
|
||||
```typescript
|
||||
import type { ActionFunctionArgs } from '@remix-run/node';
|
||||
import { getUploadUrl } from '~/config/api-config';
|
||||
|
||||
export async function action({ request }: ActionFunctionArgs) {
|
||||
const uploadUrl = getUploadUrl(request);
|
||||
const formData = await request.formData();
|
||||
|
||||
const response = await fetch(uploadUrl, {
|
||||
method: 'POST',
|
||||
body: formData
|
||||
});
|
||||
|
||||
return await response.json();
|
||||
}
|
||||
```
|
||||
|
||||
### 3. OAuth重定向URL生成
|
||||
|
||||
```typescript
|
||||
import { getOAuthConfig } from '~/config/api-config';
|
||||
|
||||
export function generateOAuthUrl(request: Request): string {
|
||||
const oauthConfig = getOAuthConfig(request);
|
||||
|
||||
const params = new URLSearchParams({
|
||||
client_id: oauthConfig.clientId,
|
||||
redirect_uri: oauthConfig.redirectUri,
|
||||
response_type: 'code'
|
||||
});
|
||||
|
||||
return `${oauthConfig.serverUrl}/oauth/authorize?${params.toString()}`;
|
||||
}
|
||||
```
|
||||
|
||||
## 🧪 测试验证
|
||||
|
||||
### 1. 访问测试页面
|
||||
|
||||
通过不同端口访问测试页面来验证配置:
|
||||
|
||||
```bash
|
||||
# 客户端A
|
||||
http://localhost:5174/test/client-config
|
||||
|
||||
# 客户端B
|
||||
http://localhost:5175/test/client-config
|
||||
|
||||
# 客户端C
|
||||
http://localhost:5176/test/client-config
|
||||
|
||||
# 客户端D
|
||||
http://localhost:5177/test/client-config
|
||||
```
|
||||
|
||||
### 2. 检查配置状态
|
||||
|
||||
测试页面会显示:
|
||||
- ✅ Nginx代理是否正常工作
|
||||
- ✅ 客户端识别是否成功
|
||||
- ✅ 配置匹配是否正确
|
||||
|
||||
### 3. 验证请求头
|
||||
|
||||
在浏览器开发者工具中检查网络请求,确认包含:
|
||||
- `X-Client-ID`: 对应的客户端标识
|
||||
- `X-Original-Port`: 原始端口号
|
||||
- `X-Forwarded-Port`: 转发端口号
|
||||
|
||||
## 🔍 调试信息
|
||||
|
||||
### 查看Nginx日志
|
||||
|
||||
```bash
|
||||
# 查看客户端A的访问日志
|
||||
sudo tail -f /var/log/nginx/client-a-access.log
|
||||
|
||||
# 查看客户端D的访问日志
|
||||
sudo tail -f /var/log/nginx/client-d-access.log
|
||||
```
|
||||
|
||||
### 使用调试工具
|
||||
|
||||
```typescript
|
||||
import { detectClientFromRequest, getRequestDebugInfo } from '~/utils/client-detection';
|
||||
|
||||
export async function loader({ request }: LoaderFunctionArgs) {
|
||||
const clientId = detectClientFromRequest(request);
|
||||
const debugInfo = getRequestDebugInfo(request);
|
||||
|
||||
console.log('🔧 调试信息:', { clientId, debugInfo });
|
||||
|
||||
// ... 其他逻辑
|
||||
}
|
||||
```
|
||||
|
||||
## ⚠️ 注意事项
|
||||
|
||||
### 1. 兼容性
|
||||
- 保持了原有的静态配置导出,确保现有代码不受影响
|
||||
- 新的动态配置函数是可选的,可以逐步迁移
|
||||
|
||||
### 2. 环境要求
|
||||
- 需要Nginx正确配置并运行
|
||||
- 确保 `nginx-ubuntu-optimized.conf` 配置文件已应用
|
||||
|
||||
### 3. 错误处理
|
||||
- 如果无法检测到客户端ID,会回退到默认值 'main'
|
||||
- 如果Nginx未正确配置,仍可通过环境变量设置客户端ID
|
||||
|
||||
## 🔄 迁移指南
|
||||
|
||||
### 从环境变量迁移到动态配置
|
||||
|
||||
**之前(需要设置环境变量):**
|
||||
```bash
|
||||
# .env文件
|
||||
NEXT_PUBLIC_CLIENT_ID=client-d
|
||||
```
|
||||
|
||||
**现在(自动检测):**
|
||||
```typescript
|
||||
// 在loader中
|
||||
const config = getApiConfig(request); // 自动从请求头获取客户端ID
|
||||
```
|
||||
|
||||
### 更新现有代码
|
||||
|
||||
1. **替换静态配置调用:**
|
||||
```typescript
|
||||
// 旧方式
|
||||
import { API_BASE_URL } from '~/config/api-config';
|
||||
|
||||
// 新方式
|
||||
import { getApiBaseUrl } from '~/config/api-config';
|
||||
const baseUrl = getApiBaseUrl(request);
|
||||
```
|
||||
|
||||
2. **在loader/action中传递request:**
|
||||
```typescript
|
||||
// 确保所有需要配置的地方都能访问到request对象
|
||||
export async function loader({ request }: LoaderFunctionArgs) {
|
||||
const config = getApiConfig(request);
|
||||
// ...
|
||||
}
|
||||
```
|
||||
|
||||
## 🎉 优势
|
||||
|
||||
1. **无需手动配置** - 不再需要为每个客户端设置环境变量
|
||||
2. **自动识别** - 通过访问端口自动识别客户端
|
||||
3. **动态切换** - 同一个应用实例支持多个客户端
|
||||
4. **向后兼容** - 现有代码无需修改即可继续工作
|
||||
5. **易于调试** - 提供完整的调试信息和测试页面
|
||||
|
||||
现在你可以直接通过 `http://localhost:5177` 访问应用,系统会自动识别为 `client-d` 并使用对应的配置!
|
||||
Reference in New Issue
Block a user