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数据访问的主要内容,如果未能解决你的问题,请参考以下文章