目 錄
第一章 通訊架構介紹... 2
1.1 通訊的本質... 2
1.2 架構簡介... 3
1.3 解決現實問題... 4
1.4 應用場景... 5
1.5 架構應用特點... 6
1.6 架構設計特點... 7
1.7 插件式應用架構... 9
1.8 開發環境... 10
1.9 第三方元件... 11
1.10 小結... 12
第一章 通訊架構介紹
1.1 通訊的本質
通訊就是資訊的傳遞,資訊傳遞又分為:單向資訊傳遞和雙向資訊傳遞。用喇叭進行廣播是單向資訊傳遞,打電話是雙向資訊傳遞。
單向資訊傳遞相對較為簡單,隻需要向資訊接收者實時發送資料,而不用管資訊是否到達,以及到達後是否進行了處理。這種資訊傳遞方式适用于對資料完整性要求不高的應用場景,例如:采集溫度傳感器的資料。但是,如果資料源或是傳感器比較多的話,要考慮到并發量的問題,随着網際網路技術的發展,并發問題是可以很好的解決。
雙向資訊傳遞相對較為複雜,不僅涉及到發送資料的問題,還涉及到資訊握手、資料補傳等一系列互動問題。如果把雙向資訊傳遞非要分成用戶端和服務端的話,還涉及到是哪一方先發起資訊傳遞,用戶端主動向服務端發送資料,服務端接收到資料後進行處理;但是,有時候服務端不希望接收到用戶端的資料,隻有在服務端向用戶端發送請求指令後,用戶端根據指令才可以傳回相應的資料。在與硬體進行雙向通訊的時候,還涉及到載波通道是半雙工和全雙工的問題,半雙工是同一時刻在通道上隻能A向B或B向A發送資料,隻能單向資料傳輸;全雙工是A向B發送資料,同時B向A也可以發送資料,發送和接收資料兩者可以同步進行。這種資訊傳遞方式适用于對資料完全性要求比較高的應用場景。
不管是單向資訊傳遞,還是雙向資訊傳遞,都涉及傳輸協定、編碼方式和資料校驗。傳輸協定是能夠封裝和解析并且能夠互相了解的資料格式,它是一種資料規約方式,可以使用标準的協定方式,例如:Modbus、XMPP、AMQP、MQTT等,也可以使用自定義協定;有了傳輸協定後,在傳輸過程中還涉及到編碼方式,例如:GBK、UTF、ASCII,有可能在編碼的基礎上還要進行加密,以保證資料的安全性;為了資料包完全性、可解析性,還要增加對資料的校驗,一般采用較多的校驗方式為CRC。傳輸協定、編碼方式和資料校驗的目的隻有一個:防止資料在傳輸過程中受到幹擾,或被惡意篡改,給資料處理造成意想不到的後果。打個比喻,一個中國人說國語,一個外國人說美式英文,文法不一樣,編碼格式不一樣,結果造成說話聽不懂、文字看不懂,如果誤認為是在罵人,有可能還要打一架。
現在基本都是面向對象開發方式,new出來一個對象,把對象的屬性指派後,直接把對象傳給接口函數完成發送資料。這種操作方式使開發者更多的關注業務層面,進而掩蓋了很多技術細節,例如:序列化、協定、編碼、位元組流的操作等等。
但是,SuperIO保持對底層位元組流(byte[])的操作,更多的關注通訊架構、資料協定、資料緩存、資料處理流程、裝置驅動、插件、二次開發等方面。因為在物聯網時代,将會面對很多資料源,包括:各種傳感器、手機、PC端、智能硬體、傳統嵌入式裝置等等,協定衆多,并且很難統一,是以最直接的操作資料就是位元組流(byte[])。另外,很早以前傳輸技術不發達(300波特率),同時受寄存器的存儲限制,為了減小資料量,1個位元組的8位要表示8種狀态類型。
在物聯網時代,将面臨各種通訊情況,例如:一個序列槽通道,一對一、一對多的方式通訊;一個網絡IP通道,一對一、一對多的通訊。是以,沒有一個好的架構支撐是無法滿足通用性的要求。
有人問題序列槽通訊、網絡通訊怎麼做,有人回答這些很容易,但是要把上述問題以及其他問題都考慮周全的話就是一個複雜的問題,并且有些問題不是很好解決。
1.2 架構簡介
如果一個公司的硬體産品衆多,協定又各不相同,每一個硬體産品都對應一套上位機軟體,需要專人維護。而客戶的需求日益變化,造成維護成本較高,并且阻礙了公司的快速發展。另外,就算修改同類硬體産品的配套軟體,也可能造成新的BUG出現。
随着市場和公司發展的需要,需要整合、重構軟體系統以适應環境、硬體的不斷變化,降低人力、運維成本,釋放勞動力。
是以,對于發展到一定階段、或是一個成熟的公司必然要有軟體架構作為支撐,這是從業務角度考慮發展應用架構的必然性。
技術方面,架構是一個系統全部或部分的可複用設計,通常由一組接口、抽象類和類之間的協作組成。随着資訊化的發展,軟體産品的開發也越來越複雜化,解決問題的複雜度也在不斷的提高。IT界也在尋找多種方法,包括制定各種軟體開發标準和規範、開發更進階更有生産力的程式設計語言、開發更好的編譯器和運作時以及不需要編譯的解釋性開發語言、開發功能強大以及更通用性的元件庫、探索适用不同應用場景的設計模式等。
從軟體工程角度出發,在設計層面要采用獨特的軟體構架和設計模式來達到我們預期的目标:
- n 盡量提高軟體的可重用性,避免不必要的重複編碼工作。
- n 增加組裝的封裝性。
- n 提高軟體的子產品化程度。
- n 不同功能子產品之間能夠無縫內建。
- n 軟體具有靈活的可擴充性。
- n 軟體産品的擴充和開發實作标準化。
- n 軟體産品具有面向不同應用層面的适應性和易移植性。
為了實作這些要求,在設計層面上,越來越多的軟體産品開始采用應用架構的思想進行軟體結構設計。應用架構已經是一個被廣泛使用的術語,它成為軟體開中一種非常實用并且常用的設計、開發規範。
我們肯定見過很多自稱“架構”的軟體産品,也許有人會感覺不屑,有些代碼量很少的程式居然也稱自己是某種形式的應用架構?事實上,應用架構無關乎規模大小,就像房屋一樣,摩天大樓和民房都是房屋,隻不過它們的規模和精巧度大小不一樣而已。
在架構師眼裡,代碼都是需要設計的,都是有架構的。
1.3 解決現實問題
在工業領域,經常遇到軟硬體之間的資料互動,并且面臨着複雜的現場環境:
(1)複雜的、多樣的通訊協定。有标準的協定,例如:Modbus等,也有很多根據标準協定修改的協定格式、以及自定義協定格式,并且千差萬别。對于不好的軟體架構,疲于應對,增加裝置或協定要對整個軟體進行梳理,往往在此過程中出現新的問題或BUG。
(2)針對不同使用者對軟體界面或功能的要求有很大不同,使之滿足不同使用者的顯示要求,可以自定義資料顯示界面。
(3)在做內建項目的時候,輸入輸出資料的多樣性。首先,要內建其他廠家的裝置,要求資料進行接入。其次,還有很多是其他廠家要內建自己家的裝置,就涉及的輸出資料的問題,資料格式要求也是千差萬别。
(4)通訊鍊路的多種性,對于同一個裝置可能要支援RS232/RS485/RS422、RJ45、3G/4G等通訊方式,是以對于一個裝置要對應多種通訊方式(序列槽和網絡),也給我們的開發造成很大的障礙。
(5)軟體各版本、以及軟體與硬體之間的相容性很差,管理起來錯綜複雜。
為了解決以上諸多問題,開發一個軟體架構,支援二次開發。在不對軟體架構改動的情況下,能夠很友善的接入裝置、維護裝置、內建裝置、處理裝置業務資料等。軟體架構相對穩定,把容易變化的部分進行靈活設計。
1.4 應用場景
作為一個架構平台,在形成産品後要定位它的應用場景,在設計架構之前要有清晰的認識,并在設計過程中不斷強化應用目标。
在産品應用方面,架構平台可能要部署在PC機上,與衆多硬體、傳感器進行資料互動,并在本地進行資料存儲。
在項目應用方面,架構平台可能部署在伺服器端,與用戶端(PC機、硬體、傳感器等)進行資料互動,并存儲到資料中。
既然架構平台在PC機上和服務端都可能應用,那麼架構與架構之間也有資料互動的可能性。
是以,架構平台的互動場景包括兩方面:第一、與硬體産品互動。第二、與軟體産品互動。基本這兩方面考慮:
1)架構平台應用在PC機上
主要應用在自動站的工控機上,通過RS485/RS232、RJ45、4-20mA等方式
采集硬體裝置的資料資訊。同時,通訊平台與伺服器端的軟體進行互動,負責上傳資料資訊,以及接收控制指令等。
2)架構平台應用在伺服器端上
終端裝置以3G/4G、有線專網、衛星等與通訊平台連接配接,進行資料互動,終
端裝置包括:PC機、移動終端(手機)、監測裝置和傳感器等。
基于以上考慮,架構平台的應用場景結構圖如下:

