云平台制作(1)-OPC Client取数模块的制作
近来由于工程需要,基于OPC DA 2.0搭建通用的取数模块,与远程webscoket服务端连接,并传输数据。在网上找了些资料,修改相应网友公开的源代码,基本达到要求,特供大家参考。
1.实体类
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace OPC_DEMO
{
public class MyOPCItem
{
public string key{ get; set; }
public string Value { get; set; }
}
}
2.源代码
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using OPCAutomation;
using System.Threading;
using System.IO;
using WebSocketSharp;
using Newtonsoft.Json;
namespace OPC_DEMO
{
public partial class Form1 : Form
{
private OPCServer KepServer;
private OPCGroups KepGroups;
private OPCGroup KepGroup;
private OPCItems KepItems;
public WebSocket wsc;
private string JsonStr;
private MyOPCItem opc;
Dictionary<string, string> MAP_CLIENTHANDLE_TAG;
public OPCItem[] OPC_ITEMS_ADDED { get; private set; }
public Form1()
{
InitializeComponent();
}
#region OPC Client
/// <summary>
/// 自动连接OPC Server,并websocket连接服务器。
/// </summary>
private void KepServerLoad()
{
try
{
KepServer = new OPCServer();
//KepServer.Connect("FBoxOpcServer", "127.0.0.1");
KepServer.Connect("Kepware.KEPServerEx.V6","127.0.0.1");
// KepServer.Connect("Kepware.KEPServerEx.V5","127.0.0.1");
if (KepServer.ServerState == (int)OPCServerState.OPCRunning)
{
wsc = new WebSocket("ws://10.0.0.128:6690/WsServices");
wsc.Connect();
richTextBox1.Text = "OPC Server连接成功";
}
else
{
richTextBox1.Text = "OPC Server连接失败";
return;
}
}
catch (Exception ex)
{
richTextBox1.Text = "OPC Server连接失败," + ex.Message;
return;
}
KepGroups = KepServer.OPCGroups;
Thread t1; // 开1个线程用于读取数据
t1 = new Thread(new ThreadStart(KepProcess));
t1.Start();
}
/// <summary>
/// 新建OPC Group并设置相应的属性,和触发改变事件
/// </summary>
public void KepProcess()
{
//KepGroup = KepGroups.Add("Channel.Device.Group");
KepGroup = KepGroups.Add("Channel1.Device1.Group");
KepGroup.UpdateRate = 1000;
KepGroup.IsActive = true;
KepGroup.IsSubscribed = true;
KepItems = KepGroup.OPCItems;
AddGroupItems();
//当KepGroup中数据发生改变的触发事件
KepGroup.DataChange += new DIOPCGroupEvent_DataChangeEventHandler(KepGroup_DataChange);
// //item1 = KepItems.AddItem("My FBox.外泵站1.AI.流量1", 1);
// item1 = KepItems.AddItem("通道 1.设备 1.标记 1", 1);
////item2 = KepItems.AddItem("My FBox.外泵站1.DI.格栅运行", 2);
//item2 = KepItems.AddItem("通道 1.设备 1.标记 2", 2);
//item3 = KepItems.AddItem("通道 1.设备 1.test",3);
}
/// <summary>
/// 单独设立添加OPCItem方法,用来添加OPCItem
/// </summary>
public void AddGroupItems()
{
List<string> str = new List<string>();
str.Add("通道 1.设备 1.标记 1");
str.Add("通道 1.设备 1.标记 2");
str.Add("通道 1.设备 1.test");
List<OPCItem> ItemsAdd = new List<OPCItem>();
MAP_CLIENTHANDLE_TAG = new Dictionary<string, string>();
int n = 0;
foreach (string tag in str)
{
ItemsAdd.Add(KepItems.AddItem(tag, n));
MAP_CLIENTHANDLE_TAG.Add(n + "", tag);
n++;
}
OPC_ITEMS_ADDED = ItemsAdd.ToArray();
}
//当数据改变时触发的事件
//public delegate void DelegateShowMessage(string str);
public delegate void DelegateShowMessage(MyOPCItem str);
/// <summary>
/// 数据改变事件触发编写,调用委托事件远程发送。
/// </summary>
/// <param name="TransactionID"></param>
/// <param name="NumItems"></param>
/// <param name="ClientHandles"></param>
/// <param name="ItemValues"></param>
/// <param name="Qualities"></param>
/// <param name="TimeStamps"></param>
public void KepGroup_DataChange(int TransactionID, int NumItems, ref Array ClientHandles, ref Array ItemValues, ref Array Qualities, ref Array TimeStamps)
{
Dictionary<string, string> tagValueMap = new Dictionary<string, string>();
string str = "";
// DelegateShowMessage show1 = new DelegateShowMessage(ShowMessage);
DelegateShowMessage show1 = new DelegateShowMessage(ShowMessage);
for (int i = 1; i <= NumItems; i++)
{
string clientHandle = ClientHandles.GetValue(i).ToString();
string tag = MAP_CLIENTHANDLE_TAG[clientHandle];
string val = ItemValues.GetValue(i).ToString();
//C# Dictionary 字典 添加数据
tagValueMap.Add(tag, val);
//for (int i = 1; i <= NumItems; i++)
//{
// if (ClientHandles.GetValue(i).Equals(1))
// {
// str = "通道 1.设备 1.标记 1:" + ItemValues.GetValue(i).ToString();
// }
// if (ClientHandles.GetValue(i).Equals(2))
// {
// str = "通道 1.设备 1.标记 2:" + ItemValues.GetValue(i).ToString();
// }
// if (ClientHandles.GetValue(i).Equals(3))
// {
// str = "通道 1.设备 1.test:" + ItemValues.GetValue(i).ToString();
// }
}
//str = tagValueMap["通道 1.设备 1.标记 1"];
// str = tagValueMap["通道 1.设备 1.标记 2"];
//str = tagValueMap["通道 1.设备 1.标记 test"];
// BeginInvoke(show1, new string[] { str });
MyOPCItem json =ParseOPCData(tagValueMap);
BeginInvoke(show1, json);
}
//public string ParseOPCData(Dictionary<string,string> tagValueMap)
//{
// foreach (var item in tagValueMap)
// {
// string key = item.Key;
// var value = item.Value;
// return "{"+"key:"+ key + "," + "Value:"+ value+"}";
// }
// return "";
//}
/// <summary>
/// 读Dictionary中的值,并传递给实体类。
/// </summary>
/// <param name="tagValueMap"></param>
/// <returns></returns>
public MyOPCItem ParseOPCData(Dictionary<string, string> tagValueMap)
{
opc = new MyOPCItem();
foreach (var item in tagValueMap)
{
opc.key = item.Key;
opc.Value = item.Value;
return opc;
}
return null;
}
//public void ShowMessage(string str)
//{
// //wsc.Send(JsonConvert.SerializeObject(str));
// // wsc.Send(str);
// richTextBox1.AppendText(str + System.Environment.NewLine);
//}
/// <summary>
/// websocket传递数据,和测试客户端显示。
/// </summary>
/// <param name="opc"></param>
public void ShowMessage(MyOPCItem opc)
{
wsc.Send(JsonConvert.SerializeObject(opc));
richTextBox1.AppendText(opc.Value + System.Environment.NewLine);
}
#endregion
private void Form1_Load_1(object sender, EventArgs e)
{
KepServerLoad();
}
private void Form1_FormClosing_1(object sender, FormClosingEventArgs e)
{
KepServer.Disconnect();
}
}
}
3.结论
初步实现与websocket的数据对接,以json对象的形式传递,还需要websocket服务端将其反序列化为json字符串,并解析给前端使用。当然,这只是一个初步的Demo,其性能优化,线程占有的内存,以及稳定性都有待测试。
云平台制作(1)-OPC Client取数模块的制作的更多相关文章
- 重磅发布丨乐维监控:全面兼容云平台,助力企业DevOps转型升级!
2019年伊始,我们迎来了乐维监控的又一重大功能更新——云平台监控,这将有效帮助企业将云上.云下数据聚合,方便统一化的监控管理与维护!未来,乐维监控每一次的产品功能及版本更新,我们都将第一时间于此发布 ...
- 完整部署CentOS7.2+OpenStack+kvm 云平台环境(4)--用OZ工具制作openstack镜像
在部署openstack云平台环境的时候,需要上传镜像到glance. 首先下载iso镜像,这里下载了centos6.5镜像,放到/usr/local/src目录下然后用OZ工具制作openstack ...
- Redis之高可用、集群、云平台搭建(非原创)
文章大纲 一.基础知识学习二.Redis常见的几种架构及优缺点总结三.Redis之Redis Sentinel(哨兵)实战四.Redis之Redis Cluster(分布式集群)实战五.Java之Je ...
- Redis之高可用、集群、云平台搭建
原文:Redis之高可用.集群.云平台搭建 文章大纲 一.基础知识学习二.Redis常见的几种架构及优缺点总结三.Redis之Redis Sentinel(哨兵)实战四.Redis之Redis Clu ...
- 使用 Velero 跨云平台迁移集群资源到 TKE
概述 Velero 是一个非常强大的开源工具,可以安全地备份和还原,执行灾难恢复以及迁移Kubernetes群集资源和持久卷,可以在 TKE 平台上使用 Velero 备份.还原和迁移集群资源,关于如 ...
- 完整部署CentOS7.2+OpenStack+kvm 云平台环境(1)--基础环境搭建
公司在IDC机房有两台很高配置的服务器,计划在上面部署openstack云平台虚拟化环境,用于承载后期开发测试和其他的一些对内业务.以下对openstack的部署过程及其使用做一详细介绍,仅仅依据本人 ...
- A亚马逊WS网上系列讲座——怎么样AWS云平台上千万用户的应用建设
用户选择云计算平台构建应用程序的一个重要原因是高弹性的云平台和可扩展性. 面向Internet应用程序通常需要支持用户使用大量,但要建立一个高度可扩展.具有一定的挑战,高度可用的应用程序,只有立足AW ...
- 腾讯基于Kubernetes的企业级容器云平台GaiaStack (转)
GaiaStack介绍 GaiaStack是腾讯基于Kubernetes打造的容器私有云平台.这里有几个关键词: 腾讯:GaiaStack可服务腾讯内部所有BG的业务: Kubernetes:Gaia ...
- OpenStack(二)——使用Kolla部署OpenStack-allinone云平台
(1).Kolla概述 Kolla是OpenStack下用于自动化部署的一个项目,它基于docker和ansible来实现,其中docker主要负责镜像制作和容器管理,ansible主要负责环境的部署 ...
随机推荐
- MIT6.828-LAB1 : PC启动
Lab1 1. 先熟悉PC的物理地址空间 这里其实有很多可以说的,不过先简单描述一下吧.从0x00000000到0x00100000这1mb的地址空间时机器处于16位的实模式.也就是说这个时候机器的汇 ...
- HR面试:过五关斩六将后,小心阴沟翻船!(史上最全、避坑宝典)
文章很长,建议收藏起来,慢慢读! 疯狂创客圈为小伙伴奉上以下珍贵的学习资源: 疯狂创客圈 经典图书 : <Netty Zookeeper Redis 高并发实战> 面试必备 + 大厂必备 ...
- 题解 P3233 [HNOI2014]世界树
题目传送门 解题思路 正解当然是虚树了. 首先对于原树以及虚树各开一个结构体存边,这个不用多说. 然后我们先 DFS 一遍,求出各个节点的时间戳,子树大小,深度以及父亲节点,并初始化倍增 LCA . ...
- WEB安全新玩法 [6] 防范图形验证码重复使用
在完成关键业务操作时,要求用户输入图形验证码是防范自动化攻击的一种措施.为安全起见,即使针对同一用户,在重新输入信息时也应该更新图形验证码.iFlow 业务安全加固平台可以加强这方面的处理. 某网站系 ...
- vscode 配置 Pug Compile Hero Pro 插件步骤
这个随笔主要介绍 vscode 配置 Pug Compile Hero Pro 插件的步骤,实现快速使用less 以及 scss 等的编程语言 第一步 当然是安装我们的插件啦! 在插件商店里 搜 Sa ...
- excel函数提取内容中的汉字
RIGHT(A2,LENB(A2)-LEN(A2)) 函数LENB将每个汉字(双字节字符)的字符数按2计数,LEN函数则对所有的字符都按1计数.因此"LENB(A2)-LEN(A2)&quo ...
- 6、负载均衡HAproxy介绍
6.1.常用负载均衡器软件说明: 现在常用的三大开源软件负载均衡器分别是Nginx.HAProxy.LVS. 1.nginx负载均衡的特点: (1)工作在网络的七层之上,可以针对http应用做一些分流 ...
- (数据科学学习手札124)pandas 1.3版本主要更新内容一览
本文示例代码及文件已上传至我的Github仓库https://github.com/CNFeffery/DataScienceStudyNotes 1 简介 就在几天前,pandas发布了其1.3版本 ...
- Java程序设计(2021春)——第一章续笔记与思考
Java程序设计(2021春)--第一章续笔记与思考 目录 Java程序设计(2021春)--第一章续笔记与思考 Java数据类型 基本数据类型 引用类型 基本数据类型--整数类型的细节 基本数据类型 ...
- 常见链表操作-链表中环的检测(JAVA实现)
问题如何检测一个单链表中是否有环,例如下图的例子. 解决思路1:快慢指针法这是最常见的方法.思路就是有两个指针P1和P2,同时从头结点开始往下遍历链表中的所有节点. P1是慢指针,一次遍历一个节点.P ...