一、   引子

写这个开源系列已经十来篇了。自从十年前注册博客园以来,关注了张善友、老赵、xiaotie、深蓝色右手等一众大牛,也围观了逗比的吉日嘎啦、精密顽石等形形色色的园友。然而整整十年一篇文章都没有写过,属于非常努力的在社区汲取营养的菜青虫一只,现在也算破茧而出了,虽然远没有得道化蝶的境界,也在写作过程中得到不少提升。我开源的这个项目也有我固有的不良代码风格:严重缺乏注释,一方面是懒,一方面因为是单兵作战,也未曾想过让别人理解自己的代码。如何用简洁明了的方式表达自己的思路,虽然烧脑,但得到了社区的初步认可,在激励我把这个系列坚持下去的同时,对下一步如何完善这个项目,思路也更加清晰了。

二、      为什么要移植到.NET Core

.NET Core是.NET Framework的新一代版本,具有跨平台 (Windows、Mac OSX、Linux) 能力的应用程序开发框架。.NET Core遵循最宽松的开源协议,可以方便的移植到非微软平台,同时据说有相当出色的性能。这些已经足够吸引人了,对我这一工控狗而言,架构如果限定在Windows操作系统,有几个问题是难以解决但必须面对的:

  • 实时性

Windows是非实时的操作系统;受限于操作系统,我的网关程序始终找不到高精度的定时器,对一些实时性要求很高的场合,例如高精度机床控制,就力不从心了,而如果网关能移植到实时系统,这个问题就能得到解决。

  • 跨平台性

在一些诸如军工、机关、央企的场合都指定使用linux操作系统,如果不能跨平台,显然根本没有入局的机会。.NET Core的跨平台能力保证了广泛的适应性,起码不会因为绑定平台而被拒(杯具)。

  • 开源社区支持

因为宽松的开源协议,.NET Core现在已经成为很热门的开源项目,在社区获得了广泛的支持。最起码不用担心它的生命被微软忽然宣布死亡-微软虽然是.NET社区强有力的支持者,但不是唯一的;有谷歌,三星,Unity甚至红帽加入的.NET基金会的强大阵容;越来越多的开源社区接纳了.NET,并为之开发各种组件和应用。

  • 性能

看了不少公开资料及社区反馈,.NET Core的性能相比.NET Framework有大幅提升。部分常用类库据说提升达到60%(求证实)。但.NET Core毫无疑问是.NET 平台的未来,会得到持续的升级。

三、   如何移植

关于如何移植,博客园有不少好的文章。以我粗浅的理解和实践,就是建立一个.NET Core项目(VS017支持.NET Core 2.0),VS会自动加载相关的依赖项;将我网关部分的代码拷贝到新的文件夹下,形成下面这几个新的基于Core的项目:

可以看到,Core项目没有常规的dll引用方式,而代之以“项目”引用(即同一解决方案下的项目,这点和.NET Framework类似)以及NuGet包引用。NuGet可以理解为类库“商店”,在NuGet上寻找你需要的组件和类库,基本上常用的,你觉得应该有的,都能搜到,并傻瓜式下载、安装、部署。

和常规的.NET项目比较,基本大同小异,目标框架可选.NET Core的各版本。编译后生成的同样是dll文件,反射依然可用。另外还惊喜的发现.NET Core依然支持不安全代码-也就是支持指针,似乎说明微软设计者相当重视性能问题。

要让JAVA死忠们接受后来者.NET Core,性能优势、VS支持、部署傻瓜化这些显然很有吸引力。对我这类.NET 老用户而言,一个Core项目并没有什么违和感。一切都是亲切的老面孔,但深入之后,会发现也有一些不同之处,只是解决起来总体十分顺畅。下面说说我试手将SCADA项目的网关部分初步移植到.NET Core的过程。

四、   .NET Core填坑记

  • 移植准备

大概的学习了下.NET Core的基本概念,发现有几个重要问题必须要面对:

没有UI: Winform、WPF这一类的UI库并没有在.NET Core实现。大概是因为界面这部分各家差异太大,而且界面技术日新月异,做跨平台的界面现在流行用Web。Core只提供了简单的控制台输出显示。看来人机界面部分(HMI控件、WPF界面)目前是无法移植了。不过真正有移植价值的还是在网关部分,这部分如果能跨平台,界面用H5,WPF,还是QT都无所谓,反正都是通用的Socket通讯。(注:在最新的.NET Core 3.0版本,能够在Windows环境下兼容WPF,Winform,兼容UWP,这个消息值得期待)

没有对SQL Server的支持:大概因为SQL Server本身就不跨平台吧。这就逼得我必须寻找一个跨平台的数据库用来做系统配置和元数据存储。根据网友们的建议,我考虑 用MySQL作数据库,开源跨平台,用户多,工具完备,支持网络访问,性能也不错。好在NuGet上有不少开源类库支持对MySQL读写。

