Skip to content
Snippets Groups Projects
rules_injector.py 6.88 KiB
Newer Older
#!/usr/bin/python

import requests
import json
import sys
import os
import glob

debug=1

def AuthenticatedHTTP_GetRequest(urlPre,service,user,passw):

    URI=urlPre+service
    if debug: print URI

    myHeaders={}
    myHeaders['Content-Type']='application/json;charset=utf8'
    myHeaders['Accept']= 'application/json'

    try:
        response=requests.get(URI,auth=(user,passw),headers=myHeaders)
        response.raise_for_status()
    except requests.exceptions.HTTPError as e:
        print "{}\n".format(e)
        return response
    except requests.exceptions.RequestException as ex:
         print ex
         return None

    return response.json()

def AuthenticatedHTTP_PutRequest(urlPre,service,
                                user,passw,payLoad):

    URI=urlPre+service
    if debug: print URI

    myHeaders={}
    myHeaders['Content-Type']='application/json;charset=utf8'
    myHeaders['Accept']= 'application/json'

    try :
        response=requests.put(URI,data=json.dumps(payLoad),auth=(user,passw),headers=myHeaders)
        response.raise_for_status()
    except requests.exceptions.HTTPError as e:
        print "{}\n".format(e)
        return response
    except requests.exceptions.RequestException as ex:
         print ex
         return None

    return response

def AuthenticatedHTTP_DeleteRequest(urlPre,service,
                                user,passw):

    URI=urlPre+service
    if debug: print URI

    #myHeaders={}
    #myHeaders['Content-Type']='application/json;charset=utf8'
    #myHeaders['Accept']= 'application/json'

    try :
        response=requests.delete(URI,auth=(user,passw))
        response.raise_for_status()
    except requests.exceptions.HTTPError as e:
        print "{}\n".format(e)
        return response
    except requests.exceptions.RequestException as ex:
         print ex
         return None

    return response

def statsRender(httpResp,flowTag):
    ''' render flow statitics '''

    statsDic=httpResp
    msg="[Cookie {cookie}] active since {secs} seconds\n Bytes {byte} - Packets {packets}"
    # si potrebbe ottimizzare facendo una sola scansione 
    for flows in statsDic['flow-node-inventory:table']:
        for flow in flows['flow']:
            cookie=int(flow['cookie'])
            if cookie==int(flowTag):
                seconds=flow['opendaylight-flow-statistics:flow-statistics']['duration']['second']
                byteTot=flow['opendaylight-flow-statistics:flow-statistics']['byte-count']
                packTot=flow['opendaylight-flow-statistics:flow-statistics']['packet-count']
                print msg.format(cookie=cookie,byte=byteTot,packets=packTot,secs=seconds)
                break
            else:
                continue 
    print "\n-------------------\n"

if __name__ == '__main__':

    urlPref="http://127.0.0.1:8181/restconf"
    targetTemplConfig="/config/opendaylight-inventory:nodes/node/{nodeid}/flow-node-inventory:table/1/flow/{flowid}/"
    targetTemplOperat="/operational/opendaylight-inventory:nodes/node/{nodeid}/table/0"
    # si potrebbe interrogare il controller, invece di metterli statici
    #id_SCBD="openflow:585045261839360"
    #id_SCSF="openflow:303570285128704"

    # DA RISCRIVERE
    serviceExmpl='/config/network-topology:network-topology/topology/ovsdb:1/node/ovsdb:%2F%2FHOST1'
    jsonFileExmpl="json-rul"
    if len(sys.argv) < 2:
        print "Usage: \n{} {} {} [{}]".format(sys.argv[0],"<jsonFilePrefix>","push|pull|stats","outputNodeID")
        print "For instance:\n{} {} {}\n".format(sys.argv[0],serviceExmpl,jsonFileExmpl)
        print "will post all the json-rul* files in our current dir to the target URL"
        print "Target url is built from hardcoded [{}] and <targetAPI>".format(urlPref)
        sys.exit(-1)

            
    filePref=sys.argv[1]
    mode=sys.argv[2]
    if len(sys.argv) > 3:
        outputNodeID=sys.argv[3]
    else:
        outputNodeID=""

    filePref+="*json"
    username='admin'
    password='admin'
    for jsonfile in os.listdir("."): 
        if jsonfile in glob.glob(filePref):
            print "sourcing {}".format(jsonfile)
            with open(jsonfile,'r') as jfile:
                payload=json.load(jfile)

                if mode=="push":
                    payload['flow'][0]['hard-timeout']=unicode('0')
                    #payload['flow']['hard-timeout']=unicode('0')
                elif mode=="pull":
                   payload['flow'][0]['hard-timeout']=unicode('1')
                   #:payload['flow']['hard-timeout']=unicode('1')
                elif mode=="stats":
                    myCookie=payload['flow'][0]['cookie']  
                else:
                     print "{} : unknown operating mode".format(mode)
                     sys.exit(-1)   
            
                # DA verificare con altre regole
                flowID=payload['flow'][0]['id']
                #flowID=payload['flow']['id']

                if outputNodeID=="":
                    try:
                        outputNodeID=payload['flow'][0]['instructions']['instruction'][0]['apply-actions']['action'][0]['output-action']['output-node-connector']
                        #outputNodeID=payload['flow']['instructions']['instruction'][0]['apply-actions']['action'][0]['output-action']['output-node-connector']
                        portSeparatorIndex=outputNodeID.rindex(':')
                        outputNodeID=outputNodeID[0:portSeparatorIndex]
                    except KeyError:
                        print 'Fatal : flow output node is not specified from command line and  cannot be deduced from json file.' 
                        sys.exit(-1) 
                
                if mode=="stats":
                   targetAPI=targetTemplOperat.format(nodeid=outputNodeID)
                   res=AuthenticatedHTTP_GetRequest(urlPref,targetAPI,username,password)
                   statsRender(res,myCookie)   
                else:
                   targetAPI=targetTemplConfig.format(nodeid=outputNodeID,flowid=flowID)
                   #print targetAPI 
                   if   mode == "push":
                       res=AuthenticatedHTTP_PutRequest(urlPref,targetAPI,username,password,payload)
                   elif mode == "pull":
                       res=AuthenticatedHTTP_DeleteRequest(urlPref,targetAPI,username,password)
                   else:
                       print "{} mode unknown, don't know what to do".format(mode)
                       sys.exit(-2)

                # da ottimizzare !!
                if mode != "stats": 
                    if res.status_code == 201 or res.status_code == 200:
                        httpRes="HTTP is OK"
                    else:
                        httpRes="HTTP returned with an error code :(" 

                    print httpRes

                #outMsg="========\n{}{}\n{}\n{}\n=========".format(urlPref,targetAPI,payload,httpRes)
                outMsg="========\n{}{}\n{}\n=========".format(urlPref,targetAPI,payload)
                jfile.close()