PLC数据访问

Posted jonney

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了PLC数据访问相关的知识,希望对你有一定的参考价值。

PLC是很多机床设备上都有的控制中心,和PLC通信是很多做工厂管理系统的必经之路。

一年前有个项目需要和PLC(西门子S200)通信,不仅读取里面的数据,还需要写数据需要控制机床的运行,当时不大了解,由于设备比较老,没有以太网模块,还是在设备供应商的提示下用串口rs485联通pc,查资料了解modbus协议,完全手写按照modbus协议和PLC通信,最后总算了磕磕绊绊完成项目,后来还有各种超时异常造成机床运行错误,哎。

现在是第二个阶段,在老前辈的带领下,虽说对PLC下位机程序还是了解甚少,但是对如何与PLC通信方面比以前了解更多。由于市面上PLC的品牌和型号比较多,如果是要求各种PLC都和服务器连接并受控制或集中管理,基本上都会安装以太网扩展卡,然后在服务器上部署opc服务器,opc服务器的种类也比较多,西门子有自己的opc服务器,第三方的opc服务器也很好,能兼容很多种PLC种类和型号,自带的各种驱动,就现在这个项目来说用的是kepserver,用这个管理软件的人很多,只要知道想要的数据在PLC的正确地址,在kepserver做个配置即可。