.Net Core下没有Windows 服务:原有的WCF后台服务和封装为Windows 服务组件的功能废弃,网关直接挂接一个控制台程序。需要与客户端交互,除了原有的基于Socket的TLV协议,还可以设计RESTful 调用接口,比WCF这种笨家伙只会更方便。

Windows日志的实现方式大不相同:大概为了和其他系统兼容,不能采用直接读写EventLog的方式了。SCADA项目的流水账记录和错误日志都写入Windows事件管理器,必须要替换。我比较了几种常用的日志移植方法,决定采用微    软自家的Logging组件,官方支持,同时扩展性看上去不错,最重要的是简单,写法上也和之前区别不大。另外第三方的Log4Net,NLog也移植到了.NET Core,这些日志库更为强大和专业。

没有内置串口组件:因为是工控组件,对串口的支持是必要的。但Core并没有内置SerialPort这种类库,感觉有点奇怪。在NuGet上搜到有RJCP.IO.Ports这个库,用法和SerialPort大同小异。

还有一些小功能需要移植,如读写ini配置文件等。好在NuGet上都有官方类库可用。

  • 移植过程

MySQL连接用了NuGet下载的MySQLConnector类库。开源免费,同时下载的人很多,从一个侧面印证了它的优秀。我重写了DataHelper类,使之能够实现多种数据库支持。简单起见,套用了一个数据库工厂模式,定义了一套数据读写接口。MySQLConnector比起Framework下的SqlConnector,没有什么特别的,继承的是同一套接口或抽象类,例如DbParameter、DbDataReader、DbCommand等。唯一注意的就是之前惯用的数据库批量写入类SqlBulkCopy不能再用了。MySql里有它自家的批量写入方式。

对日志的操作用了一个“提供者模式”,对于在Debug模式下有DebugLoggerProvider、控制台模式下有ConsoleLoggerProvider,设计十分合理。

对配置文件的管理用了一个构建者(Builder)模式,无论是ini配置方式还是xml配置方式都有自己的实现。

从对日志和配置的官方实现,让我感觉微软对.NET Core的设计颇为用心。在.NET FX下对配置文件或者日志的读写,要么是专门对Windows设计的EventLog日志类,要么连ini的官方支持都没有,必须调用API函数。而在Core中进行了重构,进行了合理充分的抽象,架构十分简洁明了,尤其是充分考虑了各平台对日志、配置文件的共性需求,易于扩展,也有助于开源社区自行发展完善。

  • 总体感觉

感觉Core和老的Framework还是非常相似的,起码绝大部分是兼容的。只有与操作系统和数据库密切相关的部分被重新实现了,但也很容易在NuGet找到替代办法。可以说,移植体验很顺畅。移植过程很傻瓜。让我这类初次使用者就能很快完成移植,甚至感觉Core重写之后比老的Framework代码更为简洁,架构更为清晰。这让我对Core的前景信心大增。

  • 未来改进

这次的移植只是初试,虽然编译通过并在虚拟机环境下测试,但并没在真实Linux环境下测试。因为不熟悉mysql,原有SQL SERVER的部分功能(如存储过程等)移植不全。未来我希望把网关部分也加入NuGet包,并提供支持.NET Core的设备驱动包下载,依靠开源社区使这个项目支持越来越多的系统平台、硬件设备和行业。

五、   下面的计划

写一系列帖子,把架构、原理讲清楚。大致如下:

github地址:https://github.com/GavinYellow/SharpSCADA。QQ群:102486275

