Browse Source

StartNetworkAsync 修复请求参数问题

feature/x1-web-request
hyh 2 days ago
parent
commit
cb73f9dad7
  1. 8
      src/X1.Application/Features/DeviceRuntimes/Commands/StartDeviceRuntime/StartDeviceRuntimeCommandHandler.cs
  2. 8
      src/X1.DynamicClientCore/Features/IInstrumentProtocolClient.cs
  3. 16
      src/X1.DynamicClientCore/Features/Service/InstrumentProtocolClient.cs
  4. 14
      src/X1.DynamicClientCore/Models/CellularNetworkRequest.cs
  5. 94
      src/modify.md

8
src/X1.Application/Features/DeviceRuntimes/Commands/StartDeviceRuntime/StartDeviceRuntimeCommandHandler.cs

@ -396,7 +396,13 @@ public class StartDeviceRuntimeCommandHandler : IRequestHandler<StartDeviceRunti
_logger.LogDebug("启动网络,设备代码: {DeviceCode}, 运行时代码: {RuntimeCode}", _logger.LogDebug("启动网络,设备代码: {DeviceCode}, 运行时代码: {RuntimeCode}",
networkRequest.DeviceCode, networkRequest.RuntimeCode); networkRequest.DeviceCode, networkRequest.RuntimeCode);
var startResult = await _protocolClient.StartNetworkAsync(networkRequest); // 创建包装请求对象
var request = new CellularNetworkRequest
{
CellularNetwork = networkRequest
};
var startResult = await _protocolClient.StartNetworkAsync(request);
_logger.LogDebug("网络启动结果,设备代码: {DeviceCode}, 启动成功: {StartResult}", _logger.LogDebug("网络启动结果,设备代码: {DeviceCode}, 启动成功: {StartResult}",
networkRequest.DeviceCode, startResult); networkRequest.DeviceCode, startResult);

8
src/X1.DynamicClientCore/Features/IInstrumentProtocolClient.cs

@ -20,14 +20,14 @@ namespace X1.DynamicClientCore.Features
/// <summary> /// <summary>
/// 启动网络连接 /// 启动网络连接
/// </summary> /// </summary>
/// <param name="instrumentNumber">仪器编号,用于标识特定的仪器设备</param> /// <param name="request">蜂窝网络启动请求</param>
/// <param name="options">请求选项,包含超时、请求头等配置</param> /// <param name="options">请求选项,包含超时、请求头等配置</param>
/// <param name="cancellationToken">取消令牌,用于取消异步操作</param> /// <param name="cancellationToken">取消令牌,用于取消异步操作</param>
/// <returns>异步任务,表示网络启动操作的完成状态</returns> /// <returns>异步任务,表示网络启动操作的完成状态</returns>
/// <exception cref="ArgumentNullException">当instrumentNumber为null或空时抛出</exception> /// <exception cref="ArgumentNullException">当request为null时抛出</exception>
/// <exception cref="ArgumentException">当instrumentNumber格式无效时抛出</exception> /// <exception cref="ArgumentException">当request中的设备编号为空时抛出</exception>
Task<bool> StartNetworkAsync( Task<bool> StartNetworkAsync(
CellularNetworkConfiguration cellular, CellularNetworkRequest request,
RequestOptions? options = null, RequestOptions? options = null,
CancellationToken cancellationToken = default); CancellationToken cancellationToken = default);

16
src/X1.DynamicClientCore/Features/Service/InstrumentProtocolClient.cs

