Add VPP interface options support
[apex.git] / lib / python / apex_python_utils.py
1 ##############################################################################
2 # Copyright (c) 2016 Feng Pan (fpan@redhat.com), Dan Radez (dradez@redhat.com)
3 #
4 # All rights reserved. This program and the accompanying materials
5 # are made available under the terms of the Apache License, Version 2.0
6 # which accompanies this distribution, and is available at
7 # http://www.apache.org/licenses/LICENSE-2.0
8 ##############################################################################
9
10 import apex
11 import argparse
12 import sys
13 import logging
14 import os
15 import yaml
16
17 from jinja2 import Environment
18 from jinja2 import FileSystemLoader
19
20 from apex import NetworkSettings
21 from apex import NetworkEnvironment
22 from apex import DeploySettings
23 from apex import Inventory
24 from apex import ip_utils
25
26
27 def parse_net_settings(args):
28     """
29     Parse OPNFV Apex network_settings.yaml config file
30     and dump bash syntax to set environment variables
31
32     Args:
33     - file: string
34       file to network_settings.yaml file
35     """
36     settings = NetworkSettings(args.net_settings_file)
37     net_env = NetworkEnvironment(settings, args.net_env_file,
38                                  args.compute_pre_config,
39                                  args.controller_pre_config)
40     target = args.target_dir.split('/')
41     target.append('network-environment.yaml')
42     dump_yaml(dict(net_env), '/'.join(target))
43     settings.dump_bash()
44
45
46 def dump_yaml(data, file):
47     """
48     Dumps data to a file as yaml
49     :param data: yaml to be written to file
50     :param file: filename to write to
51     :return:
52     """
53     with open(file, "w") as fh:
54         yaml.dump(data, fh, default_flow_style=False)
55
56
57 def parse_deploy_settings(args):
58     settings = DeploySettings(args.file)
59     settings.dump_bash()
60
61
62 def run_clean(args):
63     apex.clean_nodes(args.file)
64
65
66 def parse_inventory(args):
67     inventory = Inventory(args.file, ha=args.ha, virtual=args.virtual)
68     if args.export_bash is True:
69         inventory.dump_bash()
70     else:
71         inventory.dump_instackenv_json()
72
73
74 def find_ip(args):
75     """
76     Get and print the IP from a specific interface
77
78     Args:
79     - interface: string
80       network interface name
81     - address_family: int
82       4 or 6, respective to ipv4 or ipv6
83     """
84     interface = ip_utils.get_interface(args.interface,
85                                        args.address_family)
86     if interface:
87         print(interface.ip)
88
89
90 def build_nic_template(args):
91     """
92     Build and print a Triple-O nic template from jinja template
93
94     Args:
95     - template: string
96       path to jinja template to load
97     - enabled_networks: comma delimited list
98       list of networks defined in net_env.py
99     - ext_net_type: string
100       interface or br-ex, defines the external network configuration
101     - address_family: string
102       4 or 6, respective to ipv4 or ipv6
103     - ovs_dpdk_bridge: string
104       bridge name to use as ovs_dpdk
105     """
106     template_dir, template = args.template.rsplit('/', 1)
107
108     netsets = NetworkSettings(args.net_settings_file)
109     nets = netsets.get('networks')
110     ds = DeploySettings(args.deploy_settings_file).get('deploy_options')
111     env = Environment(loader=FileSystemLoader(template_dir), autoescape=True)
112     template = env.get_template(template)
113
114     if ds['dataplane'] == 'fdio':
115         nets['tenant']['nic_mapping'][args.role]['phys_type'] = 'vpp_interface'
116         if ds['sdn_l3']:
117             nets['external'][0]['nic_mapping'][args.role]['phys_type'] =\
118                 'vpp_interface'
119     if ds.get('performance', {}).get(args.role.title(), {}).get('vpp', {})\
120             .get('uio-driver'):
121         nets['tenant']['nic_mapping'][args.role]['uio-driver'] =\
122             ds['performance'][args.role.title()]['vpp']['uio-driver']
123         if ds['sdn_l3']:
124             nets['external'][0]['nic_mapping'][args.role]['uio-driver'] =\
125                 ds['performance'][args.role.title()]['vpp']['uio-driver']
126     if ds.get('performance', {}).get(args.role.title(), {}).get('vpp', {})\
127             .get('interface-options'):
128         nets['tenant']['nic_mapping'][args.role]['interface-options'] =\
129             ds['performance'][args.role.title()]['vpp']['interface-options']
130
131     print(template.render(nets=nets,
132                           role=args.role,
133                           external_net_af=netsets.get_ip_addr_family(),
134                           external_net_type=args.ext_net_type,
135                           ovs_dpdk_bridge=args.ovs_dpdk_bridge))
136
137
138 def get_parser():
139     parser = argparse.ArgumentParser()
140     parser.add_argument('--debug', action='store_true', default=False,
141                         help="Turn on debug messages")
142     parser.add_argument('-l', '--log-file', default='/var/log/apex/apex.log',
143                         dest='log_file', help="Log file to log to")
144     subparsers = parser.add_subparsers()
145     # parse-net-settings
146     net_settings = subparsers.add_parser('parse-net-settings',
147                                          help='Parse network settings file')
148     net_settings.add_argument('-s', '--net-settings-file',
149                               default='network-settings.yaml',
150                               dest='net_settings_file',
151                               help='path to network settings file')
152     net_settings.add_argument('-e', '--net-env-file',
153                               default="network-environment.yaml",
154                               dest='net_env_file',
155                               help='path to network environment file')
156     net_settings.add_argument('-td', '--target-dir',
157                               default="/tmp",
158                               dest='target_dir',
159                               help='directory to write the'
160                                    'network-environment.yaml file')
161     net_settings.add_argument('--compute-pre-config',
162                               default=False,
163                               action='store_true',
164                               dest='compute_pre_config',
165                               help='Boolean to enable Compute Pre Config')
166     net_settings.add_argument('--controller-pre-config',
167                               action='store_true',
168                               default=False,
169                               dest='controller_pre_config',
170                               help='Boolean to enable Controller Pre Config')
171
172     net_settings.set_defaults(func=parse_net_settings)
173     # find-ip
174     get_int_ip = subparsers.add_parser('find-ip',
175                                        help='Find interface ip')
176     get_int_ip.add_argument('-i', '--interface', required=True,
177                             help='Interface name')
178     get_int_ip.add_argument('-af', '--address-family', default=4, type=int,
179                             choices=[4, 6], dest='address_family',
180                             help='IP Address family')
181     get_int_ip.set_defaults(func=find_ip)
182     # nic-template
183     nic_template = subparsers.add_parser('nic-template',
184                                          help='Build NIC templates')
185     nic_template.add_argument('-r', '--role', required=True,
186                               choices=['controller', 'compute'],
187                               help='Role template generated for')
188     nic_template.add_argument('-t', '--template', required=True,
189                               dest='template',
190                               help='Template file to process')
191     nic_template.add_argument('-s', '--net-settings-file',
192                               default='network-settings.yaml',
193                               dest='net_settings_file',
194                               help='path to network settings file')
195     nic_template.add_argument('-e', '--ext-net-type', default='interface',
196                               dest='ext_net_type',
197                               choices=['interface', 'vpp_interface', 'br-ex'],
198                               help='External network type')
199     nic_template.add_argument('-d', '--ovs-dpdk-bridge',
200                               default=None, dest='ovs_dpdk_bridge',
201                               help='OVS DPDK Bridge Name')
202     nic_template.add_argument('--deploy-settings-file',
203                               help='path to deploy settings file')
204
205     nic_template.set_defaults(func=build_nic_template)
206     # parse-deploy-settings
207     deploy_settings = subparsers.add_parser('parse-deploy-settings',
208                                             help='Parse deploy settings file')
209     deploy_settings.add_argument('-f', '--file',
210                                  default='deploy_settings.yaml',
211                                  help='path to deploy settings file')
212     deploy_settings.set_defaults(func=parse_deploy_settings)
213     # parse-inventory
214     inventory = subparsers.add_parser('parse-inventory',
215                                       help='Parse inventory file')
216     inventory.add_argument('-f', '--file',
217                            default='deploy_settings.yaml',
218                            help='path to deploy settings file')
219     inventory.add_argument('--ha',
220                            default=False,
221                            action='store_true',
222                            help='Indicate if deployment is HA or not')
223     inventory.add_argument('--virtual',
224                            default=False,
225                            action='store_true',
226                            help='Indicate if deployment inventory is virtual')
227     inventory.add_argument('--export-bash',
228                            default=False,
229                            dest='export_bash',
230                            action='store_true',
231                            help='Export bash variables from inventory')
232     inventory.set_defaults(func=parse_inventory)
233
234     clean = subparsers.add_parser('clean',
235                                   help='Parse deploy settings file')
236     clean.add_argument('-f', '--file',
237                        help='path to inventory file')
238     clean.set_defaults(func=run_clean)
239
240     return parser
241
242
243 def main():
244     parser = get_parser()
245     args = parser.parse_args(sys.argv[1:])
246     if args.debug:
247         logging.basicConfig(level=logging.DEBUG)
248     else:
249         apex_log_filename = args.log_file
250         os.makedirs(os.path.dirname(apex_log_filename), exist_ok=True)
251         logging.basicConfig(filename=apex_log_filename,
252                             format='%(asctime)s %(levelname)s: %(message)s',
253                             datefmt='%m/%d/%Y %I:%M:%S %p',
254                             level=logging.DEBUG)
255     if hasattr(args, 'func'):
256         args.func(args)
257     else:
258         parser.print_help()
259         exit(1)
260
261 if __name__ == "__main__":
262     main()