Merge pull request 'dev_lx' (#19) from dev_lx into main

Reviewed-on: #19
pull/21/head
刘鑫 2 months ago
commit 188cb03904
  1. 21
      WeiCloud.Fusion/AlarmService/Alarm.DomainService/DahAlarm/DahuaGeneralCtlService.cs
  2. 2
      WeiCloud.Fusion/AlarmService/Alarm.DomainService/DahAlarm/IDahuaGeneralCtlService.cs
  3. 45
      WeiCloud.Fusion/AlarmService/AlarmService.API/Controllers/AlarmController.cs
  4. 82
      WeiCloud.Fusion/Common.SharedService/Common.Shared.Application/DaHua/ResponeDto/EventEnvelopeDto.cs

@ -2,6 +2,7 @@
using Common.Shared.DomainService;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Logging;
using MongoDB.Bson;
using System.Net.Http.Headers;
using System.Net.Http.Json;
using System.Text.Json;
@ -98,16 +99,14 @@ namespace Alarm.DomainService.DahAlarm
MonitorType = "url",
Events = new List<EventConfig>
{
new EventConfig
{
new() {
Category = "alarm",
SubscribeAll = 1,
DomainSubscribe = 2,
Authorities = new List<Authority>
{
new Authority
{
Types = new List<string> { "4321" }
new() {
Types = ["81"]
}
}
}
@ -189,13 +188,13 @@ namespace Alarm.DomainService.DahAlarm
/// <param name="dto"></param>
/// <returns></returns>
/// <exception cref="NotImplementedException"></exception>
public async Task<DaHApiResult<bool>> HandleAsync(object dto2)
public async Task<DaHApiResult<bool>> HandleAsync(EventEnvelopeDto dto)
{
DaHApiResult<bool> result = new() { Code = "200", Msg = "接口调用成功", Data = true };
_logger.LogWarning($"报警回调的数据{dto2}");
try
{
if (dto2 is null)
if (dto is null)
{
result.Code = "500";
result.Msg = "请求参数不能为空";
@ -203,14 +202,14 @@ namespace Alarm.DomainService.DahAlarm
_logger.LogWarning("大华报警事件订阅回调处理失败,参数不能为空");
return result;
}
EventEnvelopeDto dto = dto2 as EventEnvelopeDto;
if (dto.Info is not null)
{
//这是大华的残卫报警类型
if (dto.Info.AlarmType == 4321)
{
//拼接物联平台标准的mqtt消息格式
var payload = "[{\"taglabel\":\"" + dto.Info.DeviceCode + ".alart." + dto.Info.DeviceName + "\",\"value\":\"" + dto.Info.AlarmStat + "\",\"time\":\"" + DateTimeOffset.UtcNow.ToUnixTimeSeconds() + "\"}]";
var payload = "[{\"taglabel\":\"DH" + dto.Info.DeviceName + "\",\"value\":\"" + dto.Info.AlarmStat + "\",\"time\":\"" + DateTimeOffset.UtcNow.ToUnixTimeSeconds() + "\"}]";
// var payload = "[{\"taglabel\":\"残卫测试报警按钮.alarmStat\",\"value\":\"" + dto.Info.AlarmStat + "\",\"time\":\"" + DateTimeOffset.UtcNow.ToUnixTimeSeconds() + "\"}]";
await _mqttClient.EnsureConnectedAsync(mqttHostIp, mqttHostPort, mqttUsername, mqttPassword, topicName, mqttClientId);
@ -289,7 +288,7 @@ namespace Alarm.DomainService.DahAlarm
_logger.LogWarning("获取事件列表:token无效");
return new DaHApiResult<SubscribeDataDto> { Success = false, Code = "1009", Msg = "token无效" };
}
// var url = $"http://demo.weienergy.cn:15230/open-api/token/v1/oauth/token?client_id=69591850&client_secret=WHcpAryKFc28suzL&grant_type=client_credentials";
// var url = $"https://{_configuration["DahuaAuth:Host"]}/evo-apigw/evo-brm/1.0.0/device/1000007";
var url = $"https://{_configuration["DahuaAuth:Host"]}/evo-apigw/evo-event/1.0.0/subscribe/subscribe-list?monitorType=url&category={name}";
try
{

@ -25,6 +25,6 @@ namespace Alarm.DomainService.DahAlarm
/// <param name="env"></param>
/// <param name="ct"></param>
/// <returns></returns>
Task<DaHApiResult<bool>> HandleAsync(object env);
Task<DaHApiResult<bool>> HandleAsync(EventEnvelopeDto env);
}
}

@ -1,6 +1,8 @@
using Alarm.DomainService.DahAlarm;
using Common.Shared.Application.DaHua;
using Microsoft.AspNetCore.Mvc;
using MongoDB.Bson;
using System.Text.Json;
namespace AlarmService.API.Controllers
{
@ -34,12 +36,49 @@ namespace AlarmService.API.Controllers
/// <summary>
/// 报警的回调
/// </summary>
/// <param name="env"></param>
/// <param name="data"></param>
/// <returns></returns>
[HttpPost]
public async Task<DaHApiResult<bool>> DahuaAuthCallback(object env)
[Consumes("application/json")]
[Produces("application/json")]
public async Task<IActionResult> DahuaAuthCallback([FromBody] JsonElement data)
{
return await _generalCtlService.HandleAsync(env);
EventEnvelopeDto dto = new EventEnvelopeDto();
try
{
dto = JsonSerializer.Deserialize<EventEnvelopeDto>(data.ToJson())!;
}
catch (Exception ex)
{
_logger.LogWarning($"收到了报警回调{data.ToJson()}");
_logger.LogError(ex, "JSON反序列化失败");
}
// 即使数据结构异常,也不应该让平台收到 HTTP 500
try
{
if (dto != null)
{
await _generalCtlService.HandleAsync(dto);
}
else
{
_logger.LogWarning("接收到的DTO为 null,跳过业务处理");
}
}
catch (Exception ex)
{
_logger.LogError(ex, "处理回调时异常");
}
// 返回 Java 示例中的成功结构
var result = new
{
code = "0",
message = "成功"
};
return new JsonResult(result);
}
/// <summary>

@ -19,23 +19,42 @@ namespace Common.Shared.Application.DaHua
/// <summary>方法名(平台定义,不同大类可能不同)</summary>
[JsonPropertyName("method")]
public string? Method { get; set; }
public string Method { get; set; } = string.Empty; // 改为非空,符合必填要求
/// <summary>序号(非唯一标识,平台侧递增)</summary>
[JsonPropertyName("id")]
public long? Id { get; set; }
public long Id { get; set; } // 改为非空,符合必填要求
/// <summary>子系统名称(与你订阅时的 subsystem.name/magic 对应)</summary>
[JsonPropertyName("subsystem")]
public string? Subsystem { get; set; }
public string Subsystem { get; set; } = string.Empty; // 改为非空,符合必填要求
/// <summary>域 ID(级联域标识)</summary>
[JsonPropertyName("domainId")]
public string? DomainId { get; set; }
public string? DomainId { get; set; } // 保持可空,非必填
/// <summary>实际负载(不同大类结构不同,统一先接成 JsonElement)</summary>
/// <summary>实际负载(不同大类结构不同)</summary>
[JsonPropertyName("info")]
public AlarmVO Info { get; set; }
public AlarmVO Info { get; set; } = new AlarmVO(); // 初始化避免空引用
// 忽略JSON中存在但实体类未定义的字段(如userIds、sid、uuid等)
[JsonIgnore(Condition = JsonIgnoreCondition.WhenWritingNull)]
public object? UserIds { get; set; }
[JsonIgnore(Condition = JsonIgnoreCondition.WhenWritingNull)]
public object? Sid { get; set; }
[JsonIgnore(Condition = JsonIgnoreCondition.WhenWritingNull)]
public object? InfoArray { get; set; }
[JsonIgnore(Condition = JsonIgnoreCondition.WhenWritingNull)]
public object? Protocol { get; set; }
[JsonIgnore(Condition = JsonIgnoreCondition.WhenWritingNull)]
public object? SupplementFlag { get; set; }
[JsonIgnore(Condition = JsonIgnoreCondition.WhenWritingNull)]
public string? Uuid { get; set; }
}
/// <summary>
@ -45,79 +64,86 @@ namespace Common.Shared.Application.DaHua
{
/// <summary>设备编码</summary>
[JsonPropertyName("deviceCode")]
public string? DeviceCode { get; set; }
public string? DeviceCode { get; set; } // 保持可空,非必填
/// <summary>设备名称</summary>
[JsonPropertyName("deviceName")]
public string? DeviceName { get; set; }
public string? DeviceName { get; set; } // 保持可空,非必填
/// <summary>通道序号</summary>
[JsonPropertyName("channelSeq")]
public int? ChannelSeq { get; set; }
public int? ChannelSeq { get; set; } // 保持可空,非必填
/// <summary>通道名称</summary>
[JsonPropertyName("channelName")]
public string? ChannelName { get; set; }
public string? ChannelName { get; set; } // 保持可空,非必填
/// <summary>单元类型(必填:平台字段 unitType)</summary>
[JsonPropertyName("unitType")]
public int UnitType { get; set; }
public int UnitType { get; set; } // 保持非空,必填
/// <summary>单元序号(必填:平台字段 unitSeq)</summary>
/// <summary>单元序号(必填:平台字段 unitSeq)</summary>
[JsonPropertyName("unitSeq")]
public int UnitSeq { get; set; }
public int? UnitSeq { get; set; } // 改为可空,非必填(关键修改)
/// <summary>报警唯一编码(幂等键之一)</summary>
[JsonPropertyName("alarmCode")]
public string AlarmCode { get; set; } = string.Empty;
public string AlarmCode { get; set; } = string.Empty; // 保持非空,必填
/// <summary>报警状态:1 产生;2 消失(幂等键之一)</summary>
[JsonPropertyName("alarmStat")]
public int AlarmStat { get; set; }
public int AlarmStat { get; set; } // 保持非空,必填
/// <summary>报警类型</summary>
[JsonPropertyName("alarmType")]
public int AlarmType { get; set; }
public int AlarmType { get; set; } // 保持非空,必填
/// <summary>报警级别</summary>
[JsonPropertyName("alarmGrade")]
public int AlarmGrade { get; set; }
public int AlarmGrade { get; set; } // 保持非空,必填
/// <summary>报警时间(秒级时间戳,平台可能传字符串或数字,建议按字符串接收)</summary>
/// <summary>报警时间(秒级时间戳,平台可能传字符串或数字)</summary>
[JsonPropertyName("alarmDate")]
public string AlarmDate { get; set; } = string.Empty;
public string AlarmDate { get; set; } = string.Empty; // 保持非空,必填
/// <summary>报警图片相对路径(如需取图需按平台 OSS 规则拼接)</summary>
/// <summary>报警图片相对路径</summary>
[JsonPropertyName("alarmPicture")]
public string? AlarmPicture { get; set; }
public string? AlarmPicture { get; set; } // 保持可空,非必填
/// <summary>报警图片大小(字节)</summary>
[JsonPropertyName("alarmPictureSize")]
public long? AlarmPictureSize { get; set; }
public long? AlarmPictureSize { get; set; } // 保持可空,非必填
/// <summary>备注信息</summary>
[JsonPropertyName("memo")]
public string? Memo { get; set; }
public string? Memo { get; set; } // 保持可空,非必填
/// <summary>节点类型:1 设备;2 通道</summary>
[JsonPropertyName("nodeType")]
public int NodeType { get; set; }
public int NodeType { get; set; } // 保持非空,必填
/// <summary>节点编码(设备或通道编码)</summary>
[JsonPropertyName("nodeCode")]
public string NodeCode { get; set; } = string.Empty;
public string NodeCode { get; set; } = string.Empty; // 保持非空,必填
/// <summary>组织编码</summary>
[JsonPropertyName("orgCode")]
public string? OrgCode { get; set; }
public string? OrgCode { get; set; } // 保持可空,非必填
/// <summary>组织名称</summary>
[JsonPropertyName("orgName")]
public string? OrgName { get; set; }
public string? OrgName { get; set; } // 保持可空,非必填
/// <summary>扩展字段(不同类型报警差异字段)</summary>
[JsonPropertyName("extend")]
public JsonElement? Extend { get; set; }
public JsonElement? Extend { get; set; } // 保持可空,非必填
// 忽略JSON中存在但文档未定义的扩展字段(isSave、isEvent等)
[JsonIgnore]
public bool? IsSave { get; set; }
[JsonIgnore]
public bool? IsEvent { get; set; }
}
public sealed class SubscribeDataDto

Loading…
Cancel
Save