本文篇幅較長,主要涉及以下內容:
-
介紹傳統 CLI 配置網絡設備存在的挑戰,網管協議出現的背景
-
SNMP 原理,交互過程,以及 trade-off
-
NETCONF 架構,交互過程
-
RESTCONF 架構,和 NETCONF 的對比
隨着 5G 的大火,SDN, NFV 等概念被頻繁提及。想要更好的理解這些概念,網絡協議自然是對必不缺少的一環。
拿 SDN 來說,全稱為 Software Defined Networking - 軟件定義網絡。從傳統網絡來說,整體采用分布式的架構,控制平面和轉發平面都位於同一台設備上。在運維,以及靈活性上都有着不小的挑戰。
而 SDN 的出現,將控制平面和轉發平面解耦,並將所有的設備統一管理起來,使得網絡具有了可編程的能力,從面相服務的角度,根據業務需要,實時動態的調整設備的配置或狀態,大大降低了管理難度。
那么 NETCONF,RESTCONF 這樣的協議又是起到怎樣的作用呢?
這就要從 SDN 架構說起,SDN 主要有三個角色,SDN 應用,SDN 控制,網絡設備。
SDN 應用一般會通過 HTTP 的方式,調用 SDN 控制器暴露的接口,而 SDN 控制器,會通過 NETCONF,RESTCONF 類似的協議,與設備進行交互,進行業務的下發。
可見,NETCONF 類似的協議起到和設備直接交互的作用。
還有最近 DEVOPS 概念的流行,也強調從傳統人工 CLI 配置,過度到自動化的網絡配置。而 NETCONF 類似協議,就讓這些自動化操作成為可能,比如現在的 ANSIBLE,Python 的各種類庫。
下面是網管協議的實際用例,可以看到涵蓋的范圍已經非常之廣:
下面就從傳統 CLI 面臨的挑戰開始,來詳細了解下這些發揮着重要作用的協議。
傳統命令操作帶來的主要挑戰
采用傳統 CLI 配置方式主要存在着如下的挑戰:
在兼容性方面,若是網絡工程師的話肯定深有體會。
拿配置靜態路由舉例, Cisco 設備命令如下:
Router(config)#ip route 0.0.0.0 0.0.0.0 10.10.10.1
而對於華為和華三設備來說:
Router(config)#p route-static 0.0.0.0 0.0.0.0 10.10.10.1
有時不光是不同廠商之間的命令不同,甚至同一廠商不同型號之間的命令也不相同。
比如思科針對不同的場景就區分了不同的網絡軟件系統:
- 針對於企業的 IOS
- 針對於運營商的 IOS-XR
- 針對於數據中心的 NX-OS
- 以及面向下一代的 IOS-XE,將數據層面和控制解耦,底層支持 Linux.
而出錯率這方面,更不必說,人工配置遠沒有機器配置的准確以及迅速。
而且目前的網絡在規模和需求上也和之前大不一樣,比如在實時性上,作為運營商需要根據業務需求動態調整策略如 EVPN,L3VPN,L2TP。傳統 CLI 手工配置根本無法滿足,而無法做到維護管理。而現在的常用解決方案都是利用一些現成的 SDN Controller 進行實時調整如 Cisco 的 NSO.
在數據采集方面,傳統人工定時登上設備材料系統日志,分析情況,這更加無法適用。在故障響應上,數據采集,分析都存在先天的不足。比如收集效率低,數據的利用率延遲或不高。
最后從商業成本的考慮,人工的維護方案也是較高的一筆輸出。
而且對於工程師而言,需要不斷學習不同廠商的配置命令,學習成本很高,但意義不大。
通常來說,網絡工程師在開始一個項目前,會進行如下四個部分:
- 了解用戶的需求
- 針對用戶的需求,確定相應的具體方案。
- 根據用戶的方案,查找並學習對應設備的配置命令
- 最后申請割接窗口,准備回滾方案並實施。
在這里的第三步,其實就是一個比較耗時,但沒多少意義的過程。因為在集中學習不同廠商的設備命令,但從業務考慮明明解決的都是同一個問題。
在發現 CLI 管理設備的方式出現瓶頸后,並不是馬上過度到現在流行的網絡自動化配置方式,而是先推出了一個叫 Simple Network Management Protocol
- SNMP 的應用層協議,甚至在當前的一些現網中,依然被使用。
SNMP
SNMP 的出現,主要想解決兩個問題:
- 設備信息的采集
- 使用 GUI 替代 CLI 的方式進行設備配置下發
但由於其讀多寫少的特點,現被廣泛用於設備信息的監控和采集。
SNMP 目前共有三個版本:
- SNMP V1,第一個版本。在管理設備上,采用明文的方式,有
read-only
,read-write
,trap
三種和設備通信的方式。 - SNMP V2,主要改進了性能,安全性以及設備交流的方式。
- SNMP V3,主要優化了安全性,增加了一些更強的認證流程。
SNMP 原理
SNMP 整體架構上有些類似於 Client / Server,其主要的工作組件主要有三個:
-
SNMP Manager:,主要用於管理網絡中的多個設備,對其進行讀和寫的操作。類似於 Server.
-
SNMP Agent:運行在網絡設備上,通常都需要手動開啟。作為 SNMP 代理,在收到 SNMP Manager 發出請求后,對請求的內容進行解析,然后對設備進行配置,將配置的結果作為 Response 回復給 Manager.
-
SNMP MIB: MIB - Management Information Base 全稱為信息管理庫。可以將其理解成用於交互的一種數據模型,也就是交互的規則。MIB 同樣存在於網絡設備中。定義和描述了如何管理設備上的資源。Manager 和 Agent 之間的交流的信息就是 MIB 的內容。
可以看到一個 Manager 可以管理網絡中的多個設備。而每台設備上運行着 SNMP Agent 用於和 Manger信息交互,交流的內容需要符合 MIB 的規范。
看到這,可能對 MIB 這個概念還是有些模糊。這樣,我們先不從最后的結果來分析這個組件的作用,而是從設計的角度,來說一下推導下為什么要有 MIB 這個東西?
這里想要實現的是通過 Manager 去管理網絡上的 Agent(其實就是管理設備)。那么如何管理呢,比如 Manager 想要獲取 Agent1 的 GigabitEthernet0/0/0/1 的 IP 地址。
這時就需要在 Agent1 上先約定好一個內容,比如當 Agent 接收到 1.1
這個字符串時,就會將接口的信息返回給 Manager.
之后如果 Manager 發送 1.1
就能獲取到接口的信息了,但發送別的內容,Agent 是無法識別並工作的。MIB 本質就是這樣,確定了如 1.1
這樣的一組規則,去規范信息交互的訪問方式。
其實,這里的 1.1
就是 MIB 中的一個對象,在 MIB 中還以層級的方式存在着許多這樣的對象,將網絡的設備的資源抽象成形如 1.1
對象。通過這些對象,Manger 和 Agent 就可以實現很好的交流了。
真正的 MIB 類似與下圖,而這里形如 1.3.6.1.1.1.2
這樣連接起來的字符串稱為 ASN,其實就是對應了設備上的各種資源,Manager 和 Agent 也通過它們進行交流。
SNMP 操作
SNMP Manger 和 SNMP Agent 間的交互主要有三種類型:
- SNMP Get
- SNMP SET
- SNMP Notifications
SNMP Get:主要是檢索設備的信息,Get 一種有三種類型:
- GET - 從 SNMP agent 獲取固定的對象。
- GETNEXT - 檢索當前對象的后一個對象,由於 MIB 本身層級的樹形結構,存在后繼。
- GETBULK - 獲取一組固定的對象。
SNMP SET:主要是修改 MIB 中的對象,進而修改設備的配置。
SBMP Notifications:是 SNMP 的主要特性,之前的 GET 和 SET 是屬於拉的操作,而 SNMP 正好相反,類似於推的操作,可以由 agent 發起,將一些信息 push 到 SNMP Manager 上。類似於 Web Socket. 主要用於通知如認證失敗,重啟,斷開連接等事件。
Notifications 主要有兩種形式:Traps 和 Informs. 兩者間的不同主要在於可靠性,agent 在產生 Informs 給 Manager 后,如果發送失敗,會重新發送。Manager 收到后,需要回復確認給 agent。
而 Traps 不同,無論消息發送是否成功,Manager 都不需要回復。
SNMP 缺點
雖然 SNMP 的出現,在一定程度上解決了網絡設備的管理問題。但面對現代大規模的網絡來說,依然有着很多挑戰:
- 性能不足,在下發和讀取配置時,采用依次讀取,效率低。
- 下發不足,支持寫 MIB 的對象相對於讀較少。
- 不支持事務機制,在配置下發失敗是,無法回滾。
- 拓展性差,提供給外部的接口較少。
- 模型兼容性差,MIB 庫混亂,無法適配所有廠商,導致定義各種私有 MIB 庫。
面對這些問題,06 年由 IETF 領導並開發出了一個新的協議 - NETCONF,網絡管理協議。和 SNMP 不同,NETCONF 基於 RPC 的方式,天生就能很好的支持事務回滾等操作,從而更好地處理復雜網絡的各種需求。
NETCONF
NETCONF 協議提供了一種更簡單的方式來管理("查詢,配置,修改,刪除")設備,就像數據庫操作中的 DML. 同時開放了 API 接口,當想要對設備進行操作時,直接通過調用 API 進行。
對於支持 NETCONF 的設備來說,至少能開啟一個或多個 session。並且在每個 session 中應用的配置更改,都可以被全局的 session 監聽到。這就讓一個或多個 Manager(Client) 操作同一個設備(agent)成為了可能。
相比 SNMP 而言,有着如下的優勢:
- 基於 RPC,增加了事務支持
- 優化查詢功能,增加過濾查詢方式
- 拓展性強,在其協議內部分為 4 層,各層之間相互獨立
- 更好的將配置和狀態數據解耦,並區分狀態數據(candidate, running, startup)
- 易使用,結合提供的 API,實現可編程性的網絡操作
- 安全性更好,在傳輸層可選用 SSH,TLS 協議等。
NETCONF 采用 C/S 的架構,通過 RPC 在 client 和 server 間交流。client 可以是 Python 腳本或應用。server 一般指的是網絡設備,在具體實現上有三個組件:
-
NETCONF agent:運行在網絡設備上,用於接收和處理 RPC 請求。還可主動將一些告警事件通知客戶端。
-
NETCONF 客戶端:利用 NETCONF 協議對網絡設備進行管理以及接收 agent 發出的告警通知。
-
datastore:在 NETCONF 中,區分了多個不同類型的 datastore, 這些 datastore 保存着不同狀態下的設備信息。
關於 datastore 可以將其理解成一個可以獲取和存儲信息的概念。在具體實現上,可以是文件,數據庫,內存等等。
在 NETCONF 中常用到三類 datastore:
-
startup configuration datastore: 保存了設備啟動時,加載的配置信息。
-
candidate configuration datastore: 保存了想要運行的配置信息,修改該數據庫時,並不會影響設備的真實配置。
-
running configuration datastore: 保存了當前設備上正在生效的配置,修改時會影響真實的設備。
此外提到 datastore 就必須要提到一種數據模型語言 —— YANG,datestore 中就是以 YANG 的形式來約束配置的數據。
YANG 的出現結合上 NETCONF 和 RESTCONF 這樣的協議,為自動化,可編程化的網絡提供了強大的支持。YANG 的本質和之前 SNMP 中 MIB ASN 一樣,作用都是以一種方式來約束數據,關於 YANG 之后會寫一篇文章單獨介紹。
NETCONF 協議架構
NETCONF 分為 4 層,各層之間項目獨立。
- 內容層:
這一層包含了以 XML 或 JSON 格式的配置數據,也就是想對設備進行管理的具體內容。(由 XSD 或者 YANG 約束生成)
- 操作層:
定義了 Client 和 Server 交互時的一系列操作方法,用於獲取或修改配置數據。
- 消息層:
為編碼數據時,提供了一種 RPC 和通知的機制:
* RPC invocations(<rpc> messages)
* RPC results(<rpc-reply> messages)
* event notifications(<notification> messages)
- 傳輸層:
NETCONF 使用 SSH 或 TLS 協議,保證數據在 Client 和 Server 傳輸的安全性。
NETCONF 交互
對於 Manager 和 Agent 來說,Session 建立會經歷如下的過程:
- Manager 請求 NETCONF 中 SSH 子系統建立連接。
- Agent 回復 Hello 消息,包含本身支持的特性和能力。
- Manager 告知 Agent 自己所支持的特性和能力。
- Manager 開始發送 RPC 操作請求。
- Agent 回復 RPC 請求操作結果。
具體看下 NETCONF 中消息的報文結構,以修改接口配置舉例:
Manager 請求變更接口配置:
<rpc message-id="101" xmlns="urn:ietf:params:xml:ns:netconf:base:1.0">
<edit-config>
<target>
<running/>
</target>
<config>
<top xmlns="http://example.com/schema/1.2/config">
<interface>
<name>Ethernet0/0</name>
<mtu>1500</mtu>
</interface>
</top>
</config>
</edit-config>
</rpc>
Agent 回復結果:
<rpc-reply message-id="101 xmlns="urn:ietf:params:xml:ns:netconf:base:1.0">
<ok/>
</rpc-reply>
首先可以看到,NETCONF 使用 XML 作為數據傳輸的格式。
第一行的 <rpc>
標簽,表明該請求是 RPC 請求,message-id
屬性由 client/manager 確定。Agent 在回復結果時,會帶上 message-id
,用於表示該操作的結果。
urn:ietf:
屬性表示 XML 中的命令空間。 base:1.0
表示當前 NETCONF 的版本。
第二行 <edit-config>
指定執行 RPC 操作的內容為修改配置。
之后 <config>
中包裹的內容就是,想要下發的配置內容,修改 mtu 為 1500.
但這里還有一個疑問,在說到 NETCONF 時,總提到一種叫 YANG 的語言,那么它們之間的關系是什么?
在組裝修改設備配置 Payload 時,這里也沒有用到 YANG ?
其實,YANG 早已用到了。為什么 <interface>
中可以包含 <name>
和 <mtu>
屬性。而不是把 mtu
放在和 <interface>
同級。
原因就在於上面的格式,都是按照 YANG 的約束而來。
在設備中,存在着許多的 YANG Module,這些 Module 都是由 YANG 語言編寫的文件。當 agent
接收到 RPC 請求時,會通過 YANG Module 來校驗發來的數據,格式是否合法。
簡單來說,可以把 YANG 理解成一份約束文件,里面規定着傳來參數的格式,是數組,對象還是其他格式。
至於說為什么 YANG 文件能約束 XML 的文件格式,原因在於 YANG 和 XML 之間是可以相互轉換的,甚至 YANG 還可以轉換成 JSON. 在之后的 RESTCONF 中會提到這一點。
到目前為止,對 NETCONF 已經有了一個大體認識:
NETCONF 的出現是為了彌補像 SNMP 這些協議的不足。更好的滿足現在網絡的需要,在易用性,拓展性等等方面都做出了進一步優化,從而更方便,高效的管理網絡。
究其本質,NETCONF 是由多個協議組裝而成。數據的產生及校驗通過 YANG,數據的格式是 XML. 接口的調用通過 RPC,數據的傳輸通過 SSH.
NETCONF 操作
Server 端:打開設備 NETCONF
# 打開 netconf
netconf-yang
# 查看 netconf 進程
show platform software yang-management
Client 端:測試設備 NETCONF
ssh admin@IP -p 830 -s netconf
關於 NETCONF 具體實現編程化操作,可以參見 YANG 這篇。
RESTCONF
在談起 RESTCONF 前,想必剛接觸這個概念的人都會有這樣一個疑問 RESTCONF 和 REST 到底有沒有關系?
再回答這個問題前,先來回憶一下什么是 REST,以及 REST 出現的背景。
REST - Representational State Transfer,全稱為表現層狀態轉化,是建立在 HTTP 基礎上,對其進行規范的一種架構風格要求。
注意,REST 是一種設計的風格,而不是標准。
其認為,網絡中的實體都是以資源的方式存在,但資源卻存在着多種表現形式,取決於使用者的需要。比如一個用戶的信息,可以用 XML, JSON, 甚至是 txt 等多種方式表現出來。將不同的網絡資源轉換成不同的表現形式,就是其表現層的體現。
而狀態轉移來說,由於 HTTP 本身是無狀態的協議,所以資源的狀態全都保存在服務端。當對服務端的資源進行操作時,必然存在數據狀態的改變。
但由於狀態的改變基於表現層,所以稱為表現層狀態轉移。
在具體實現上,URI 定義了訪問資源的具體路徑,而 HTTP 中 Header 的 Content-Type
和 Accept
決定了了表現層的形式。
HTTP 中的 CURD 動作(Create,Put,Get,Delete,patch..)去改變服務端的資源狀態。
比如查詢書店具有的圖書:
GET http://www.store.com/products
通過 REST 的方式,更合理的實現 WEB 服務之間的交互。
這時再看 RESTCONF,就很好理解了。RESTCONF 是通過 REST 來實現對網絡設備管理的協議。其本質和 NETCONF 很像,使用 YANG 進行數據的定義和約束,使用 HTTP 進行交互。使用 NETCONF 中 datastore 的概念,進行信息的儲存。
RESTCONF 架構
圖中很好的表示了 RESTCONF 協議組成,很形象的指出 RESTCONF = NETCONF / YANG + HTTP(s).
如果拿之前的 NETCONF 協議架構作為對比,RESTCONF 就是將:
- 內容層,同樣由 YANG 約束生成。
- RPC 消息層和操作層,換成了 HTTP 的操作層。
- 將 SSH 構成的傳輸層,換成了 HTTP(s)的傳輸方式。
RESTCONF VS NETCONF 交互
圖中很好的對比了 RESTCONF 和 NETCONF 的交互過程,都是采用了 C/S 架構,在具體組件上:
NETCONF | RESTCONF | |
---|---|---|
客戶端 | NETCONF client | HTTP Client |
配置格式由誰約定 | YANG module / XSD | YANG module |
發送內容格式 | XML | XML/JSON |
交互方式 | RPC | HTTP |
傳輸協議 | SSH | HTTP(s) |
服務端 | NETCONF server | HTTP server |
對於操作來說,將 RPC 操作換成了 HTTP 操作:
RESTCONF 操作
Server 端:打開設備 RESTCONF
# 打開 RESTCONF
restconf-yang
# 查看 RESTCONF 進程
show platform software yang-management
Client 端:
由於已經采用了 REST 風格,可以利用 POSTMAN 等等 HTTP 客戶端進行測試。
關於 RESTCONF 具體實現編程化操作和其 URL 的使用是非常重要的一部分,但由於其依賴 YANG 這個概念,這個后面會單獨提到,可以參見 YANG 這篇。
總結
這篇文章,耗時很久,查閱了大量資料,完成后真的如釋重負一般。
當然對網管協議也有了進一步的理解。
下面做一個簡單的總結:
傳統 CLI 配置方式,已經無法滿足當代網絡可編程化的需要,而且在兼容性,易用性,正確率存在着諸多問題,進而網管協議應運而生。
SNMP 作為推出的第一代協議,在一定程度上解決了設備管理的問題。但由於其讀多寫少的特點,以及在兼容性,效率,以及缺乏事務性的不足,在現網中,一般用其作為設備配置采集或監控的工具。
為了更好的滿足網絡的需要,第二代協議 NETCONF 出現,由於 NETCONF 天生 RPC 支持事務的特點,再加上 YANG 解決了多廠商命令兼容性的問題,現被廣泛使用在各種網管平台,SDN 控制器中。
隨后 HTTP REST 風格的普及,IETF 又推出了 RESTCONF 協議,將 NETCONF 和 HTTP 整合在一起,以更為流行的方式,實現對設備的管理。