[feature/APPC-7] ansible server commit
[appc.git] / appc-adapters / appc-ansible-adapter / appc-ansible-example-server / AnsibleModule.py
1 '''
2 /*-
3 * ============LICENSE_START=======================================================
4 * APPC
5 * ================================================================================
6 * Copyright (C) 2017 AT&T Intellectual Property.  All rights reserved.
7 * ================================================================================
8 * Licensed under the Apache License, Version 2.0 (the "License");
9 * you may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
11 *
12 *      http://www.apache.org/licenses/LICENSE-2.0
13 *
14 * Unless required by applicable law or agreed to in writing, software
15 * distributed under the License is distributed on an "AS IS" BASIS,
16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17 * See the License for the specific language governing permissions and
18 * limitations under the License.
19 * ============LICENSE_END=========================================================
20 * ECOMP is a trademark and service mark of AT&T Intellectual Property.
21 */
22 '''
23
24 import os, subprocess
25 import sys
26 from collections import namedtuple
27 import json
28
29 import uuid
30
31 def ansibleSysCall (inventory_path, playbook_path, nodelist, mandatory,
32                     envparameters, localparameters, lcm, timeout):
33
34     print "***> in AnsibleModule.ansibleSysCall"
35     print "   EnvParameters:  ", envparameters
36     print "   LocalParameters:", localparameters
37     print "   Inventory:      ", inventory_path
38     print "   Playbook:       ", playbook_path
39     print "   NodeList:       ", nodelist
40     print "   Mandatory:      ", mandatory
41     print "   Timeout:        ", timeout
42     log = []
43
44     str_parameters = ''
45                 
46     if not envparameters == {}:
47         for key in envparameters:
48             if str_parameters == '':
49                 str_parameters = '"'  + str(key) + '=\'' + str(envparameters[key])  + '\''
50             else:
51                 str_parameters += ' '  + str(key) + '=\'' + str(envparameters[key])  + '\''
52         str_parameters += '"'
53                         
54     if len(str_parameters) > 0:
55         cmd = 'timeout --signal=KILL ' + str(timeout) + \
56               ' ansible-playbook -v --extra-vars ' + str_parameters + ' -i ' + \
57               inventory_path + ' ' + playbook_path
58     else:
59         cmd = 'timeout --signal=KILL ' + str(timeout) + \
60               ' ansible-playbook -v -i ' + inventory_path + ' ' + playbook_path
61
62     print "   CMD:            ", cmd
63
64     print "\n =================ANSIBLE STDOUT BEGIN============================================\n"
65     p = subprocess.Popen(cmd, shell=True,
66                          stdout=subprocess.PIPE,
67                          stderr=subprocess.STDOUT) 
68     # p.wait()
69     (stdout_value, err) = p.communicate()
70     
71     stdout_value_cleanup = ''
72     for line in stdout_value:
73         stdout_value_cleanup += line.replace('  ', ' ')
74     stdout_value = stdout_value_cleanup.splitlines() 
75
76     ParseFlag = False
77     retval = {}
78     returncode = p.returncode
79
80     if returncode == 137:
81         
82         print "   ansible-playbook system call timed out"
83         # ansible-playbook system call timed out
84         for line in stdout_value: # p.stdout.readlines():
85             log.append (line)
86             
87             
88     elif 'ping' in lcm:
89
90         targetnode = envparameters['TargetNode'].split(' ')
91         str_json = None
92         for line in stdout_value: # p.stdout.readlines():
93             print line # line,
94             if "PLAY RECAP" in line:
95                 ParseFlag = False
96             if ParseFlag and len(line.strip())>0:
97                 str_json += line.strip()
98             if "TASK [debug]" in line:
99                 ParseFlag = True
100                 str_json = ''
101             log.append (line)
102
103         if str_json:
104             if '=>' in str_json:
105                 out_json =eval(str_json.split('=>')[1].replace('true','True').replace('false','False'))
106
107                 if 'ping.stdout_lines' in out_json:
108                     for node in targetnode:
109                         ip_address = node
110                         ok_flag = '0'
111                         changed_flag = '0'
112                         unreachable_flag = '0'
113                         failed_flag = '1'
114                         for rec in out_json['ping.stdout_lines']:
115                             if node in rec and "is alive" in rec:
116                                 ok_flag = '1'
117                                 changed_flag = '1'
118                                 unreachable_flag = '0'
119                                 failed_flag = '0'
120                         for rec in out_json['ping.stdout_lines']:
121                             if node in rec and "address not found" in rec:
122                                 ok_flag = '0'
123                                 changed_flag = '0'
124                                 unreachable_flag = '1'
125                                 failed_flag = '0'
126                         retval[ip_address]=[ok_flag, changed_flag, unreachable_flag,
127                                             failed_flag]
128     else:
129             
130         for line in stdout_value: # p.stdout.readlines():
131             print line # line,
132             if ParseFlag and len(line.strip())>0:
133                 ip_address = line.split(':')[0].strip()
134                 ok_flag = line.split(':')[1].strip().split('=')[1].split('changed')[0].strip()
135                 changed_flag = line.split(':')[1].strip().split('=')[2].split('unreachable')[0].strip()
136                 unreachable_flag = line.split(':')[1].strip().split('=')[3].split('failed')[0].strip()
137                 failed_flag = line.split(':')[1].strip().split('=')[4].strip()
138                 retval[ip_address]=[ok_flag, changed_flag, unreachable_flag, failed_flag]
139             if "PLAY RECAP" in line:
140                 ParseFlag = True
141             log.append (line)
142         
143     # retval['p'] = p.wait()
144
145     print " =================ANSIBLE STDOUT END==============================================\n"
146
147     return retval, log, returncode
148
149 if __name__ == '__main__':
150
151     from multiprocessing import Process, Value, Array, Manager
152     import time
153
154     nodelist = 'host'
155
156     playbook_file = 'ansible_sleep@0.00.yml'
157
158
159     d = Manager().dict()
160     
161     p = Process(nodelist=ansible_call, args=('ansible_module_config', playbook_file, nodelist,d, ))
162     p.start()
163
164     print "Process running"
165     print d
166     p.join()
167     print d