添加:ZHub 管理接口文档和客户端使用指南
This commit is contained in:
421
docs/tutorial-extras/troubleshooting.md
Normal file
421
docs/tutorial-extras/troubleshooting.md
Normal file
@@ -0,0 +1,421 @@
|
||||
---
|
||||
sidebar_position: 10
|
||||
title: 故障排除
|
||||
description: ZHub 常见问题和解决方案
|
||||
---
|
||||
|
||||
# 故障排除
|
||||
|
||||
本文档提供了 ZHub 使用过程中常见问题的诊断和解决方案。
|
||||
|
||||
---
|
||||
|
||||
## 连接问题
|
||||
|
||||
### 1. 客户端连接失败
|
||||
|
||||
**症状**:
|
||||
- 客户端无法连接到 ZHub 服务
|
||||
- 连接超时或连接被拒绝
|
||||
|
||||
**可能原因**:
|
||||
- 服务未启动
|
||||
- 端口被占用
|
||||
- 网络连接问题
|
||||
- 防火墙阻止连接
|
||||
|
||||
**诊断步骤**:
|
||||
```bash
|
||||
# 1. 检查服务是否运行
|
||||
ps aux | grep zhub
|
||||
|
||||
# 2. 检查端口是否监听
|
||||
netstat -tulpn | grep :1216
|
||||
netstat -tulpn | grep :711
|
||||
|
||||
# 3. 测试端口连通性
|
||||
telnet 127.0.0.1 1216
|
||||
telnet 127.0.0.1 711
|
||||
|
||||
```
|
||||
|
||||
**解决方案**:
|
||||
```bash
|
||||
# 启动服务
|
||||
./zhub.sh
|
||||
|
||||
# 检查配置文件
|
||||
cat app.ini
|
||||
|
||||
# 修改端口(如果冲突)
|
||||
# 编辑 app.ini 文件
|
||||
[service]
|
||||
addr=0.0.0.0:1217 # 修改端口
|
||||
watch=0.0.0.0:712 # 修改管理端口
|
||||
```
|
||||
|
||||
### 2. 连接频繁断开
|
||||
|
||||
**症状**:
|
||||
- 客户端连接后频繁断开重连
|
||||
- 日志中出现连接异常
|
||||
|
||||
**可能原因**:
|
||||
- 网络不稳定
|
||||
- 服务端资源不足
|
||||
- 客户端配置问题
|
||||
|
||||
**解决方案**:
|
||||
```java
|
||||
// 客户端配置优化
|
||||
ZHubClient zhub = new ZHubClient(
|
||||
"127.0.0.1:1216",
|
||||
"groupid",
|
||||
"appid",
|
||||
"token"
|
||||
);
|
||||
|
||||
// 重新创建客户端连接(使用正确的参数)
|
||||
zhub = new ZHubClient("127.0.0.1:1216", "groupid", "appid", "token");
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 权限问题
|
||||
|
||||
### 1. 认证失败
|
||||
|
||||
**症状**:
|
||||
- 客户端连接时提示认证失败
|
||||
- 日志显示 "invalid or expired token"
|
||||
|
||||
**可能原因**:
|
||||
- Token 过期
|
||||
- Token 格式错误
|
||||
- 权限配置错误
|
||||
|
||||
**诊断步骤**:
|
||||
```bash
|
||||
# 1. 检查权限配置
|
||||
curl http://127.0.0.1:711/_/info
|
||||
|
||||
# 2. 检查 auth.yml 文件
|
||||
cat auth.yml
|
||||
|
||||
# 3. 重新加载权限配置
|
||||
curl http://127.0.0.1:711/auth/reload
|
||||
```
|
||||
|
||||
**解决方案**:
|
||||
```yaml
|
||||
# 更新 auth.yml 中的 token 过期时间
|
||||
tokens:
|
||||
- id: 1
|
||||
user_id: 1
|
||||
token: "token-12345"
|
||||
expiration: "2030-12-31T23:59:59Z" # 延长过期时间
|
||||
status: "active"
|
||||
```
|
||||
|
||||
### 2. Topic 权限不足
|
||||
|
||||
**症状**:
|
||||
- 无法订阅或发布特定 Topic
|
||||
- 权限验证失败
|
||||
|
||||
**解决方案**:
|
||||
```yaml
|
||||
# 在 auth.yml 中添加权限
|
||||
users:
|
||||
- id: 2
|
||||
username: "client-001"
|
||||
reads: ["user.*", "order.*"] # 添加读取权限
|
||||
writes: ["user.*"] # 添加写入权限
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 消息问题
|
||||
|
||||
### 1. 消息丢失
|
||||
|
||||
**症状**:
|
||||
- 发送的消息未被接收
|
||||
- 消息处理不完整
|
||||
|
||||
**可能原因**:
|
||||
- 网络问题
|
||||
- 客户端处理异常
|
||||
- 服务端资源不足
|
||||
|
||||
**诊断步骤**:
|
||||
```bash
|
||||
# 1. 检查服务状态
|
||||
curl http://127.0.0.1:711/_/info
|
||||
|
||||
# 2. 查看服务日志
|
||||
tail -f zhub.log
|
||||
|
||||
# 3. 检查内存使用
|
||||
curl http://127.0.0.1:711/_/cleanup
|
||||
```
|
||||
|
||||
**解决方案**:
|
||||
```java
|
||||
// 客户端消息处理优化
|
||||
zhub.subscribe("topic-name", message -> {
|
||||
try {
|
||||
// 处理消息
|
||||
processMessage(message);
|
||||
} catch (Exception e) {
|
||||
logger.error("消息处理失败", e);
|
||||
// 记录失败消息,后续重试
|
||||
}
|
||||
});
|
||||
```
|
||||
|
||||
|
||||
---
|
||||
|
||||
## RPC 问题
|
||||
|
||||
### 1. RPC 调用超时
|
||||
|
||||
**症状**:
|
||||
- RPC 调用长时间无响应
|
||||
- 超时异常
|
||||
|
||||
**可能原因**:
|
||||
- 服务端处理时间过长
|
||||
- 网络延迟
|
||||
- 服务端异常
|
||||
|
||||
**解决方案**:
|
||||
```java
|
||||
// RPC 调用(基础版本)
|
||||
RpcResult<String> result = zhub.rpc("rpc-topic", "data", IType.STRING);
|
||||
if (result.getRetcode() == 0) {
|
||||
System.out.println("RPC 调用成功: " + result.getResult());
|
||||
} else {
|
||||
System.err.println("RPC 调用失败: " + result.getRetmsg());
|
||||
}
|
||||
```
|
||||
|
||||
### 2. RPC 调用失败
|
||||
|
||||
**症状**:
|
||||
- RPC 调用返回错误码
|
||||
- 服务端未响应
|
||||
|
||||
**诊断步骤**:
|
||||
```java
|
||||
// 检查 RPC 结果
|
||||
RpcResult<String> result = zhub.rpc("rpc-topic", "data", IType.STRING);
|
||||
if (result.getRetcode() != 0) {
|
||||
logger.error("RPC 调用失败: code={}, msg={}",
|
||||
result.getRetcode(), result.getRetmsg());
|
||||
}
|
||||
```
|
||||
|
||||
**解决方案**:
|
||||
```java
|
||||
// 服务端 RPC 处理优化
|
||||
zhub.rpcSubscribe("rpc-topic", IType.STRING, request -> {
|
||||
try {
|
||||
String data = request.getValue();
|
||||
// 处理业务逻辑
|
||||
String result = processData(data);
|
||||
return request.render(result);
|
||||
} catch (Exception e) {
|
||||
logger.error("RPC 处理异常", e);
|
||||
return request.retError("服务处理失败: " + e.getMessage());
|
||||
}
|
||||
});
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 性能问题
|
||||
|
||||
### 1. 内存使用过高
|
||||
|
||||
**症状**:
|
||||
- 服务端内存持续增长
|
||||
- 系统响应变慢
|
||||
|
||||
**诊断步骤**:
|
||||
```bash
|
||||
# 1. 检查内存使用
|
||||
free -h
|
||||
top -p $(pgrep zhub)
|
||||
|
||||
# 2. 查看服务状态
|
||||
curl http://127.0.0.1:711/_/info
|
||||
|
||||
# 3. 清理内存
|
||||
curl http://127.0.0.1:711/_/cleanup
|
||||
```
|
||||
|
||||
**解决方案**:
|
||||
```ini
|
||||
# 优化 app.ini 配置
|
||||
[log]
|
||||
level=info # 降低日志级别
|
||||
handlers=file # 使用文件日志
|
||||
|
||||
[data]
|
||||
dir=./data # 确保数据目录存在
|
||||
```
|
||||
|
||||
### 2. 消息处理缓慢
|
||||
|
||||
**症状**:
|
||||
- 消息处理延迟增加
|
||||
- 系统吞吐量下降
|
||||
|
||||
**解决方案**:
|
||||
```java
|
||||
// 使用异步处理
|
||||
zhub.subscribe("topic-name", message -> {
|
||||
CompletableFuture.runAsync(() -> {
|
||||
processMessage(message);
|
||||
});
|
||||
});
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 定时任务问题
|
||||
|
||||
### 1. 定时任务不执行
|
||||
|
||||
**症状**:
|
||||
- 配置的定时任务未执行
|
||||
- 任务状态异常
|
||||
|
||||
**诊断步骤**:
|
||||
```bash
|
||||
# 1. 检查数据库连接
|
||||
curl http://127.0.0.1:711/_/info
|
||||
|
||||
# 2. 重新加载定时任务
|
||||
curl http://127.0.0.1:711/timer/reload
|
||||
|
||||
# 3. 检查数据库配置
|
||||
mysql -u root -p -e "SELECT * FROM zhub.tasktimer WHERE status = 10;"
|
||||
```
|
||||
|
||||
**解决方案**:
|
||||
```sql
|
||||
-- 检查定时任务配置
|
||||
SELECT timerid, name, expr, single, status FROM tasktimer;
|
||||
|
||||
-- 更新任务状态
|
||||
UPDATE tasktimer SET status = 10 WHERE name = 'task-name';
|
||||
|
||||
-- 检查时间表达式格式
|
||||
UPDATE tasktimer SET expr = '*/5 * * * * ?' WHERE name = 'task-name';
|
||||
```
|
||||
|
||||
### 2. 定时任务重复执行
|
||||
|
||||
**症状**:
|
||||
- 同一个定时任务被多次执行
|
||||
- 业务逻辑重复处理
|
||||
|
||||
**解决方案**:
|
||||
```sql
|
||||
-- 确保单实例执行
|
||||
UPDATE tasktimer SET single = 1 WHERE name = 'task-name';
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 分布式锁问题
|
||||
|
||||
### 1. 锁获取失败
|
||||
|
||||
**症状**:
|
||||
- 无法获取分布式锁
|
||||
- 业务逻辑无法执行
|
||||
|
||||
**解决方案**:
|
||||
```java
|
||||
// 优化锁获取逻辑
|
||||
public boolean processWithLock(String resourceKey) {
|
||||
Lock lock = zhub.tryLock(resourceKey, 10); // 10秒超时
|
||||
if (!lock.success()) {
|
||||
logger.warn("获取锁失败,资源被占用: {}", resourceKey);
|
||||
return false;
|
||||
}
|
||||
|
||||
try {
|
||||
// 执行业务逻辑
|
||||
processResource(resourceKey);
|
||||
return true;
|
||||
} finally {
|
||||
lock.unLock();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 2. 死锁问题
|
||||
|
||||
**症状**:
|
||||
- 系统卡死
|
||||
- 资源无法释放
|
||||
|
||||
**解决方案**:
|
||||
```java
|
||||
// 避免死锁的最佳实践
|
||||
public void safeProcess() {
|
||||
// 1. 避免嵌套锁
|
||||
// 2. 设置合理的超时时间
|
||||
// 3. 确保锁的释放
|
||||
|
||||
Lock lock1 = zhub.tryLock("resource1", 5);
|
||||
if (!lock1.success()) return;
|
||||
|
||||
try {
|
||||
Lock lock2 = zhub.tryLock("resource2", 5);
|
||||
if (!lock2.success()) return;
|
||||
|
||||
try {
|
||||
// 业务逻辑
|
||||
} finally {
|
||||
lock2.unLock();
|
||||
}
|
||||
} finally {
|
||||
lock1.unLock();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 监控和诊断
|
||||
|
||||
### 基础监控
|
||||
|
||||
```bash
|
||||
# 检查服务状态
|
||||
curl http://127.0.0.1:711/_/info
|
||||
|
||||
# 查看服务日志
|
||||
tail -f zhub.log
|
||||
|
||||
# 检查内存使用
|
||||
free -h
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 联系支持
|
||||
|
||||
如果遇到无法解决的问题,请提供:
|
||||
|
||||
1. **错误日志**: 完整的错误信息
|
||||
2. **配置信息**: app.ini 和 auth.yml 配置
|
||||
3. **复现步骤**: 详细的问题复现步骤
|
||||
|
||||
更多技术支持信息请参考 [FAQ 文档](./faq.md)。
|
||||
Reference in New Issue
Block a user