如何从客户端应用程序 (Dash.js) 向 OpenFlow 交换机发送消息

Posted

技术标签:

【中文标题】如何从客户端应用程序 (Dash.js) 向 OpenFlow 交换机发送消息【英文标题】:How to sending messages from a client application (Dash.js) to the OpenFlow Switch 【发布时间】:2015-11-17 22:53:17 【问题描述】:

我有一个名为 Dash.js 的客户端应用程序,即视频播放器,它在模拟带有交换机和 openflow 控制器的 SDN 网络的环境中运行。

此应用程序使视频质量适应用户网络的带宽。

确定客户端是否会请求替换段以适应可用带宽的类是 AbrController.js。

MediaPlayer.dependencies.AbrController = function () 
    "use strict";

    var autoSwitchBitrate = true,
        qualityDict = ,
        confidenceDict = ,

        getInternalQuality = function (type) 
            var quality;

            if (!qualityDict.hasOwnProperty(type)) 
                qualityDict[type] = 0;
            

            quality = qualityDict[type];

            return quality;
        ,

        setInternalQuality = function (type, value) 
            qualityDict[type] = value;
        ,

        getInternalConfidence = function (type) 
            var confidence;

            if (!confidenceDict.hasOwnProperty(type)) 
                confidenceDict[type] = 0;
            

            confidence = confidenceDict[type];

            return confidence;
        ,

        setInternalConfidence = function (type, value) 
            confidenceDict[type] = value;
        ;

    return 
        debug: undefined,
        abrRulesCollection: undefined,
        manifestExt: undefined,
        metricsModel: undefined,
        metricsBaselinesModel: undefined,


        getAutoSwitchBitrate: function () 
            return autoSwitchBitrate;
        ,

        setAutoSwitchBitrate: function (value) 
            autoSwitchBitrate = value;
        ,

        getMetricsFor: function (data) 
            var deferred = Q.defer(),
                self = this;

            self.manifestExt.getIsVideo(data).then(
                function (isVideo) 
                    if (isVideo) 
                        deferred.resolve(self.metricsModel.getMetricsFor("video"));
                     else 
                        self.manifestExt.getIsAudio(data).then(
                            function (isAudio) 
                                if (isAudio) 
                                    deferred.resolve(self.metricsModel.getMetricsFor("audio"));
                                 else 
                                    deferred.resolve(self.metricsModel.getMetricsFor("stream"));
                                
                            
                        );
                    
                
            );

            return deferred.promise;
        ,
        
        getMetricsBaselineFor: function (data) 
            var deferred = Q.defer(),
                self = this;

            self.manifestExt.getIsVideo(data).then(
                function (isVideo) 
                    if (isVideo) 
                        deferred.resolve(self.metricsBaselinesModel.getMetricsBaselineFor("video"));
                     else 
                        self.manifestExt.getIsAudio(data).then(
                            function (isAudio) 
                                if (isAudio) 
                                    deferred.resolve(self.metricsBaselinesModel.getMetricsBaselineFor("audio"));
                                 else 
                                    deferred.resolve(self.metricsBaselinesModel.getMetricsBaselineFor("stream"));
                                    //self.debug.log("GET STREAM.");

                                
                            
                        );
                    
                
            );

            return deferred.promise;
        ,

        getPlaybackQuality: function (type, data, availableRepresentations) 
            var self = this,
                deferred = Q.defer(),
                newQuality = MediaPlayer.rules.SwitchRequest.prototype.NO_CHANGE,
                newConfidence = MediaPlayer.rules.SwitchRequest.prototype.NO_CHANGE,
                i,
                len,
                funcs = [],
                req,
                values,
                quality,
                confidence;

            quality = getInternalQuality(type);

            confidence = getInternalConfidence(type);

            //self.debug.log("ABR enabled? (" + autoSwitchBitrate + ")");

            if (autoSwitchBitrate) 
                //self.debug.log("Check ABR rules.");

              self.getMetricsFor(data).then(
                  function (metrics) 
                    self.getMetricsBaselineFor(data).then(
                      function (metricsBaseline) 
                        self.abrRulesCollection.getRules().then(
                            function (rules) 
                                for (i = 0, len = rules.length; i < len; i += 1) 
                                    funcs.push(rules[i].checkIndex(quality, metrics, data, metricsBaseline, availableRepresentations));
                                
                                Q.all(funcs).then(
                                    function (results) 
                                        //self.debug.log(results);
                                        values = ;
                                        values[MediaPlayer.rules.SwitchRequest.prototype.STRONG] = MediaPlayer.rules.SwitchRequest.prototype.NO_CHANGE;
                                        values[MediaPlayer.rules.SwitchRequest.prototype.WEAK] = MediaPlayer.rules.SwitchRequest.prototype.NO_CHANGE;
                                        values[MediaPlayer.rules.SwitchRequest.prototype.DEFAULT] = MediaPlayer.rules.SwitchRequest.prototype.NO_CHANGE;

                                        for (i = 0, len = results.length; i < len; i += 1) 
                                            req = results[i];
                                            if (req.quality !== MediaPlayer.rules.SwitchRequest.prototype.NO_CHANGE) 
                                                values[req.priority] = Math.min(values[req.priority], req.quality);
                                            
                                        

                                        if (values[MediaPlayer.rules.SwitchRequest.prototype.WEAK] !== MediaPlayer.rules.SwitchRequest.prototype.NO_CHANGE) 
                                            newConfidence = MediaPlayer.rules.SwitchRequest.prototype.WEAK;
                                            newQuality = values[MediaPlayer.rules.SwitchRequest.prototype.WEAK];
                                        

                                        if (values[MediaPlayer.rules.SwitchRequest.prototype.DEFAULT] !== MediaPlayer.rules.SwitchRequest.prototype.NO_CHANGE) 
                                            newConfidence = MediaPlayer.rules.SwitchRequest.prototype.DEFAULT;
                                            newQuality = values[MediaPlayer.rules.SwitchRequest.prototype.DEFAULT];
                                        

                                        if (values[MediaPlayer.rules.SwitchRequest.prototype.STRONG] !== MediaPlayer.rules.SwitchRequest.prototype.NO_CHANGE) 
                                            newConfidence = MediaPlayer.rules.SwitchRequest.prototype.STRONG;
                                            newQuality = values[MediaPlayer.rules.SwitchRequest.prototype.STRONG];
                                        

                                        if (newQuality !== MediaPlayer.rules.SwitchRequest.prototype.NO_CHANGE && newQuality !== undefined) 
                                            quality = newQuality;
                                        

                                        if (newConfidence !== MediaPlayer.rules.SwitchRequest.prototype.NO_CHANGE && newConfidence !== undefined) 
                                            confidence = newConfidence;
                                        

                                        self.manifestExt.getRepresentationCount(data).then(
                                            function (max) 
                                                // be sure the quality valid!
                                                if (quality < 0) 
                                                    quality = 0;
                                                
                                                // zero based
                                                if (quality >= max) 
                                                    quality = max - 1;
                                                

                                                if (confidence != MediaPlayer.rules.SwitchRequest.prototype.STRONG &&
                                                    confidence != MediaPlayer.rules.SwitchRequest.prototype.WEAK) 
                                                    confidence = MediaPlayer.rules.SwitchRequest.prototype.DEFAULT;
                                                

                                                setInternalQuality(type, quality);
                                                //self.debug.log("New quality of " + quality);

                                                setInternalConfidence(type, confidence);
                                                //self.debug.log("New confidence of " + confidence);

                                                deferred.resolve(quality: quality, confidence: confidence);
                                            
                                        );
                                    
                                );
                            
                        );
                    
                );
               
             );
             else 
                self.debug.log("Unchanged quality of " + quality);
                deferred.resolve(quality: quality, confidence: confidence);
            

            return deferred.promise;
        ,

        setPlaybackQuality: function (type, newPlaybackQuality) 
            var quality = getInternalQuality(type);

            if (newPlaybackQuality !== quality) 
                setInternalQuality(type, newPlaybackQuality);
            
        ,

        getQualityFor: function (type) 
            return getInternalQuality(type);
        
    ;