1.5 架構應用特點
對于架構的特點,我們要有簡單、清晰的規劃,其中包括:功能層面、性能層面、應用層面、運作層面、二次開發層面等等 ,這些将強化我們在設計、開發過程的目标。這些不僅要寫在紙上,更要記在腦子裡。SuperIO在設計的時候,簡單的列出了它的特點,盡管有些特點是後來完善的,如下:
- n 快速建構通訊資料采集平台軟體的宿主程式
- n 快速建構裝置驅動,以及相關的協定驅動、指令緩沖、自定義參數和實時資料屬性等
- n 快速二次開發圖形顯示、資料輸出、服務驅動,并以插件的形式進行挂載。
- n 一個裝置驅動,同時支援序列槽(COM)和網絡(TCP Server/Tcp Client)通訊機制,可以自由切換
- n 内置協定驅動,可以把第三方協定轉換成自定義的協定,協定的本質是對位元組流的操作。
- n 内置裝置指令緩沖器,可以設定指令發送的優先級别,保證指令的快速響應。
- n 以服務驅動插件的方式對OPC服務、4-20mA輸出、LED大屏顯示、短信服務等進行二次開發。
- n 快速開發、運作穩定、擴充性強大
- n 适用工業上位機軟體,以及系統內建中采集遠端裝置資料
- n 支援Windows XP/7/8/8.1、Windows Server 2003/2008/2012
1.6 架構設計特點
有些書籍說了一大堆設計特點,有點讓人不知所雲,沒見有層次感,我認為對于此類架構的特點最重要的包括兩點:穩定性、擴充性、性能。
穩定性
對于一個實時資料采集架構來說,首要的設計特點就是穩定性,這是其他一切特點的前提。不能出現異常後軟體無故退出的現象、不能出現關閉軟體後程序無法退出的現象、不能出現無法響應資料的現象、不能出現無法處理資料的現象等等。
基于可能存在的這些潛在的問題,我們要考慮:容錯機制、子產品無縫對接、記錄日志等。
容錯機制是所有軟體都有的一種機制,核心思想是對異常狀态的處理方法。對于操作一般性的功能,如果出現異常狀态,我們可能不需要過多的幹預,隻需要進行日志記錄就可以了,對于再次操作同樣的功能可以驗證異常狀态的可重複性,根據日志資訊可以有針對性的進行解決;對于事務性的任務,對異常狀态的處理會有多種選擇,可以簡單的記錄異常資訊、可以銷毀目前的資源,重新開始任務,直接任務成功、可以恢複到出現異常狀态的節點等,根據不同的場景,選擇處理的方式也不一樣。就相當于,某人說錯話了,要進行補救,那就要看當時的環境和面對的人,如果是好朋友,這事就算過去了。
子產品無縫對接要求我們對接口、抽象類以及類的子產品劃分、設計粒度有很好的把握,更多的展現在經驗方面。子產品之間是一個契約關系,如何履行契約會涉及到很多設計模式的選擇,是以說對設計子產品的把握程度直接影響軟體架構的成熟度。就好比兩個人對話,說話方式、語意都不能互相了解,就有可能話不投機半句多。
記錄日志是所有軟體必須要有的特點,這為我們排查錯誤提供了很大的友善。日志記錄有很多開源的項目可以拿來直接使用,例如常用的Log4Net。但是,有時間研究這東西的時間,自己也能寫一個适用于自己的日志庫了。
穩定性是軟體運作的最直接反應,是所有實時性架構設計最主要考慮的因素,也是最難達到的。
擴充性
使用者可能比設計者更關心穩定性,但是使用者不僅僅滿足于穩定性,還會提出各種新需求,更多的展現在功能方面。如果擴充性不好,對于開發者來說是萬丈深淵。
是以,可擴充性是應用架構最顯著的特征之一,它意味着應用架構的功能具有生長能力。沒有擴充能力的應用架構毫無使用價值和意義,因為架構本身就是為了提供一個統一的上下文環境給具體的應用使用。應用架構的可擴充性使我們能夠基于一個平台實作不同的功能,滿足不同的應用需求,有些需求是架構本身就支援的。
架構的可擴充性主要是通過繼承和聚合兩種方式實作的。繼承方式是指通過派生類繼承基類或接口,通過重用基類的功能并定義新的功能的方式實作功能擴充;聚合方式是指調用不同的類型組合為一個新類型而擴充出全新的功能。研究Framework架構源代碼,能夠深切感受到繼承和聚合的作用。
如果單說擴充性會讓人有些空洞,那麼我們還要考慮子產品化、可重用性、可維護性等等。
子產品化,并不是把每個功能都編譯成一個DLL程式集就可以稱之為子產品化,一個程式集内部也可以子產品化。從架構層面在邏輯上橫向、縱向對子產品和層次進行劃分,以降低子產品之間的耦合度,不會因為一個子產品的變化而影響其他子產品,劃分子產品時保證子產品之間輸入輸出的統一性。
可重用性,也可以稱為可複用性,是衡量代碼品質的重要标志之一。既然是架構設計其中一個目的就是提高效率,減少沒有必要的重複勞作,降低成本。一般來說,架構可重用可以是離散存在的函數、可以是封裝好的類庫、可以是封裝好的衆多類庫,以友善我們在類似功能、業務中使用。
可維護性,根據業務需求變化能夠友善進行改變的能力,也是擴充性的落腳點。保證我們盡量少修改代碼完成需求而又不影響軟體的整體運作。
性能
性能是軟體運作效率的重要名額,是對軟體運作極限的考驗。例如,不管挂載多少裝置驅動,使用者要求1秒鐘要讀取一次所有裝置的資料,如果實作不了,使用者說對不起,我們不能簽合同。
在網際網路行業對性能的要求更高、更全面,有很多名額性的參數,例如:響應時間、延遲時間、吞吐量、并發量、資源使用率等等,是以一般要對軟體、服務進行壓力測試。在傳統行業方面也不防借鑒使用先進的架構或第三方元件,例如:消息隊列架構(kafka、ActiveMq、RabbitMq、ZeroMq、EQueue),響應式消息架構(Akka.net)、作業排程架構(Quartz.net)等等,這些能夠有助于提高軟體、系統的執行效率和性能。
當然,對于性能來講,軟體隻是一個方面,更多的還涉及到網絡結構、伺服器部署等方面,是一項綜合性的結構。
對于穩定性、擴充性、性能,它是一個整體的三個方面。相信大家都看過F1比賽,要求賽車在高速行駛過程中保持不翻車,高速行駛對輪胎磨損很嚴重,并且要求在很短的時間内友善對輪胎的更換。
1.7 插件式應用架構
插件技術是在軟體的設計和開發過程中,将整個應用程式劃分為宿主程式和插件對象兩部分,宿主程式能夠調用插件對象,插件對象能夠在宿主程式上實作自己的邏輯,而兩者的互動基于一種公共的通信契約。宿主程式可以獨立于插件對象存在,即使沒有任何插件對象,宿主程式的運作也不受影響,是以,我們可以在避免改變宿主程式的情況下通過增減插件或修改插件的方式增加或調整功能。由于使用了插件技術的宿主程式具備了一個架構的本質特征,是以可以将它看作是一種插件式架構。插件式架構能夠有效地降低功能對象與對象管理邏輯之間的耦合程度,并将耦合置于最優的程度。
對大部分計算機使用者和軟體開發者而言,插件式應用架構其實算不上什麼神秘的東西,事實上,幾乎每個人都曾使用過具有插件式功能的軟體産品。這些軟體有大有小,從操作簡單的諸如播放器軟體到複雜桀骜的各種專業應用軟體,都或多或少采用過插件機制,隻是對于最終使用者而言,由于常常滿足于使用一款成熟軟體,很少有人刻意去關注這些軟體使用的是什麼樣的架構體系。
Visual Studio IDE、Elipse等都是插件式的開發工具,并實作了很強大的插件機制,也促使這些軟體變的越來越強大。
一般而,一款軟體、一個架構使用插件機制的原因主要基于以下3點:
- n 可以在無需對程式進行重新編譯和釋出的條件下擴充程式的功能。
- n 可以在不需要程式源代碼的環境下為程式增加新的功能。
- n 在一個程式的業務邏輯不斷發生改變、新的規則頻頻加入時能夠靈活适應。
實作插件機制一般有3種技術:基于動态連接配接庫DLL的插件、基于元件對象模型COM的插件、以及基于.NET反射技術的插件。
SuperIO是使用反射技術實作的插件機制,在後面的章節中進行詳細介紹。
1.8 開發環境
開發語言
使用C#開發的SuperIO架構,當然使用其他語言也可以實作,例如:JAVA。
開發工具
一開始使用的是Visual Studio 2008工具進行開發,後來更新到Visual Studio 2012,并對SuperIO進行了重新編譯。
支援架構
一開始使用的是Framework 2.0架構進行開發,後來更新到Framework 4.0,為了相容較低版本的作業系統(Windows xp sp3),最高版本的架構隻能使用Framework 4.0,再高版本的架構在Windows xp sp3下無法運作。如下圖:
編譯環境
使用X86平台對項目進行編譯,如果開發插件也需要用X86平台進行編譯,主要考慮到32位和64位作業系統的通用性。如下圖:
開發環境:
一開始在Windows xp sp3作業系統下進行開發,後來更新到Windows 8/8.1。
1.9 第三方元件
使用Developer Express套件對架構的UI部分進行布局,主要應用在Menu、MdiTabForm、DockPanel這三個方面。
使用PCOMM.DLL對序列槽通道進行操作,沒有使用微軟自帶的SerialPort元件,因為這個元件與一些工業序列槽卡不相容,請參見:
SerialPort操作PCI-1621D多序列槽卡,出現異常"參數不正确"OPC服務端使用的是OPC基金會的WtOPCSvr.dll元件,但是這個需要正版授權。OPC用戶端使用的是OPCDAAuto.dll元件。可以在
http://pan.baidu.com/s/1pJ7lZWf下載下傳SuperIO_Demo.rar事例代碼,裡邊有完整的OPC服務端和用戶端的代碼。事例說明:
http://www.bmpj.net/article-11-1.html。
1.10 小結
從軟體設計角度,架構是一個可複用的軟體架構解決方案,規定了應用的體系結構,闡明軟體體系結構中各層次間及其層次内部各元件間的毅力關系,責任配置設定和控制流程,表現為一組接口,抽象類以及執行個體間協作的方法。
架構決定了一個軟體的生命力,一個好的架構更能促進我們對它的持續維護、重構、完善。
下一單将介紹(SuperIO)架構總體的設計。
作者:唯笑志在
Email:[email protected]
QQ:504547114
.NET開發技術聯盟:54256083