无法在 ONVIF 中实现事件订阅

Unable to implement event subscription in ONVIF

我正在通过使用 Onvif 设备管理器 dll(onvif.services、发现、会话和 utils.async、通用、诊断、fsharp dll)来实现 ONVIF。

到目前为止,我能够发现 onvif 设备,获取范围(设备信息)及其配置文件,流式传输视频并实现 ptz 控制。

现在我正在实施事件订阅,但我无法订阅任何特定事件。

Here is my code of event subscription. and i don't know what to do next.

OnvifParam deviceparam = ONVIFDevices[listBox1.SelectedIndex];
deviceparam.Account = new NetworkCredential { UserName = "admin", Password = "admin" };
var sessionFactory = new NvtSessionFactory(deviceparam.Account);

int listenport = 8085;
string EventListeningPort = null;
int.TryParse(EventListeningPort, out listenport);
Uri uri = new Uri(deviceparam.Uris[0].ToString());
deviceparam.URL = uri.ToString();
Profile[] profiles = null;
var f = sessionFactory.CreateSession(uri);
profiles = f.GetProfiles().RunSynchronously();
deviceparam.Profiles = profiles;

OdmSession o = new OdmSession(f);

var subs = o.GetBaseEvents(listenport).Subscribe();

var eventprop = f.GetEventProperties();

FilterType filter = new FilterType();

谁能告诉我如何实现事件订阅?

经过大量阅读和搜索,我已经使用 Onvif 设备管理器 dll 实现了事件。

我们可以通过三种方式订阅事件。

1.Real时间Pull-Point通知接口。(Pull-Point机制)

2.Basic通知接口。(推送机制)

3.Notification 流接口。 (元数据流)

实时Pull-Point通知界面

这个界面提供了一个防火墙友好的通知界面。在此客户端中,将定期从相机中拉取拉取事件的消息。所以我们创建一个 pull-point 订阅,然后从相机中提取事件。

CODE

class Events
{
   public void GenerateEvent()
    {
        // for this device must be discoverable and and its account and uri must be known

        var sessionFactory = new NvtSessionFactory(deviceparam.Account); // deviceparam is camera and account contaion its username and password
        var sess = sessionFactory.CreateSession(uri);
        OdmSession os = new OdmSession(sess);
        os.GetPullPointEvents()// this function contains function for the subscription and pull messages
            .Subscribe(
            evnt =>
            {
                Console.WriteLine(EventParse.ParseTopic(evnt.topic));
                var messages = EventParse.ParseMessage(evnt.message);
                messages.ForEach(msg => Console.WriteLine(msg));
            }, err =>
            {
                Console.WriteLine(err.Message);
            }
            );

    } 
}

public static class EventParse
{
    public static string ParseTopic(TopicExpressionType topic) 
    {
        string topicString = "";

        topic.Any.ForEach(node => {
            topicString += "value: " + node.Value;
            });

            return topicString;
    }

    public static string[] ParseMessage(Message message) 
    {
        List<string> messageStrings = new List<string>();

        messageStrings.Add("messge id: " + message.key);

        if(message.source!= null)
            message.source.simpleItem.ForEach(sitem => 
            {
                string txt = sitem.name + " " + sitem.value;
                messageStrings.Add(txt);
            });

        if (message.data != null)
            message.data.simpleItem.ForEach(sitem => 
            {
                string txt = sitem.name + " " + sitem.value;
                messageStrings.Add(txt);
            });

        return messageStrings.ToArray();
    }
}

基本通知界面。(推送机制)

在此界面中,相机将通知客户端有关事件。发送Notification的连接是由摄像头发起的,建立在TCP协议上,所以这里需要防火墙的权限。

此接口的优点是客户端不需要是设置订阅的同一实体,即相机可以在订阅完成后将事件发送给任何客户端。

CODE

class Events
{
    public void GenerateBaseEvent()
    {
        // for this device must be discoverable and and its account and uri must be known

        var sessionFactory = new NvtSessionFactory(deviceparam.Account); // deviceparam is camera and account contaion its username and password
        var sess = sessionFactory.CreateSession(uri);
        OdmSession os = new OdmSession(sess);
        os.GetBaseEvents(9865)// some random port number
            .Subscribe(
            evnt =>
            {
                Console.WriteLine(EventParse.ParseTopic(evnt.topic));
                var messages = EventParse.ParseMessage(evnt.message);
                messages.ForEach(msg => Console.WriteLine(msg));
            }, err =>
            {
                Console.WriteLine(err.Message);
            }
            );

    }
}

通知流接口

在此界面中,我们通过 RTP 或 RTSP 流接收 real-time 中的事件通知。首先,设置一个媒体配置文件,其中包含一个带有所需事件过滤器的 MetadataConfiguration。之后,流 可以获取和使用该配置文件的 URI。

我还没试过这个界面

以上代码没有过滤器,所以它会为所有事件发出通知。