87c309fdb3b3699edc0a57f943957c110b83e7d6
[osm/devops.git] / descriptor-packages / nsd / ping_pong_ns / src / scripts / start_traffic.py
1 #!/usr/bin/env python3
2
3 ############################################################################
4 # Copyright 2016 RIFT.IO Inc #
5 # #
6 # Licensed under the Apache License, Version 2.0 (the "License"); #
7 # you may not use this file except in compliance with the License. #
8 # You may obtain a copy of the License at #
9 # #
10 # http://www.apache.org/licenses/LICENSE-2.0 #
11 # #
12 # Unless required by applicable law or agreed to in writing, software #
13 # distributed under the License is distributed on an "AS IS" BASIS, #
14 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. #
15 # See the License for the specific language governing permissions and #
16 # limitations under the License. #
17 ############################################################################
18
19
20 import argparse
21 import logging
22 import paramiko
23 import os
24 import subprocess
25 import sys
26 import time
27
28 import yaml
29
30
31 def ssh(cmd, host, user, password):
32 """ Run an arbitrary command over SSH. """
33
34 client = paramiko.SSHClient()
35 client.set_missing_host_key_policy(paramiko.AutoAddPolicy())
36
37 client.connect(host, port=22, username=user, password=password)
38
39 stdin, stdout, stderr = client.exec_command(cmd, get_pty=True)
40 retcode = stdout.channel.recv_exit_status()
41 client.close()
42
43 return (
44 retcode,
45 stdout.read().decode('utf-8').strip(),
46 stderr.read().decode('utf-8').strip()
47 )
48
49
50 def start_traffic(yaml_cfg, logger):
51 '''Use curl and set admin status to enable on pong and ping vnfs'''
52
53 curl_fmt = 'curl -D /dev/stdout -H "Accept: application/vnd.yang.data' \
54 '+xml" -H "Content-Type: application/vnd.yang.data+json" ' \
55 '-X POST -d "{{ {data} }}" http://127.0.0.1:' \
56 '{mgmt_port}/api/v1/{vnf_type}/{url}'
57
58 # Get userid and password for the VNF
59 user = yaml_cfg['parameter']['ssh-username']
60 passwd = yaml_cfg['parameter']['ssh-password']
61
62 # Get port from user parameter
63 service_port = yaml_cfg['parameter']['port']
64
65 service_ip = None
66
67 def exec_cmd(vnf_type, mgmt_ip, port, url, data):
68 curl_cmd = curl_fmt.format(
69 mgmt_port=port,
70 vnf_type=vnf_type,
71 data=data,
72 url=url
73 )
74
75 logger.debug("Executing cmd: %s", curl_cmd)
76 rc, out, err = ssh(curl_cmd, mgmt_ip, user, passwd)
77
78 if rc != 0:
79 logger.error("cmd={}, rc={}, stderr={}, stdout={}".
80 format(curl_cmd, rc, err, out))
81 else:
82 logger.debug("cmd={}, rc={}, stderr={}, stdout={}".
83 format(curl_cmd, rc, err, out))
84
85 return rc
86
87 def setup_service(mgmt_ip, port, vnf_type):
88 data = '\\"ip\\":\\"{}\\", \\"port\\":5555'.format(service_ip)
89 return exec_cmd(vnf_type, mgmt_ip, port, 'server', data)
90
91 def enable_service(mgmt_ip, port, vnf_type):
92 data='\\"enable\\":true'
93 url='adminstatus/state'
94 return exec_cmd(vnf_type, mgmt_ip, port, url, data)
95
96 # Enable pong service first
97 for index, vnfr in yaml_cfg['vnfr'].items():
98 logger.debug("VNFR {}: {}".format(index, vnfr))
99
100 def get_cp_ip(cp_name):
101 for cp in vnfr['connection_point']:
102 if cp['name'].endswith(cp_name):
103 return cp['ip_address']
104
105 # Check if it is pong vnf
106 if 'pong_vnf' in vnfr['name']:
107 vnf_type = 'pong'
108 mgmt_ip = vnfr['mgmt_ip_address']
109 port = vnfr['mgmt_port']
110 service_ip = get_cp_ip('cp1')
111
112 max_tries = 60
113 tries = 0
114 while tries < max_tries:
115 rc = setup_service(mgmt_ip, port, vnf_type)
116 tries += 1
117 if rc != 0:
118 logger.error("Setup service for pong failed ({}): {}".
119 format(tries, rc))
120 if rc != 7:
121 return rc
122 else:
123 time.sleep(1) # Sleep for 1 seconds
124 else:
125 break
126
127 rc = enable_service(mgmt_ip, port, vnf_type)
128 if rc != 0:
129 logger.error("Enable service for pong failed: {}".
130 format(rc))
131 return rc
132
133 # Add a delay to provide pong port to come up
134 time.sleep(1)
135
136 # Enable ping service next
137 for index, vnfr in yaml_cfg['vnfr'].items():
138 logger.debug("VNFR {}: {}".format(index, vnfr))
139
140 # Check if it is pong vnf
141 if 'ping_vnf' in vnfr['name']:
142 vnf_type = 'ping'
143 mgmt_ip = vnfr['mgmt_ip_address']
144 port = vnfr['mgmt_port']
145 if service_ip is None:
146 logger.error("Did not find pong ip!!")
147 return 1
148
149 max_tries = 30
150 tries = 0
151 while tries < max_tries:
152 rc = setup_service(mgmt_ip, port, vnf_type)
153 tries += 1
154 if rc != 0:
155 logger.error("Setup service for ping failed ({}): {}".
156 format(tries, rc))
157 if rc != 7:
158 return rc
159 else:
160 time.sleep(1) # Sleep for 1 seconds
161 else:
162 break
163
164 rc = enable_service(mgmt_ip, port, vnf_type)
165 if rc != 0:
166 logger.error("Enable service for ping failed: {}".
167 format(rc))
168
169 return rc
170
171
172 def main(argv=sys.argv[1:]):
173 try:
174 parser = argparse.ArgumentParser()
175 parser.add_argument("yaml_cfg_file", type=argparse.FileType('r'))
176 parser.add_argument("-q", "--quiet", dest="verbose", action="store_false")
177 args = parser.parse_args()
178
179 run_dir = os.path.join(os.environ['RIFT_INSTALL'], "var/run/rift")
180 if not os.path.exists(run_dir):
181 os.makedirs(run_dir)
182 log_file = "{}/ping_pong_start_traffic-{}.log".format(run_dir, time.strftime("%Y%m%d%H%M%S"))
183
184 # logging.basicConfig(filename=log_file, level=logging.DEBUG)
185 logger = logging.getLogger('ping-pong-start-traffic')
186 logger.setLevel(logging.DEBUG)
187
188 fh = logging.FileHandler(log_file)
189 fh.setLevel(logging.DEBUG)
190
191 ch = logging.StreamHandler()
192 if args.verbose:
193 ch.setLevel(logging.DEBUG)
194 else:
195 ch.setLevel(logging.INFO)
196
197 # create formatter and add it to the handlers
198 formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s')
199 fh.setFormatter(formatter)
200 ch.setFormatter(formatter)
201 logger.addHandler(fh)
202 logger.addHandler(ch)
203
204 except Exception as e:
205 logger.exception("Exception in {}: {}".format(__file__, e))
206 sys.exit(1)
207
208 try:
209 logger.debug("Input file: {}".format(args.yaml_cfg_file.name))
210 yaml_str = args.yaml_cfg_file.read()
211 yaml_cfg = yaml.load(yaml_str)
212 logger.debug("Input YAML: {}".format(yaml_cfg))
213
214 rc = start_traffic(yaml_cfg, logger)
215 logger.info("Return code: {}".format(rc))
216 sys.exit(rc)
217
218 except Exception as e:
219 logger.exception("Exception in {}: {}".format(__file__, e))
220 sys.exit(1)
221
222 if __name__ == "__main__":
223 main()