Add status command

status command allows to show deployments and daemonset statuses

Change-Id: Iaf2f7d23b9ad1e54f512c63c224cb79cb78a76f3
This commit is contained in:
Sergey Reshetnyak 2016-08-17 16:34:38 +03:00
parent 8b45b177f6
commit c76ec7a9fe
4 changed files with 149 additions and 0 deletions

View File

@ -7,6 +7,7 @@ import sys
from cliff import app from cliff import app
from cliff import command from cliff import command
from cliff import commandmanager from cliff import commandmanager
from cliff import lister
import fuel_ccp import fuel_ccp
from fuel_ccp import build from fuel_ccp import build
@ -16,6 +17,7 @@ from fuel_ccp import config
from fuel_ccp import dependencies from fuel_ccp import dependencies
from fuel_ccp import deploy from fuel_ccp import deploy
from fuel_ccp import fetch from fuel_ccp import fetch
from fuel_ccp import status
from fuel_ccp import validate from fuel_ccp import validate
from fuel_ccp.validation import service as validation_service from fuel_ccp.validation import service as validation_service
@ -175,6 +177,34 @@ class ConfigDump(BaseCommand):
config.dump_yaml(self.app.stdout) config.dump_yaml(self.app.stdout)
class ShowStatus(lister.Lister):
"""Show status of deployment"""
def get_parser(self, *args, **kwargs):
parser = super(ShowStatus, self).get_parser(*args, **kwargs)
parser.set_defaults(**CONF.action._dict)
parser.add_argument("-l", "--long",
action="store_true",
help="show all components status")
parser.add_argument("-s", "--short",
action="store_true",
help="show cluster status (ready or not)")
parser.add_argument("components",
nargs="*",
help="CCP conponents to show status")
return parser
def take_action(self, parsed_args):
config.load_component_defaults()
if parsed_args.long:
return status.show_long_status()
elif parsed_args.short:
return status.show_short_status()
else:
return status.show_long_status(parsed_args.components)
def signal_handler(signo, frame): def signal_handler(signo, frame):
sys.exit(-signo) sys.exit(-signo)

View File

@ -137,6 +137,30 @@ def list_cluster_deployments():
selector="ccp=true") selector="ccp=true")
def list_cluster_pods(service=None):
selector = "ccp=true"
if service:
selector = ",".join((selector, "app=%s" % service))
client = get_client()
return pykube.Pod.objects(client).filter(
namespace=CONF.kubernetes.namespace,
selector=str(selector))
def list_cluster_jobs():
client = get_client()
return pykube.Job.objects(client).filter(
namespace=CONF.kubernetes.namespace,
selector="ccp=true")
def list_cluster_services():
client = get_client()
return pykube.Service.objects(client).filter(
namespace=CONF.kubernetes.namespace,
selector="ccp=true")
def get_object_names(items): def get_object_names(items):
names = [] names = []
for item in items: for item in items:

94
fuel_ccp/status.py Normal file
View File

@ -0,0 +1,94 @@
from __future__ import print_function
import logging
from fuel_ccp import config
from fuel_ccp import kubernetes
CONF = config.CONF
LOG = logging.getLogger(__name__)
class State(object):
def __init__(self, name, total, running, urls):
self.name = name
self.total = total or 0
self.running = running or 0
self.urls = urls or []
def __repr__(self):
if self.ready:
return "ok"
else:
return "nok" # not ready
def __lt__(self, other):
return self.name.__lt__(other.name)
def __bool__(self):
return self.ready
def __nonzero__(self):
return self.ready
@property
def ready(self):
return self.total == self.running
def _get_pods_status(service, svc_map):
pods = kubernetes.list_cluster_pods(service=service)
total = running = 0
for pod in pods:
total += 1
if pod.ready:
running += 1
return State(
name=service,
total=total,
running=running,
urls=svc_map.get(service, []))
def get_pod_states(components=None):
ext_ip = CONF.configs.get("k8s_external_ip", "")
ext_link_template = "http://{ext_ip}:{port}"
states = []
svc_map = {}
for svc in kubernetes.list_cluster_services():
svc_name = svc.obj["metadata"]["name"]
svc_map.setdefault(svc_name, [])
for port in svc.obj["spec"]["ports"]:
svc_map[svc_name].append(ext_link_template.format(
ext_ip=ext_ip,
port=port["nodePort"]))
for dp in kubernetes.list_cluster_deployments():
if not components or dp.name in components:
states.append(_get_pods_status(dp.name, svc_map))
for ds in kubernetes.list_cluster_daemonsets():
if not components or ds.name in components:
states.append(_get_pods_status(ds.name, svc_map))
return states
def show_long_status(components=None):
states = get_pod_states(components)
columns = ("service", "pod", "ready", "links")
formatted_states = []
for state in sorted(states):
formatted_states.append((
state.name,
"/".join((str(state.running), str(state.total))),
state,
"\n".join(state.urls)))
return columns, formatted_states
def show_short_status():
status = "ok" if all(get_pod_states()) else "nok"
return ("status",), ((status,),)

View File

@ -32,6 +32,7 @@ ccp.cli =
deploy = fuel_ccp.cli:Deploy deploy = fuel_ccp.cli:Deploy
fetch = fuel_ccp.cli:Fetch fetch = fuel_ccp.cli:Fetch
show-dep = fuel_ccp.cli:ShowDep show-dep = fuel_ccp.cli:ShowDep
status = fuel_ccp.cli:ShowStatus
validate = fuel_ccp.cli:Validate validate = fuel_ccp.cli:Validate
config_dump = fuel_ccp.cli:ConfigDump config_dump = fuel_ccp.cli:ConfigDump