218 lines
8.1 KiB
Python
218 lines
8.1 KiB
Python
# Copyright 2012 Hewlett-Packard Development Company, L.P.
|
|
#
|
|
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
|
# not use this file except in compliance with the License. You may obtain
|
|
# a copy of the License at
|
|
#
|
|
# http://www.apache.org/licenses/LICENSE-2.0
|
|
#
|
|
# Unless required by applicable law or agreed to in writing, software
|
|
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
|
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
|
# License for the specific language governing permissions and limitations
|
|
# under the License.
|
|
|
|
import prettytable
|
|
import novaclient
|
|
|
|
from novaclient import client
|
|
|
|
|
|
# NOTE(LinuxJedi): Override novaclient's error handler as we send messages in
|
|
# a slightly different format which causes novaclient's to throw an exception
|
|
|
|
def from_response(response, body):
|
|
"""
|
|
Return an instance of an ClientException or subclass
|
|
based on an httplib2 response.
|
|
|
|
Usage::
|
|
|
|
resp, body = http.request(...)
|
|
if resp.status != 200:
|
|
raise exception_from_response(resp, body)
|
|
"""
|
|
cls = novaclient.exceptions._code_map.get(
|
|
response.status, novaclient.exceptions.ClientException
|
|
)
|
|
request_id = response.get('x-compute-request-id')
|
|
if body:
|
|
message = "n/a"
|
|
details = "n/a"
|
|
if hasattr(body, 'keys'):
|
|
message = body.get('message', None)
|
|
details = body.get('details', None)
|
|
return cls(code=response.status, message=message, details=details,
|
|
request_id=request_id)
|
|
else:
|
|
return cls(code=response.status, request_id=request_id)
|
|
|
|
novaclient.exceptions.from_response = from_response
|
|
|
|
|
|
class LibraAPI(object):
|
|
def __init__(self, username, password, tenant, auth_url, region,
|
|
insecure, debug, bypass_url):
|
|
self.nova = client.HTTPClient(
|
|
username,
|
|
password,
|
|
tenant,
|
|
auth_url,
|
|
region_name=region,
|
|
service_type='compute',
|
|
http_log_debug=debug,
|
|
insecure=insecure,
|
|
bypass_url=bypass_url
|
|
)
|
|
|
|
def limits_lb(self, args):
|
|
resp, body = self._get('/limits')
|
|
column_names = ['Verb', 'Value', 'Remaining', 'Unit', 'Next Available']
|
|
columns = ['verb', 'value', 'remaining', 'unit', 'next-available']
|
|
self._render_list(column_names, columns,
|
|
body['limits']['rate']['values']['limit'])
|
|
column_names = ['Values']
|
|
columns = ['values']
|
|
self._render_dict(column_names, columns, body['limits']['absolute'])
|
|
|
|
def protocols_lb(self, args):
|
|
resp, body = self._get('/protocols')
|
|
column_names = ['Name', 'Port']
|
|
columns = ['name', 'port']
|
|
self._render_list(column_names, columns, body['protocols'])
|
|
|
|
def algorithms_lb(self, args):
|
|
resp, body = self._get('/algorithms')
|
|
column_names = ['Name']
|
|
columns = ['name']
|
|
self._render_list(column_names, columns, body['algorithms'])
|
|
|
|
def list_lb(self, args):
|
|
if args.deleted:
|
|
resp, body = self._get('/loadbalancers?status=DELETED')
|
|
else:
|
|
resp, body = self._get('/loadbalancers')
|
|
column_names = ['Name', 'ID', 'Protocol', 'Port', 'Algorithm',
|
|
'Status', 'Created', 'Updated']
|
|
columns = ['name', 'id', 'protocol', 'port', 'algorithm', 'status',
|
|
'created', 'updated']
|
|
self._render_list(column_names, columns, body['loadBalancers'])
|
|
|
|
def status_lb(self, args):
|
|
resp, body = self._get('/loadbalancers/{0}'.format(args.id))
|
|
column_names = ['ID', 'Name', 'Protocol', 'Port', 'Algorithm',
|
|
'Status', 'Created', 'Updated', 'IPs', 'Nodes',
|
|
'Persistence Type', 'Connection Throttle']
|
|
columns = ['id', 'name', 'protocol', 'port', 'algorithm', 'status',
|
|
'created', 'updated', 'virtualIps', 'nodes',
|
|
'sessionPersistence', 'connectionThrottle']
|
|
if 'sessionPersistence' not in body:
|
|
body['sessionPersistence'] = 'None'
|
|
if 'connectionThrottle' not in body:
|
|
body['connectionThrottle'] = 'None'
|
|
self._render_dict(column_names, columns, body)
|
|
|
|
def delete_lb(self, args):
|
|
self._delete('/loadbalancers/{0}'.format(args.id))
|
|
|
|
def create_lb(self, args):
|
|
data = {}
|
|
nodes = []
|
|
data['name'] = args.name
|
|
if args.port is not None:
|
|
data['port'] = args.port
|
|
if args.protocol is not None:
|
|
data['protocol'] = args.protocol
|
|
if args.algorithm is not None:
|
|
data['algorithm'] = args.algorithm
|
|
for node in args.node:
|
|
addr = node.split(':')
|
|
nodes.append({'address': addr[0], 'port': addr[1],
|
|
'condition': 'ENABLED'})
|
|
data['nodes'] = nodes
|
|
if args.vip is not None:
|
|
data['virtualIps'] = [{'id': args.vip}]
|
|
|
|
resp, body = self._post('/loadbalancers', body=data)
|
|
column_names = ['ID', 'Name', 'Protocol', 'Port', 'Algorithm',
|
|
'Status', 'Created', 'Updated', 'IPs', 'Nodes']
|
|
columns = ['id', 'name', 'protocol', 'port', 'algorithm', 'status',
|
|
'created', 'updated', 'virtualIps', 'nodes']
|
|
self._render_dict(column_names, columns, body)
|
|
|
|
def modify_lb(self, args):
|
|
data = {}
|
|
if args.name is not None:
|
|
data['name'] = args.name
|
|
if args.algorithm is not None:
|
|
data['algorithm'] = args.algorithm
|
|
self._put('/loadbalancers/{0}'.format(args.id), body=data)
|
|
|
|
def node_list_lb(self, args):
|
|
resp, body = self._get('/loadbalancers/{0}/nodes'.format(args.id))
|
|
column_names = ['ID', 'Address', 'Port', 'Condition', 'Status']
|
|
columns = ['id', 'address', 'port', 'condition', 'status']
|
|
self._render_list(column_names, columns, body['nodes'])
|
|
|
|
def node_delete_lb(self, args):
|
|
self._delete('/loadbalancers/{0}/nodes/{1}'
|
|
.format(args.id, args.nodeid))
|
|
|
|
def node_add_lb(self, args):
|
|
data = {}
|
|
nodes = []
|
|
|
|
for node in args.node:
|
|
addr = node.split(':')
|
|
nodes.append({'address': addr[0], 'port': addr[1],
|
|
'condition': 'ENABLED'})
|
|
data['nodes'] = nodes
|
|
resp, body = self._post('/loadbalancers/{0}/nodes'
|
|
.format(args.id), body=data)
|
|
column_names = ['ID', 'Address', 'Port', 'Condition', 'Status']
|
|
columns = ['id', 'address', 'port', 'condition', 'status']
|
|
self._render_list(column_names, columns, body['nodes'])
|
|
|
|
def node_modify_lb(self, args):
|
|
data = {'condition': args.condition}
|
|
self._put('/loadbalancers/{0}/nodes/{1}'
|
|
.format(args.id, args.nodeid), body=data)
|
|
|
|
def node_status_lb(self, args):
|
|
resp, body = self._get('/loadbalancers/{0}/nodes/{1}'
|
|
.format(args.id, args.nodeid))
|
|
column_names = ['ID', 'Address', 'Port', 'Condition', 'Status']
|
|
columns = ['id', 'address', 'port', 'condition', 'status']
|
|
self._render_dict(column_names, columns, body)
|
|
|
|
def _render_list(self, column_names, columns, data):
|
|
table = prettytable.PrettyTable(column_names)
|
|
for item in data:
|
|
row = []
|
|
for column in columns:
|
|
rdata = item[column]
|
|
row.append(rdata)
|
|
table.add_row(row)
|
|
print table
|
|
|
|
def _render_dict(self, column_names, columns, data):
|
|
table = prettytable.PrettyTable(column_names)
|
|
row = []
|
|
for column in columns:
|
|
rdata = data[column]
|
|
row.append(rdata)
|
|
table.add_row(row)
|
|
print table
|
|
|
|
def _get(self, url, **kwargs):
|
|
return self.nova.get(url, **kwargs)
|
|
|
|
def _post(self, url, **kwargs):
|
|
return self.nova.post(url, **kwargs)
|
|
|
|
def _put(self, url, **kwargs):
|
|
return self.nova.put(url, **kwargs)
|
|
|
|
def _delete(self, url, **kwargs):
|
|
return self.nova.delete(url, **kwargs)
|