开源纯C#工控网关+组态软件(十)移植到.NET Core的更多相关文章

  1. 开源纯C#工控网关+组态软件

    一.   前言 在园子潜水也七八年了.说来惭愧,这么多年虽然一直自称.NET铁杆粉丝,然仅限于回几个不痛不痒的贴,既没有发布过代码,也没有写过文章. 看着.NET和C#在国外风生水起,国内却日趋没落, ...

  2. 开源纯C#工控网关+组态软件(二)工控网关的实现

    一.   工控网关是什么 网关是物联网和工控系统的核心组件.网关起的是承上启下的作用.上即上位机,电脑/触屏监控系统.MES这些:下即下位机,包括PLC.传感器.嵌入式芯片等. 不同厂家的下位机,往往 ...

  3. 开源纯C#工控网关+组态软件(七)数据采集与归档

    一.   引子 在当前自动化.信息化.智能化的时代背景下,数据的作用日渐凸显.而工业发展到如今,科技含量和自动化水平均显著提高,但对数据的采集.利用才开始起步. 对工业企业而言,数据采集日益受到重视, ...

  4. 开源纯C#工控网关+组态软件(八)表达式编译器

    一.   引子 监控画面的主要功能之一就是跟踪下位机变量变化,并将这些变化展现为动画.大部分时候,界面上一个图元组件的某个状态,与单一变量Tag绑定,比如电机的运行态,绑定一个MotorRunning ...

  5. 开源纯C#工控网关+组态软件(九)定制Visual Studio

    一.   引子 因为最近很忙(lan),很久没发博了.不少朋友对那个右键弹出菜单和连线的功能很感兴趣,因为VS本身是不包含这种功能的.   大家想这是什么鬼,怎么我的设计器没有,其实这是一个微软黑科技 ...

  6. 开源纯C#工控网关+组态软件(三)加入一个新驱动:西门子S7

    一.   引子 首先感谢博客园:第一篇文章.第一个开源项目,算是旗开得胜.可以看到,项目大部分流量来自于博客园,码农乐园,名不虚传^^. 园友给了我很多支持,并提出了很好的改进意见.现加入屏幕分辨率自 ...

  7. 开源纯C#工控网关+组态软件(四)上下位机通讯原理

    一.   网关的功能:承上启下 最近有点忙,更新慢了.感谢园友们给予的支持,现在github上已经有.目标是最好的开源组态,看来又近一步^^ 之前有提到网关是物联网的关键环节,它的作用就是承上启下. ...

  8. 开源纯C#工控网关+组态软件(六)图元组件

    一.   图元概述 图元是构成人机界面的基本单元.如一个个的电机.设备.数据显示.仪表盘,都是图元.构建人机界面的过程就是铺排.挪移.定位图元的过程. 图元设计是绘图和编码的结合.因为图元不仅有显示和 ...

  9. 开源纯C#工控网关+组态软件(五)从网关到人机界面

    一.   引子 之前都在讲网关,不少网友关注如何实现界面.想了解下位机变量变化,是怎样一步步触发人机界面动画的. 这个步步触发,实质上是变量组(Group)的批量数据变化(DataChange)事件, ...

随机推荐

  1. 安装Compass时不能访问服务器的问题

    今天安装Compass,居然老是提示网络问题,后来根据错误提示,发现带https的域名是访问不了的,是是SSL问题.后来搜了一下,在stackoverflow找到一个人说,将https的去掉就好了.具 ...

  2. 【Android 应用开发】Android资源文件 - 使用资源存储字符串 颜色 尺寸 整型 布尔值 数组

    . 作者 : 万境绝尘 转载请注明出处 : http://blog.csdn.net/shulianghan/article/details/19913755 . 一. Android资源文件简介 1 ...

  3. Android群英传笔记——第八章:Activity与Activity调用栈分析

    Android群英传笔记--第八章:Activity与Activity调用栈分析 开篇,我们陈述一下Activity,Activity是整个应用用户交互的核心组件,了解Activity的工作模式,生命 ...

  4. Android开源项目——带图标文字的底部导航栏IconTabPageIndicator

    接下来的博客计划是,在<Android官方技术文档翻译>之间会发一些Android开源项目的介绍,直接剩下的几篇Android技术文档发完,然后就是Android开源项目和Gradle翻译 ...

  5. 树莓派linux驱动学习之LED控制

    前面我们编写了hello world的程序,接下来继续研究GPIO功能,通过GPIO来控制LED的亮灭,这在单片机中应该算是十分简单的一个程序了,但是在Linux系统中控制GPIO没有那么简单,难点就 ...

  6. 预装WIN8的电脑是GPT分区模式,无法安装WIN7

    本人的笔记本自带的是WIN8系统,现在想安装WIN7的系统,但是安装不了,提示"windows无法安装到这个磁盘.选中的磁盘采用GPT分区形式". 通过上网搜索得知WIN7一般安装 ...

  7. cocos2d-x 游戏开发之有限状态机(FSM) (三)

    cocos2d-x 游戏开发之有限状态机(FSM) (三) 有限状态机简称FSM,现在我们创建一个专门的FSM类,负责管理对象(Monkey)的状态.然后Monkey类就实现了行为与状态分离.Monk ...

  8. 让App中加入LruCache缓存,轻松解决图片过多造成的OOM

    上次有过电话面试中问到Android中的缓存策略,当时模糊不清的回答,现在好好理一下吧. Android中一般情况下采取的缓存策略是使用二级缓存,即内存缓存+硬盘缓存->LruCache+Dis ...

  9. ANDROID 中设计模式的采用--结构型模式

            结构型模式中的适配器模式.外观模式.装饰模式.代理模式都属于包装模式,都是对另外的类或对象的包装,只是各自的意图不同. 适配器模式通过对另外的类或对象的包装,将其接口转换为用户期望 ...

  10. Android BLE与终端通信(四)——实现服务器与客户端即时通讯功能

    Android BLE与终端通信(四)--实现服务器与客户端即时通讯功能 前面几篇一直在讲一些基础,其实说实话,蓝牙主要为多的还是一些概念性的东西,当你把概念都熟悉了之后,你会很简单的就可以实现一些逻 ...