C#实现数据采集系统-系统优化服务封装

系统优化-服务封装

现在我们调用modbustcp和mqtt都直接在Program,所有加载和功能都混合在一起,比较难以维护
在这里插入图片描述

类似asp.net core项目的Program.cs代码如下,构建服务配置和启动
在这里插入图片描述

要实现的效果,Main方法中就是一个服务启动,只需要几行代码
在这里插入图片描述

分析代码

这里分成两部分,一部分是配置文件加载,另一部分是各种功能调用和启动

在这里插入图片描述

优化封装

配置封装

在DAqOption增加List<RegisterPoint>数据点位集合,让配置信息都在一个Option中,他将作为参数传递到后续的服务中去

public class DAqOption
{
    public DeviceLink DeviceLink { get; set; }

    public MqttConfig MqttConfig { get; set; }

    public List<RegisterPoint> Points { get; set; }
}

创建一个DAqOptionBuilder 用来加载和创建配置文件

传入一个路径来定位配置文件路径,然后增加一个Build方法,进行配置文件,返回配置类

public class DAqOptionBuilder
{
    private string _path;

    public DAqOptionBuilder(string path = "Config")
    {
        _path = path;
    }

    public DAqOption Build()
    {
        var str = File.ReadAllText($"{_path}\\Config.json");
        var option = JsonSerializer.Deserialize<DAqOption>(str);
        var lines = File.ReadAllLines($"{_path}\\AllPoint.csv", Encoding.UTF8).ToList();
        lines.RemoveAt(0);
        List<RegisterPoint> points = new List<RegisterPoint>();
        foreach (var line in lines)
        {
            var values = line.Split(',');
            var point = new RegisterPoint()
            {
                UID = values[0],
                Name = values[1],
                Type = Type.GetType("System." + values[2]),
                RegisterType = values[3],
                Address = int.Parse(values[4]),
                Length = int.Parse(values[5]),
            };
            points.Add(point);
        }
        option.Points = points;

        return option;
    }
}

服务封装

创建一个DAqService类用于存放数据采集的相关服务操作

传入配置类对象,完成各个属性赋值

  public class DAqService
  {
      private DAqOption _option;
      private DeviceLink deviceLink;
      private List<RegisterPoint> points;

      public DAqService(DAqOption option)
      {
          _option = option;
          deviceLink = option.DeviceLink;
          points = option.Points;
      }


}

添加各个模块的对象和Start启动程序,将代码迁移过来

        //模块对象
        private MqttControllor MqttControllor;
        private ModbusTcp _modbusTcp;
        
        //方法
        
        /// <summary>
        /// 启动服务
        /// </summary>
        public void Start()
        {
    
    
            MqttControllor = new MqttControllor(_option.MqttConfig);

            ModbusTcp modbusTcp = new ModbusTcp(deviceLink, points);
            modbusTcp.DoMonitor();
            modbusTcp.ValueUpdated += ModbusTcp_ValueUpdated;
        }


        private void ModbusTcp_ValueUpdated(RegisterPoint point, object value)
        {
    
    
            try
            {
    
    
                DeviceMessage device = new DeviceMessage {
    
     DeviceId = deviceLink.UID };
                device.Data.Add(point.UID, value);
                var data = JsonSerializer.Serialize(device);
                MqttControllor.Publish($"Device/{
      
      deviceLink.UID}/Update", data); //采集立刻推送
            }
            catch (Exception ex)
            {
    
    
                Console.WriteLine(ex.Message);
            }

            Console.WriteLine($"Point:{
      
      point.UID}-->Value:{
      
      value}");
        }

推送功能改用定时器,定时推送

C# 中有好几个种定时器,我们这里使用System.Timers.Timer来使用

private System.Timers.Timer timer;

public DAqService(DAqOption option)
{
    
    
    //...
    timer = new System.Timers.Timer(1000);
    timer.Elapsed += Timer_Elapsed; 
}

private void Timer_Elapsed(object? sender, ElapsedEventArgs e)
{
    
    
    try
    {
    
    
        DeviceMessage device = new DeviceMessage {
    
     DeviceId = deviceLink.UID };
        foreach (RegisterPoint point in points)
        {
    
    
            // Console.WriteLine($"Point:{point.UID}-->Value:{point.Value}");
            device.Data.Add(point.UID, point.Value);
        }
        var data = JsonSerializer.Serialize(device);
        MqttControllor.Publish($"Device/{
      
      deviceLink.UID}/Time", data); //定时推送
    }
    catch (Exception ex)
    {
    
    
        Console.WriteLine(ex.Message);
    }
}

net6中默认全局引用

在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

默认就引用了System.Threading,可以把ImplicitUsings直接删掉,在项目自己引用需要的命名空间即可,但是这样就得在所以项目都删掉。

在这里插入图片描述

在主程序中使用

仅需四行代码

    internal class Program
    {
    
    
        static void Main(string[] args)
        {
    
    
            DAqOptionBuilder builder = new DAqOptionBuilder();
            var option = builder.Build();
            DAqService dAqService = new DAqService(option);
            dAqService.Start();
        }
    }

完整服务代码

  public class DAqService
  {
    
    
      private MqttControllor MqttControllor;
      private ModbusTcp _modbusTcp;

      private DAqOption _option;
      private DeviceLink deviceLink;
      private List<RegisterPoint> points;

      private System.Timers.Timer timer;

      public DAqService(DAqOption option)
      {
    
    
          _option = option;
          deviceLink = option.DeviceLink;
          points = option.Points;
          timer = new System.Timers.Timer(1000);
          timer.Elapsed += Timer_Elapsed;
      }

      private void Timer_Elapsed(object? sender, ElapsedEventArgs e)
      {
    
    
          try
          {
    
    
              DeviceMessage device = new DeviceMessage {
    
     DeviceId = deviceLink.UID };
              foreach (RegisterPoint point in points)
              {
    
    
                  // Console.WriteLine($"Point:{point.UID}-->Value:{point.Value}");
                  device.Data.Add(point.UID, point.Value);
              }
              var data = JsonSerializer.Serialize(device);
              MqttControllor.Publish($"Device/{
      
      deviceLink.UID}/Time", data); //定时推送
          }
          catch (Exception ex)
          {
    
    
              Console.WriteLine(ex.Message);
          }
      }

      /// <summary>
      /// 启动服务
      /// </summary>
      public void Start()
      {
    
    
          MqttControllor = new MqttControllor(_option.MqttConfig);

          ModbusTcp modbusTcp = new ModbusTcp(deviceLink, points);
          modbusTcp.DoMonitor();
          modbusTcp.ValueUpdated += ModbusTcp_ValueUpdated;
      }

      private void ModbusTcp_ValueUpdated(RegisterPoint point, object value)
      {
    
    
          try
          {
    
    
              DeviceMessage device = new DeviceMessage {
    
     DeviceId = deviceLink.UID };
              device.Data.Add(point.UID, value);
              var data = JsonSerializer.Serialize(device);
              MqttControllor.Publish($"Device/{
      
      deviceLink.UID}/Update", data); //采集立刻推送
          }
          catch (Exception ex)
          {
    
    
              Console.WriteLine(ex.Message);
          }

          Console.WriteLine($"Point:{
      
      point.UID}-->Value:{
      
      value}");
      }
  }

猜你喜欢

转载自blog.csdn.net/qq_39427511/article/details/140865173