"""
Copyright 2015 Open Networking Foundation ( ONF )

Please refer questions to either the onos test mailing list at <onos-test@onosproject.org>,
the System Testing Plans and Results wiki page at <https://wiki.onosproject.org/x/voMg>,
or the System Testing Guide page at <https://wiki.onosproject.org/x/WYQg>

    TestON is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 2 of the License, or
    ( at your option ) any later version.

    TestON is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with TestON.  If not, see <http://www.gnu.org/licenses/>.
"""
"""
    SCPFportLat test
    Test latency for port status change
    Up & Down:
    PortStatus --- Device --- Link --- Graph

    yunpeng@onlab.us
"""
class SCPFportLat:

    def __init__( self ):
        self.default = ''

    def CASE0( self, main ):
        import os
        import imp
        """
        - GIT
        - BUILDING ONOS
            Pull specific ONOS branch, then Build ONOS ono ONOS Bench.
            This step is usually skipped. Because in a Jenkins driven automated
            test env. We want Jenkins jobs to pull&build for flexibility to handle
            different versions of ONOS.
        - Construct tests variables
        """
        try:
            from tests.dependencies.ONOSSetup import ONOSSetup
            main.testSetUp = ONOSSetup()
        except ImportError:
            main.log.error( "ONOSSetup not found. exiting the test" )
            main.cleanAndExit()
        main.testSetUp.envSetupDescription()
        stepResult = main.FALSE
        try:
            main.MN1Ip = main.params[ 'MN' ][ 'ip1' ]
            main.dependencyPath = main.testOnDirectory + \
                                  main.params[ 'DEPENDENCY' ][ 'path' ]
            main.dependencyFunc = main.params[ 'DEPENDENCY' ][ 'function' ]
            main.topoName = main.params[ 'DEPENDENCY' ][ 'topology' ]
            main.cellName = main.params[ 'ENV' ][ 'cellName' ]
            main.apps = main.params[ 'ENV' ][ 'cellApps' ]
            main.scale = ( main.params[ 'SCALE' ] ).split( "," )
            main.ofportStatus = main.params[ 'TSHARK' ][ 'ofpPortStatus' ]
            main.tsharkResultPath = main.params[ 'TSHARK' ][ 'tsharkReusltPath' ]
            main.tsharkInterface = main.params[ 'TSHARK' ][ 'tsharkInterface' ]
            main.sampleSize = int( main.params[ 'TEST' ][ 'sampleSize' ] )
            main.warmUp = int( main.params[ 'TEST' ][ 'warmUp' ] )
            main.maxProcessTime = int( main.params[ 'TEST' ][ 'maxProcessTime' ] )
            main.dbFileName = main.params[ 'DATABASE' ][ 'dbName' ]
            main.startUpSleep = int( main.params[ 'SLEEP' ][ 'startup' ] )
            main.measurementSleep = int( main.params[ 'SLEEP' ][ 'measure' ] )
            main.maxScale = int( main.params[ 'max' ] )
            main.defaultTopoCfg = main.params[ 'CFG' ][ 'defaultTopo' ]
            main.interface = main.params[ 'TEST' ][ 'interface' ]
            main.timeout = int( main.params[ 'TIMEOUT' ][ 'timeout' ] )
            main.MNSleep = int( main.params[ 'SLEEP' ][ 'mininet' ] )
            main.device = main.params[ 'TEST' ][ 'device' ]
            main.debug = main.params[ 'TEST' ][ 'debug' ]

            if main.debug == "True":
                main.debug = True
            else:
                main.debug = False

            stepResult = main.testSetUp.envSetup()
            main.log.info( "Create Database file " + main.dbFileName )
            resultsDB = open( main.dbFileName, "w+" )
            resultsDB.close()

            main.portFunc = imp.load_source( main.dependencyFunc,
                                             main.dependencyPath +
                                             main.dependencyFunc +
                                             ".py" )
        except Exception as e:
            main.testSetUp.envSetupException( e )
        main.testSetUp.envSetupConclusion( stepResult )
        main.commit = main.commit.split( " " )[ 1 ]

    def CASE1( self, main ):
        # Clean up test environment and set up
        import time
        main.testSetUp.ONOSSetUp( main.Cluster, True,
                                  cellName=main.cellName, killRemoveMax=False )

        main.log.info( "Configure apps" )
        main.Cluster.active( 0 ).CLI.setCfg( main.defaultTopoCfg,
                                                  "maxEvents 1" )
        main.Cluster.active( 0 ).CLI.setCfg( main.defaultTopoCfg,
                                                  "maxBatchMs 0" )
        main.Cluster.active( 0 ).CLI.setCfg( main.defaultTopoCfg,
                                                  "maxIdleMs 0" )
        time.sleep( 1 )
        main.log.info( "Copy topology file to Mininet" )
        main.ONOSbench.copyMininetFile( main.topoName,
                                        main.dependencyPath,
                                        main.Mininet1.user_name,
                                        main.Mininet1.ip_address )
        try:
            from tests.dependencies.utils import Utils
        except ImportError:
            main.log.error( "Utils not found exiting the test" )
            main.cleanAndExit()
        try:
            main.Utils
        except ( NameError, AttributeError ):
            main.Utils = Utils()
        main.Utils.mininetCleanup( main.Mininet1 )
        time.sleep( main.MNSleep )
        main.log.info( "Start new mininet topology" )
        main.Mininet1.startNet()
        main.log.info( "Assign switch to controller to ONOS node 1" )
        time.sleep( 1 )
        main.Mininet1.assignSwController( sw='s1',
                                          ip=main.Cluster.active( 0 ).ipAddress )
        main.Mininet1.assignSwController( sw='s2',
                                          ip=main.Cluster.active( 0 ).ipAddress )

        time.sleep( 2 )

    def CASE2( self, main ):
        import time
        import numpy
        # dictionary for each node and each timestamps
        resultDict = { 'up': {}, 'down': {} }
        for d in resultDict:
            for i in range( 1, main.Cluster.numCtrls + 1 ):
                resultDict[ d ][ 'node' + str( i ) ] = {}
                resultDict[ d ][ 'node' + str( i ) ][ 'Ave' ] = {}
                resultDict[ d ][ 'node' + str( i ) ][ 'Std' ] = {}
                resultDict[ d ][ 'node' + str( i ) ][ 'EtoE' ] = []
                resultDict[ d ][ 'node' + str( i ) ][ 'PtoD' ] = []
                resultDict[ d ][ 'node' + str( i ) ][ 'DtoL' ] = []
                resultDict[ d ][ 'node' + str( i ) ][ 'LtoG' ] = []
        for i in range( 0, main.sampleSize + main.warmUp ):
            main.log.info( "==========================================" )
            main.log.info( "================iteration:{}==============".format( str( i + 1 ) ) )
            if i >= main.warmUp:
                # Portdown iteration
                main.portFunc.capturePortStatusPack( main,
                                                     main.device,
                                                     main.interface,
                                                     "down",
                                                     resultDict,
                                                     False,
                                                     main.tsharkInterface )
                time.sleep( 2 )
                # PortUp iteration
                main.portFunc.capturePortStatusPack( main,
                                                     main.device,
                                                     main.interface,
                                                     "up",
                                                     resultDict,
                                                     False,
                                                     main.tsharkInterface )
            else:
                # if warm up, keep old result dictionary
                main.portFunc.capturePortStatusPack( main,
                                                     main.device,
                                                     main.interface,
                                                     "down",
                                                     resultDict,
                                                     True,
                                                     main.tsharkInterface )
                main.portFunc.capturePortStatusPack( main,
                                                     main.device,
                                                     main.interface,
                                                     "up",
                                                     resultDict,
                                                     True,
                                                     main.tsharkInterface )

        # Dictionary for result
        maxDict = {}
        maxDict[ 'down' ] = {}
        maxDict[ 'up' ] = {}
        maxDict[ 'down' ][ 'max' ] = 0
        maxDict[ 'up' ][ 'max' ] = 0
        maxDict[ 'down' ][ 'node' ] = 0
        maxDict[ 'up' ][ 'node' ] = 0
        EtoEtemp = 0
        for d in resultDict:
            for i in range( 1, main.Cluster.numCtrls + 1 ):
                # calculate average and std for result, and grep the max End to End data
                EtoEtemp = numpy.average( resultDict[ d ][ 'node' + str( i ) ][ 'EtoE' ] )
                resultDict[ d ][ 'node' + str( i ) ][ 'Ave' ][ 'EtoE' ] = EtoEtemp
                if maxDict[ d ][ 'max' ] < EtoEtemp:
                    # get max End to End latency
                    maxDict[ d ][ 'max' ] = EtoEtemp
                    maxDict[ d ][ 'node' ] = i
                resultDict[ d ][ 'node' + str( i ) ][ 'Ave' ][ 'PtoD' ] = numpy.average( resultDict[ d ][ 'node' + str( i ) ][ 'PtoD' ] )
                resultDict[ d ][ 'node' + str( i ) ][ 'Ave' ][ 'DtoL' ] = numpy.average( resultDict[ d ][ 'node' + str( i ) ][ 'DtoL' ] )
                resultDict[ d ][ 'node' + str( i ) ][ 'Ave' ][ 'LtoG' ] = numpy.average( resultDict[ d ][ 'node' + str( i ) ][ 'LtoG' ] )

                resultDict[ d ][ 'node' + str( i ) ][ 'Std' ][ 'EtoE' ] = numpy.std( resultDict[ d ][ 'node' + str( i ) ][ 'EtoE' ] )
                resultDict[ d ][ 'node' + str( i ) ][ 'Std' ][ 'PtoD' ] = numpy.std( resultDict[ d ][ 'node' + str( i ) ][ 'PtoD' ] )
                resultDict[ d ][ 'node' + str( i ) ][ 'Std' ][ 'DtoL' ] = numpy.std( resultDict[ d ][ 'node' + str( i ) ][ 'DtoL' ] )
                resultDict[ d ][ 'node' + str( i ) ][ 'Std' ][ 'LtoG' ] = numpy.std( resultDict[ d ][ 'node' + str( i ) ][ 'LtoG' ] )

                main.log.report( "=====node{} Summary:=====".format( str( i ) ) )
                main.log.report( "=============Port {}=======".format( str( d ) ) )
                main.log.report(
                    "End to End average: {}".format( str( resultDict[ d ][ 'node' + str( i ) ][ 'Ave' ][ 'EtoE' ] ) ) )
                main.log.report(
                    "End to End Std: {}".format( str( resultDict[ d ][ 'node' + str( i ) ][ 'Std' ][ 'EtoE' ] ) ) )
                main.log.report(
                    "Package to Device average: {}".format( str( resultDict[ d ][ 'node' + str( i ) ][ 'Ave' ][ 'PtoD' ] ) ) )
                main.log.report(
                    "Package to Device Std: {}".format( str( resultDict[ d ][ 'node' + str( i ) ][ 'Std' ][ 'PtoD' ] ) ) )
                main.log.report(
                    "Device to Link average: {}".format( str( resultDict[ d ][ 'node' + str( i ) ][ 'Ave' ][ 'DtoL' ] ) ) )
                main.log.report(
                    "Device to Link Std: {}".format( str( resultDict[ d ][ 'node' + str( i ) ][ 'Std' ][ 'DtoL' ] ) ) )
                main.log.report(
                    "Link to Grapg average: {}".format( str( resultDict[ d ][ 'node' + str( i ) ][ 'Ave' ][ 'LtoG' ] ) ) )
                main.log.report(
                    "Link to Grapg Std: {}".format( str( resultDict[ d ][ 'node' + str( i ) ][ 'Std' ][ 'LtoG' ] ) ) )

        # Check if any result is abnormal
        # Port-up
        result = resultDict[ 'up' ][ 'node' + str( maxDict[ 'up' ][ 'node' ] ) ][ 'Ave' ][ 'EtoE' ]
        threshold = float( main.params[ 'ALARM' ][ 'maxPortUpAvg' ].split( ',' )[ main.cycle - 1 ] )
        if result > threshold:
            main.log.alarm( "{}-node port-up avg: {} ms > {} ms".format( main.Cluster.numCtrls, result, threshold ) )
        result = resultDict[ 'up' ][ 'node' + str( maxDict[ 'up' ][ 'node' ] ) ][ 'Std' ][ 'EtoE' ]
        threshold = float( main.params[ 'ALARM' ][ 'maxPortUpStd' ].split( ',' )[ main.cycle - 1 ] )
        if result > threshold:
            main.log.alarm( "{}-node port-up std: {} ms > {} ms".format( main.Cluster.numCtrls, result, threshold ) )
        # Port-down
        result = resultDict[ 'down' ][ 'node' + str( maxDict[ 'down' ][ 'node' ] ) ][ 'Ave' ][ 'EtoE' ]
        threshold = float( main.params[ 'ALARM' ][ 'maxPortDownAvg' ].split( ',' )[ main.cycle - 1 ] )
        if result > threshold:
            main.log.alarm( "{}-node port-down avg: {} ms > {} ms".format( main.Cluster.numCtrls, result, threshold ) )
        result = resultDict[ 'down' ][ 'node' + str( maxDict[ 'down' ][ 'node' ] ) ][ 'Std' ][ 'EtoE' ]
        threshold = float( main.params[ 'ALARM' ][ 'maxPortDownStd' ].split( ',' )[ main.cycle - 1 ] )
        if result > threshold:
            main.log.alarm( "{}-node port-down std: {} ms > {} ms".format( main.Cluster.numCtrls, result, threshold ) )

        with open( main.dbFileName, "a" ) as dbFile:
            # Scale number
            temp = str( main.Cluster.numCtrls )
            temp += ",'baremetal1'"
            # put result
            temp += "," + str( resultDict[ 'up' ][ 'node' + str( maxDict[ 'up' ][ 'node' ] ) ][ 'Ave' ][ 'EtoE' ] )
            temp += "," + str( resultDict[ 'up' ][ 'node' + str( maxDict[ 'up' ][ 'node' ] ) ][ 'Ave' ][ 'PtoD' ] )
            temp += "," + str( resultDict[ 'up' ][ 'node' + str( maxDict[ 'up' ][ 'node' ] ) ][ 'Ave' ][ 'DtoL' ] )
            temp += "," + str( resultDict[ 'up' ][ 'node' + str( maxDict[ 'up' ][ 'node' ] ) ][ 'Ave' ][ 'LtoG' ] )
            temp += "," + str( resultDict[ 'down' ][ 'node' + str( maxDict[ 'down' ][ 'node' ] ) ][ 'Ave' ][ 'EtoE' ] )
            temp += "," + str( resultDict[ 'down' ][ 'node' + str( maxDict[ 'down' ][ 'node' ] ) ][ 'Ave' ][ 'PtoD' ] )
            temp += "," + str( resultDict[ 'down' ][ 'node' + str( maxDict[ 'down' ][ 'node' ] ) ][ 'Ave' ][ 'DtoL' ] )
            temp += "," + str( resultDict[ 'down' ][ 'node' + str( maxDict[ 'down' ][ 'node' ] ) ][ 'Ave' ][ 'LtoG' ] )

            temp += "," + str( resultDict[ 'up' ][ 'node' + str( maxDict[ 'up' ][ 'node' ] ) ][ 'Std' ][ 'EtoE' ] )
            temp += "," + str( resultDict[ 'down' ][ 'node' + str( maxDict[ 'down' ][ 'node' ] ) ][ 'Std' ][ 'EtoE' ] )

            temp += "\n"
            dbFile.write( temp )
            dbFile.close()