@ -97,19 +97,23 @@ namespace X1.DynamicClientCore.Features.Service
/// <summary> /// <summary>
/// 启动网络连接 /// 启动网络连接
/// </summary> /// </summary>
/// <param name="instrumentNumber">设备编号</param> /// <param name="request">蜂窝网络启动请求</param>
/// <param name="options">请求选项</param> /// <param name="options">请求选项</param>
/// <param name="cancellationToken">取消令牌</param> /// <param name="cancellationToken">取消令牌</param>
/// <returns>异步任务</returns> /// <returns>异步任务</returns>
/// <exception cref="ArgumentException">当instrumentNumber为空或null时抛出</exception> /// <exception cref="ArgumentNullException">当request为null时抛出</exception>
/// <exception cref="ArgumentException">当request中的设备编号为空时抛出</exception>
public async Task<bool> StartNetworkAsync( public async Task<bool> StartNetworkAsync(
CellularNetworkConfiguration cellular, CellularNetworkRequest request,
RequestOptions? options = null, RequestOptions? options = null,
CancellationToken cancellationToken = default) CancellationToken cancellationToken = default)
{ {
string instrumentNumber = cellular.DeviceCode; if (request == null)
throw new ArgumentNullException(nameof(request));
string instrumentNumber = request.CellularNetwork?.DeviceCode;
if (string.IsNullOrWhiteSpace(instrumentNumber)) if (string.IsNullOrWhiteSpace(instrumentNumber))
throw new ArgumentException("设备编号不能为空", nameof(instrumentNumber)); throw new ArgumentException("设备编号不能为空", nameof(request));
try try
{ {
@ -121,7 +125,7 @@ namespace X1.DynamicClientCore.Features.Service
var response = await _dynamicHttpClient.PostAsync<ApiActionResult<NetworkStatus>>( var response = await _dynamicHttpClient.PostAsync<ApiActionResult<NetworkStatus>>(
instrumentNumber, instrumentNumber,
"CellularNetwork/generalStart", "CellularNetwork/generalStart",
cellular, request,
options, options,
cancellationToken); cancellationToken);
if (response == null) if (response == null)

14
src/X1.DynamicClientCore/Models/CellularNetworkRequest.cs

@ -0,0 +1,14 @@
namespace X1.DynamicClientCore.Models
{
/// <summary>
/// 蜂窝网络启动请求包装类
/// 用于匹配API文档要求的JSON结构
/// </summary>
public class CellularNetworkRequest
{
/// <summary>
/// 蜂窝网络配置
/// </summary>
public CellularNetworkConfiguration CellularNetwork { get; set; } = new();
}
}

94
src/modify.md

@ -5838,4 +5838,96 @@ private static DeviceRuntimeDto MapToDto(CellularDeviceRuntime runtime)
### 影响范围 ### 影响范围
- **编译错误**:修复了导致编译失败的语法错误 - **编译错误**:修复了导致编译失败的语法错误
- **PLMN处理**:改进了PLMN值的提取和处理逻辑 - **PLMN处理**:改进了PLMN值的提取和处理逻辑
- **错误处理**:增强了异常处理和日志记录功能 - **错误处理**:增强了异常处理和日志记录功能
---
## 2025-01-29 - 修复StartNetworkAsync API请求体结构不匹配问题
### 修改原因
根据API文档要求,`StartNetworkAsync` 方法发送的JSON请求体需要包含外层的 `cellularNetwork` 包装,但当前实现直接发送 `CellularNetworkConfiguration` 对象,导致请求体结构不匹配。
### 修改文件
- `X1.DynamicClientCore/Models/CellularNetworkRequest.cs` - 新增包装类
- `X1.DynamicClientCore/Features/IInstrumentProtocolClient.cs` - 修改接口签名
- `X1.DynamicClientCore/Features/Service/InstrumentProtocolClient.cs` - 修改实现方法
- `X1.Application/Features/DeviceRuntimes/Commands/StartDeviceRuntime/StartDeviceRuntimeCommandHandler.cs` - 修改调用方
### 修改内容
#### 1. 新增包装类
- **类名**: `CellularNetworkRequest`
- **功能**: 包装 `CellularNetworkConfiguration` 对象,匹配API文档要求的JSON结构
- **属性**: `CellularNetwork` - 包含实际的网络配置对象
#### 2. 修改接口签名
- **参数类型**: 将 `StartNetworkAsync` 方法的参数从 `CellularNetworkConfiguration` 改为 `CellularNetworkRequest`
- **参数验证**: 添加对 `request` 参数的 null 检查
- **文档更新**: 更新方法注释和异常说明
#### 3. 修改实现方法
- **参数处理**: 从 `request.CellularNetwork` 中提取设备编号
- **请求传递**: 直接将 `request` 对象传递给 `PostAsync` 方法
- **错误处理**: 增强参数验证和错误处理
#### 4. 修改调用方
- **包装创建**: 在调用 `StartNetworkAsync` 前创建 `CellularNetworkRequest` 包装对象
- **参数传递**: 将包装后的对象传递给协议客户端
#### 5. API文档匹配
**API文档要求的JSON结构**:
```json
{
"cellularNetwork": {
"deviceCode": "string",
"runtimeCode": "string",
"radioAccessNetworkConfiguration": "string",
"coreNetworkImsConfigurations": [...]
}
}
```
**修复后的实现**:
```csharp
// 调用方
var request = new CellularNetworkRequest
{
CellularNetwork = networkRequest
};
var startResult = await _protocolClient.StartNetworkAsync(request);
// 实现方
public async Task<bool> StartNetworkAsync(
CellularNetworkRequest request,
RequestOptions? options = null,
CancellationToken cancellationToken = default)
{
// 直接传递 request 对象给 PostAsync
var response = await _dynamicHttpClient.PostAsync<ApiActionResult<NetworkStatus>>(
instrumentNumber,
"CellularNetwork/generalStart",
request, // 使用包装后的请求对象
options,
cancellationToken);
}
```
### 技术要点
- **接口设计**: 将包装类作为接口参数,确保类型安全
- **序列化匹配**: 确保JSON序列化后的结构与API文档要求一致
- **参数验证**: 增强参数验证,提高代码健壮性
- **类型安全**: 使用强类型对象确保编译时类型检查
### 业务价值
- **API兼容性**: 确保与外部API的正确通信
- **请求成功**: 修复可能导致API调用失败的结构问题
- **调试便利**: 提供清晰的请求体结构,便于API调试
- **代码清晰**: 明确区分请求包装和实际配置对象
### 影响范围
- **接口变更**: 修改了 `IInstrumentProtocolClient` 接口的 `StartNetworkAsync` 方法签名
- **实现更新**: 更新了 `InstrumentProtocolClient` 的实现逻辑
- **调用方修改**: 修改了 `StartDeviceRuntimeCommandHandler` 中的调用方式
- **API调用**: 修复了网络启动API调用的请求体结构
- **序列化**: 改进了JSON序列化的结构匹配
- **兼容性**: 确保与外部系统的API兼容性
Loading…
Cancel
Save