;

MediaPlayer.dependencies.AbrController.prototype = 
    constructor: MediaPlayer.dependencies.AbrController
;

我想要的是每次有segment change的请求,都会触发openflow switch的消息,这样它就可以向控制器发送packetin,控制器采取行动。

对我来说,现在的问题是客户端和 OpenFlow 交换机之间的这种通信交换。

有谁知道如何拍摄这条消息并进入openflow开关?

谢谢!

【问题讨论】:

【参考方案1】:

您可以使用 REST API 将参数传递到您的网络。大多数 SDN 控制器公开其 API 以便与外部应用程序交互。

Ryu REST API:https://osrg.github.io/ryu-book/en/html/rest_api.html Opendaylight REST API:https://wiki.opendaylight.org/view/OpenDaylight_Controller:REST_Reference_and_Authentication

【讨论】:

以上是关于如何从客户端应用程序 (Dash.js) 向 OpenFlow 交换机发送消息的主要内容,如果未能解决你的问题,请参考以下文章

使用 ffmpeg 生成单个 MPEG-Dash 片段

如何在 dash.js 中制作具有特定比特率的视频

Dash.js 播放器在调试时不播放

使用 FFMPEG 播放 MPEG-dash 流[关闭]

如何制作自己的简单 MPEG DASH 播放器?

dash.js 无法一个接一个地播放多个视频