最近对onos进行了二次开发,次要实现了Juniper路由器的 driver开发。在Driver中利用NETCONF协定读取并批改路由器配置、生成NETCONF命令、并下发到路由器是Driver开发的重要局部。开发过程中,咱们研读了onos里NETCONF相干的代码,理解设施是如何进行连贯,session是如何创立,命令是如何发送的。在这里分享给大家。

一、后期筹备

要进行设施的连贯,有两个很重要的前提。一个是物理设施能够被onos控制器所辨认。第二个是该设施对应的驱动曾经在控制器中加载。只有这两个前提条件被满足,onos能力与设施进行连贯,从而下发管制命令。

对于驱动是如何加载的剖析,咱们将会在后续的文章中进行介绍。

二、设施连贯的建设

进入正题,当控制器要对具体的设施进行管制时,第一步要做的就是与该设施进行连贯。

首先进入的是org.onosproject.net.device.impl.DeviceManager的deviceConnected办法。

1、依据设施所属的BasicDeviceConfig取得设施的根本配置。

2、依据传进来的deviceDescription和取得的配置信息从新更新deviceDescription并且创立role(master、none、standby等)

3、调用applyRole(deviceId,role)将设施与role绑定。须要留神的是,当调用完这个办法之后就曾经创立了onos与设施的连贯,并将创立的session保存起来,不便当前调用(具体的实现请往下看)。

4、将device的信息存入store中。

走到这一步,onos就实现了与设施的连贯,当须要对设施发送命令时,只有找到对应的session就能够进行发送了。

从下面的剖析咱们晓得applyRole是一个很重要的办法。接下来咱们就剖析一下applyRole是如何实现上述的性能。

从下面的源码中咱们看到,在applyRole函数中最要害的就是调用了DeviceProvider的roleChanged(deviceId,newRole)函数。因为DeviceProvider是一个接口,它具体实现的类是NetconfDeviceProvider,对应的函数是Rolechanged。

能够看出,在roleChanged函数中,依据role的类型进行不同的解决。特地留神的是,当role显示为master时,通过initiateConnection函数调用NetconfControllerImpl类的connectDevice(deviceId)办法,实现NetconfDeviceInfo和NetconfDevice 的创立。并实现与设施的连贯。

上面是NetconfControllerImpl类中connectDevice(deviceId)函数的具体代码:

首先通过deviceId从deviceService中取得username、password等信息。而后依据失去的用户信息以及之前存储的设施信息生成NetconfDeviceInfo。再依据生成的NetconfDeviceInfo,最初通过createDevice函数调用deviceFactory的createNetconfDevice办法生成NetconfDevice,同时与该设施进行连贯。

createNetconfDevice办法的具体实现在NetconfControllerImpl类中。在该办法中他调用了DefaultNetconfDevice的构造函数,创立了NetconfDevice。从下图构造函数代码中,咱们能够看见,零碎在创立NetconfDevice的同时,也创立了netconfSession,并将www.sangpi.com作为netconfSession作为Device的一个属性保存起来。当用户须要与某设施进行交互时,只须要找到对应的Device对象,就能取得与该设施进行交互的session。

【留神】以下就是onos与device进行连贯的具体代码。

与DeviceFactory一样,SessionFactory的createNetconfSession函数,也是调用了NetconfSessionImpl的构造函数,进行netconfSession的创立。

与设施进行连贯的操作是通过NetconfSessionImpl类startConnection函数实现的。

1、依据deviceInfo的ip和port的信息构建connection。

2、调用connect函数游戏进行是否连贯

3、依据deviceinfo中的username等信息,看用户是否被受权。

4、如果用户被受权则调用startSshSession

在startSshSession中,创立Stream线程为当前的交换提供服务。同时向设施发送hello的NETCONF命令,实现两个设施间所反对性能的同步,为当前应用NETCONF命令进行交换打下基础。

至此onos就实现了与设施的连贯,并将创立的session保留在netconfController中。在下一节中咱们将介绍如何应用创立的session进行命令的发送。

三、NETCONF命令的发送

当控制器与设施建设好连贯当前,咱们就能够通过控制器想设施发送命令了。

本文以onos中的device-configuration命令为例,解说netconf命令是如何下发,同时控制器是如何取得路由器返回信息的。

3.1 NETCONF命令发送

当用户在onos的终端输出device-configuration命令当前,就进入了org.onosproject.cli.net.DeviceConfigGetterCommand中。

零碎依据具体的配置文件,找到ConfigGetter接口的具体实习类——NetconfConfigGetter。

在上一节咱们介绍过,在NetconfControllerImpl的createDevice函数中,零碎将生成的Device放入到了DevicesMap中,不便日后应用。

所有当须要发送命令的时候,零碎先从NetconfController里的DevicesMap中取得对应的Device,而后依据失去的Device找到对应的NetconfSession。

在取得session当前,依据用户传入的信息构建对应的NETCONF命令。并通过NetconfSessionImpl中的sendRequest函数将命令发送给设施。

在sendRequest中,先对传入的request格局进行查看,确保合乎NETCONF命令的标准。

确保request符合规范当前,应用request函数将request发送给设施。同时返回CompletableFuture futureReply。futureReply次要是用来读取设施返回的信息。如果设施无奈在规定的工夫内返回信息,则零碎会抛出异样。

上面让咱们看一下onos是如何发送信息的。

进入到NetconfSessionImpl的request函数:

3.2 设施返回信息读取

当NetconfStreamThread对象中的run函数承受到设施返回的信息当前,会对信息进行解析生成事件,发送给监听器,并将信息传播给CompletableFuture。

此时在主线程的sendRequest函数中,通过调用CompletableFuture的get办法取得返回信息。

至此,NETCONF命令的下发和信息的返回过程就完结了。

不晓得我有没有讲清楚,欢送大家拍砖探讨。