blob: a917fe778fee7bab7ad92e582a15e0076bacf4ab [file] [log] [blame]
Annie Chen60002cf2017-06-15 11:25:54 -07001#!/usr/bin/env python
2#
3# Copyright 2017 - The Android Open Source Project
4#
5# Licensed under the Apache License, Version 2.0 (the "License");
6# you may not use this file except in compliance with the License.
7# You may obtain a copy of the License at
8#
9# http://www.apache.org/licenses/LICENSE-2.0
10#
11# Unless required by applicable law or agreed to in writing, software
12# distributed under the License is distributed on an "AS IS" BASIS,
13# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14# See the License for the specific language governing permissions and
15# limitations under the License.
16
Annie Chen5d7e4002017-07-14 11:02:10 -070017import logging
18
Annie Chen60002cf2017-06-15 11:25:54 -070019from health.constant_health_analyzer import HealthyIfGreaterThanConstantNumber
20from health.constant_health_analyzer import HealthyIfLessThanConstantNumber
21from health.constant_health_analyzer import HealthyIfEquals
Cameron Moberga95211e2017-08-07 15:59:44 -070022from health.constant_health_analyzer import HealthyIfStartsWith
Cameron Moberg84517192017-06-28 17:35:07 -070023from health.custom_health_analyzer import HealthyIfNotIpAddress
Annie Chen87af10c2017-06-30 17:57:39 -070024from health.constant_health_analyzer_wrapper import HealthyIfValsEqual
Annie Chen60002cf2017-06-15 11:25:54 -070025
26
27class HealthChecker(object):
28 """Takes a dictionary of metrics and returns whether each is healthy
29 Attributes:
30 _analyzers: a list of metric, analyzer tuples where metric is a string
31 representing a metric name ('DiskMetric') and analyzer is a
32 constant_health_analyzer object
Annie Chen60002cf2017-06-15 11:25:54 -070033 config:
34 a dict formatted as follows:
35 {
36 metric_name: {
37 field_to_compare: {
38 constant : a constant to compare to
39 compare : a string specifying a way to compare
40 }
41 }
42 }
43
44
45 """
46
47 COMPARER_CONSTRUCTOR = {
48 'GREATER_THAN': lambda k, c: HealthyIfGreaterThanConstantNumber(k, c),
49 'LESS_THAN': lambda k, c: HealthyIfLessThanConstantNumber(k, c),
Cameron Moberg84517192017-06-28 17:35:07 -070050 'EQUALS': lambda k, c: HealthyIfEquals(k, c),
Annie Chen87af10c2017-06-30 17:57:39 -070051 'IP_ADDR': lambda k, c: HealthyIfNotIpAddress(k),
Cameron Moberga95211e2017-08-07 15:59:44 -070052 'EQUALS_DICT': lambda k, c: HealthyIfValsEqual(k, c),
53 'STARTS_WITH': lambda k, c: HealthyIfStartsWith(k, c)
Annie Chen60002cf2017-06-15 11:25:54 -070054 }
55
56 def __init__(self, config):
57 self._config = config
58 self._analyzers = []
59 # Create comparators from config object
60 for metric_name, metric_configs in self._config.items():
61 # creates a constant_health_analyzer object for each field
62 for field_name in metric_configs:
63 compare_type = metric_configs[field_name]['compare']
64 constant = metric_configs[field_name]['constant']
65 comparer = self.COMPARER_CONSTRUCTOR[compare_type](field_name,
66 constant)
67 self._analyzers.append((metric_name, comparer))
68
69 def get_unhealthy(self, response_dict):
70 """Calls comparators to check if metrics are healthy
71
72 Attributes:
73 response_dict: a dict mapping metric names (as strings) to the
74 responses returned from gather_metric()
75
76 Returns:
77 a list of keys, where keys are strings representing
78 the name of a metric (ex: 'DiskMetric')
79 """
80 # loop through and check if healthy
81 unhealthy_metrics = []
82 for (metric, analyzer) in self._analyzers:
Annie Chen5d7e4002017-07-14 11:02:10 -070083 try:
84 # if not healthy, add to list so value can be reported
85 if not analyzer.is_healthy(response_dict[metric]):
86 unhealthy_metrics.append(metric)
87 # don't exit whole program if error in config file, just report
88 except KeyError as e:
89 logging.warning(
90 'Error in config file, "%s" not a health metric\n' % e)
91
Annie Chen60002cf2017-06-15 11:25:54 -070092 return unhealthy_metrics