剩余的事情就是写程序,从kepserver里存取数据,就像访问数据库一样,OPCDAAuto是个不错的选择,现在我用的dotnet,网上down一个OPCDAAuto.dll直接使用,如何使用OPCDAAuto.dll网上也有很多例子。下面是简单例子:

  1 using System;
  2 using System.Windows.Forms;
  3 using log4net;
  4 using OPCAutomation;
  5 
  6 namespace OpcDaAutoTest
  7 {
  8     public partial class FormReader : Form
  9     {
 10         private ILog _logger = LogManager.GetLogger(typeof(Form1));
 11         private System.Timers.Timer _timer = new System.Timers.Timer(5000);
 12 
 13         private OPCGroups _kepGroups = null;
 14         private OPCGroup _groupOmron = null;
 15         private OPCItem _omronQty = null;
 16         private OPCItem _omronStart = null;
 17         private OPCItem _omronWarn = null;
 18         private OPCGroup _groupSiemens = null;
 19         private OPCItem _siemensQty = null;
 20         private OPCItem _siemensStart = null;
 21         private OPCItem _siemensWarn = null;
 22 
 23         const string open = "正常";
 24         const string close = "关机";
 25 
 26         public FormReader()
 27         {
 28             InitializeComponent();
 29         }
 30 
 31         private void FormReader_Load(object sender, EventArgs e)
 32         {
 33             GetLocalServer();
 34             btnConnLocalServer.Click += btnConnLocalServer_Click;
 35             FormClosing += OnFormClosing;
 36         }
 37 
 38         private void OnFormClosing(object sender, FormClosingEventArgs formClosingEventArgs)
 39         {
 40             if (_kepServer != null)
 41             {
 42                 _kepServer.Disconnect();
 43                 _kepServer = null;
 44             }
 45         }
 46 
 47         private bool ConnectRemoteServer(string remoteServerName)
 48         {
 49             try
 50             {
 51                 _kepServer.Connect(remoteServerName);
 52 
 53                 if (_kepServer.ServerState == (int)OPCServerState.OPCRunning)
 54                 {
 55                     tsslServerState.Text = "已连接到-" + _kepServer.ServerName;
 56                 }
 57                 else
 58                 {
 59                     //这里你可以根据返回的状态来自定义显示信息,请查看自动化接口API文档
 60                     tsslServerState.Text = "状态:" + _kepServer.ServerState;
 61                 }
 62             }
 63             catch (Exception err)
 64             {
 65                 MessageBox.Show("连接远程服务器出现错误:" + err.Message, "提示信息", MessageBoxButtons.OK, MessageBoxIcon.Warning);
 66                 return false;
 67             }
 68             return true;
 69         }
 70         private void btnConnLocalServer_Click(object sender, EventArgs e)
 71         {
 72             try
 73             {
 74                 if (!ConnectRemoteServer(cmbServerName.Text))
 75                 {
 76                     return;
 77                 }
 78                 
 79                 _kepGroups = _kepServer.OPCGroups;
 80                 _groupOmron = _kepGroups.Add("omron");
 81                 _omronQty = _groupOmron.OPCItems.AddItem("Channel_Omron.Device1.Qty", 1001);
 82                 _omronStart = _groupOmron.OPCItems.AddItem("Channel_Omron.Device1.Start", 1002);
 83                 _omronWarn = _groupOmron.OPCItems.AddItem("Channel_Omron.Device1.Warn", 1003);
 84 
 85                 _groupSiemens = _kepGroups.Add("siemens");
 86                 _siemensQty = _groupSiemens.OPCItems.AddItem("Channel_Siemens.Device1.Qty", 2001);
 87                 _siemensStart = _groupSiemens.OPCItems.AddItem("Channel_Siemens.Device1.Start", 2002);
 88                 _siemensWarn = _groupSiemens.OPCItems.AddItem("Channel_Siemens.Device1.Warn", 2003);
 89 
 90                 _timer.Elapsed += (o, args) =>
 91                 {
 92                     _timer.Enabled = false;
 93                     try
 94                     {
 95                         object value = null;
 96                         object quality = null;
 97                         object timestamp = null;
 98                         _omronQty.Read(1, out value, out quality, out timestamp);
 99                         _logger.Debug(_omronQty.ItemID + "=" + value);
100                         var yazhu7Qty = value;
101                         _omronStart.Read(1, out value, out quality, out timestamp);
102                         _logger.Debug(_omronStart.ItemID + "=" + value);
103                         value = value ?? true;
104                         var yazhu7Start = value.Equals(false) ? open : close;
105                         _omronWarn.Read(1, out value, out quality, out timestamp);
106                         _logger.Debug(_omronWarn.ItemID + "=" + value);
107                         SaveData("Y7", yazhu7Start, yazhu7Qty);/*保存压铸7机台数据*/
108 
109                         _siemensQty.Read(1, out value, out quality, out timestamp);
110                         _logger.Debug(_siemensQty.ItemID + "=" + value);
111                         var yazhu11Qty = value;
112                         _siemensStart.Read(1, out value, out quality, out timestamp);
113                         _logger.Debug(_siemensStart.ItemID + "=" + value);
114                         value = value ?? true;
115                         var yazhu11Start = value.Equals(false) ? open : close;
116                         _siemensWarn.Read(1, out value, out quality, out timestamp);
117                         _logger.Debug(_siemensWarn.ItemID + "=" + value);
118                         SaveData("Y11", yazhu11Start, yazhu11Qty);/*保存压铸11机台数据*/
119                     }
120                     catch (Exception exception)
121                     {
122                         _logger.Error(exception);
123                     }
124                     finally
125                     {
126                         _timer.Enabled = true;
127                     }
128                 };
129                 _timer.Enabled = true;
130                 btnConnLocalServer.Enabled = false;
131                 
132             }
133             catch (Exception err)
134             {
135                 MessageBox.Show("初始化出错:" + err.Message, "提示信息", MessageBoxButtons.OK, MessageBoxIcon.Warning);
136             }
137         }
138 
139         private void SaveData(string machineNo, string start, object qty)
140         {
141             try
142             {
143                 using (var db = DbAccess.GetDbContext())
144                 {
145                     if (start.Equals(close))
146                     {
147                         db.Sql("update kbequipment set [email protected] where type=0 and [email protected]")
148                             .Parameters(start, machineNo)
149                             .Execute();
150                     }
151                     else
152                     {
153                         db.Sql("update kbequipment set [email protected], [email protected] where type=0 and [email protected]")
154                             .Parameters(start, qty, machineNo)
155                             .Execute();
156                     }
157                 }
158             }
159             catch (Exception e)
160             {
161                 _logger.Error(e.Message, e);
162             }
163         }
164         
165         private OPCServer _kepServer;
166         private void GetLocalServer()
167         {
168             try
169             {
170                 _kepServer = new OPCServer();
171                 object serverList = _kepServer.GetOPCServers(Environment.MachineName);
172 
173                 foreach (string turn in (Array)serverList)
174                 {
175                     cmbServerName.Items.Add(turn);
176                 }
177 
178                 cmbServerName.SelectedIndex = 0;
179                 btnConnLocalServer.Enabled = true;
180             }
181             catch (Exception err)
182             {
183                 MessageBox.Show("枚举本地OPC服务器出错:" + err.Message, "提示信息", MessageBoxButtons.OK, MessageBoxIcon.Warning);
184             }
185 
186         }
187     }
188 }

 

以上是关于PLC数据访问的主要内容,如果未能解决你的问题,请参考以下文章

如何在片段中访问 SQLite 数据到 ListView

工业网关TG463实现基于EOIP的PLC远程升级控制

从片段访问父活动的数据

PLC200,不知道为啥老是 提示未找到指定的访问点,请大神赐教

怎样通过互联网对PLC进行远程监控,并且远程采集数据?

从第二个片段访问时 ViewModel 数据丢失状态