Skip to content

Commit

Permalink
Merge pull request #1642 from DataDog/remh/network_check_tags
Browse files Browse the repository at this point in the history
[HTTP/TCP Check] Add support for custom tags
  • Loading branch information
Remi Hakim committed May 28, 2015
2 parents 4032002 + 5d99182 commit 8f69fd8
Show file tree
Hide file tree
Showing 5 changed files with 144 additions and 159 deletions.
13 changes: 7 additions & 6 deletions checks.d/http_check.py
Original file line number Diff line number Diff line change
Expand Up @@ -35,8 +35,8 @@ def get_ca_certs_path():

class HTTPCheck(NetworkCheck):
SOURCE_TYPE_NAME = 'system'
SC_STATUS = 'http_check'
SC_SSL_CERT = 'http_check.ssl_cert'
SC_STATUS = 'http.can_connect'
SC_SSL_CERT = 'http.ssl_cert'

def __init__(self, name, init_config, agentConfig, instances):
self.ca_certs = init_config.get('ca_certs', get_ca_certs_path())
Expand Down Expand Up @@ -250,9 +250,10 @@ def _create_status_event(self, sc_name, status, msg, instance):

def report_as_service_check(self, sc_name, status, instance, msg=None):
instance_name = instance['name']
service_check_name = self.normalize(instance_name, sc_name)
url = instance.get('url', None)
sc_tags = ['url:%s' % url]
sc_tags = ['url:{0}'.format(url), "instance:{0}".format(instance_name)]
custom_tags = instance.get('tags', [])
tags = sc_tags + custom_tags

if sc_name == self.SC_STATUS:
# format the HTTP response body into the event
Expand All @@ -266,9 +267,9 @@ def report_as_service_check(self, sc_name, status, instance, msg=None):
msg = "%d %s\n\n%s" % (code, reason, content)
msg = msg.rstrip()

self.service_check(service_check_name,
self.service_check(sc_name,
NetworkCheck.STATUS_TO_SERVICE_CHECK[status],
tags=sc_tags,
tags=tags,
message=msg
)

Expand Down
13 changes: 8 additions & 5 deletions checks.d/tcp_check.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ class BadConfException(Exception): pass
class TCPCheck(NetworkCheck):

SOURCE_TYPE_NAME = 'system'
SERVICE_CHECK_PREFIX = 'tcp_check'
SERVICE_CHECK_NAME = 'tcp.can_connect'

def _load_conf(self, instance):
# Fetches the conf
Expand Down Expand Up @@ -154,16 +154,19 @@ def _create_status_event(self, sc_name, status, msg, instance):

def report_as_service_check(self, sc_name, status, instance, msg=None):
instance_name = instance['name']
service_check_name = self.normalize(instance_name, self.SERVICE_CHECK_PREFIX)
host = instance.get('host', None)
port = instance.get('port', None)
custom_tags = instance.get('tags', [])

if status == Status.UP:
msg = None

self.service_check(service_check_name,
tags = custom_tags + ['target_host:{0}'.format(host),
'port:{0}'.format(port),
'instance:{0}'.format(instance_name)]

self.service_check(self.SERVICE_CHECK_NAME,
NetworkCheck.STATUS_TO_SERVICE_CHECK[status],
tags= ['target_host:%s' % host,
'port:%s' % port],
tags=tags,
message=msg
)
21 changes: 21 additions & 0 deletions tests/checks/common.py
Original file line number Diff line number Diff line change
Expand Up @@ -444,3 +444,24 @@ def assertIn(self, first, second):

def assertNotIn(self, first, second):
self.assertTrue(first not in second, "{0} in {1}".format(first, second))

def assertWarning(self, warning, count=None, at_least=1, exact_match=True):
log.debug("Looking for warning {0}".format(warning))
if count is not None:
log.debug(" * should have exactly {0} statuses".format(count))
elif at_least is not None:
log.debug(" * should have at least {0} statuses".format(count))

if exact_match:
candidates = [w for w in self.warnings if w == warning]
else:
candidates = [w for w in self.warnings if warning in w]

try:
self._candidates_size_assert(candidates, count=count, at_least=at_least)
except AssertionError:
log.error("Candidates size assertion for {0}, count: {1}, "
"at_least: {2}) failed".format(warning, count, at_least))
raise

log.debug("{0} FOUND !".format(warning))
60 changes: 38 additions & 22 deletions tests/checks/integration/test_http_check.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@
'http_response_status_code': '4..',
'check_certificate_expiration': False,
'timeout': 1,
'tags': ["foo:bar"]
}, {
'name': 'cnt_mismatch',
'url': 'https://github.com',
Expand Down Expand Up @@ -100,39 +101,53 @@ def test_check(self):
self.service_checks = self.wait_for_async_service_checks(5)

# HTTP connection error
self.assertServiceCheck("http_check.conn_error", status=AgentCheck.CRITICAL,
tags=['url:https://thereisnosuchlink.com'])
tags = ['url:https://thereisnosuchlink.com', 'instance:conn_error']

self.assertServiceCheck("http.can_connect", status=AgentCheck.CRITICAL,
tags=tags
)

# Wrong HTTP response status code
self.assertServiceCheck("http_check.http_error_status_code", status=AgentCheck.CRITICAL,
tags=['url:http://httpbin.org/404'])
self.assertServiceCheck("http_check.http_error_status_code", status=AgentCheck.OK,
tags=['url:http://httpbin.org/404'], count=0)
tags = ['url:http://httpbin.org/404', 'instance:http_error_status_code']
self.assertServiceCheck("http.can_connect",
status=AgentCheck.CRITICAL,
tags=tags)

self.assertServiceCheck("http.can_connect", status=AgentCheck.OK,
tags=tags, count=0)

# HTTP response status code match
self.assertServiceCheck("http_check.status_code_match", status=AgentCheck.OK,
tags=['url:http://httpbin.org/404'])
tags = ['url:http://httpbin.org/404', 'instance:status_code_match', 'foo:bar']
self.assertServiceCheck("http.can_connect", status=AgentCheck.OK,
tags=tags)

# Content match & mismatching
self.assertServiceCheck("http_check.cnt_mismatch", status=AgentCheck.CRITICAL,
tags=['url:https://github.com'])
self.assertServiceCheck("http_check.cnt_mismatch", status=AgentCheck.OK,
tags=['url:https://github.com'], count=0)
self.assertServiceCheck("http_check.cnt_match", status=AgentCheck.OK,
tags=['url:https://github.com'])
tags = ['url:https://github.com', 'instance:cnt_mismatch']
self.assertServiceCheck("http.can_connect", status=AgentCheck.CRITICAL,
tags=tags)
self.assertServiceCheck("http.can_connect", status=AgentCheck.OK,
tags=tags, count=0)
tags = ['url:https://github.com', 'instance:cnt_match']
self.assertServiceCheck("http.can_connect", status=AgentCheck.OK,
tags=tags)

self.coverage_report()

def test_check_ssl(self):
self.run_check(CONFIG_SSL_ONLY)
# Overrides self.service_checks attribute when values are available
self.service_checks = self.wait_for_async_service_checks(6)
self.assertServiceCheck("http_check.ssl_cert.good_cert", status=AgentCheck.OK,
tags=['url:https://github.com'])
self.assertServiceCheck("http_check.ssl_cert.cert_exp_soon", status=AgentCheck.WARNING,
tags=['url:https://github.com'])
self.assertServiceCheck("http_check.ssl_cert.conn_error", status=AgentCheck.CRITICAL,
tags=['url:https://thereisnosuchlink.com'])
tags = ['url:https://github.com', 'instance:good_cert']
self.assertServiceCheck("http.ssl_cert", status=AgentCheck.OK,
tags=tags)

tags = ['url:https://github.com', 'instance:cert_exp_soon']
self.assertServiceCheck("http.ssl_cert", status=AgentCheck.WARNING,
tags=tags)

tags = ['url:https://thereisnosuchlink.com', 'instance:conn_error']
self.assertServiceCheck("http.ssl_cert", status=AgentCheck.CRITICAL,
tags=tags)

self.coverage_report()

Expand All @@ -142,6 +157,7 @@ def test_mock_case(self, getpeercert_func):
# Overrides self.service_checks attribute when values are av
# Needed for the HTTP headers
self.service_checks = self.wait_for_async_service_checks(2)
self.assertServiceCheck("http_check.ssl_cert.expired_cert", status=AgentCheck.CRITICAL,
tags=['url:https://github.com'])
tags = ['url:https://github.com', 'instance:expired_cert']
self.assertServiceCheck("http.ssl_cert", status=AgentCheck.CRITICAL,
tags=tags)
self.coverage_report()
Loading

0 comments on commit 8f69fd8

Please sign in to comment.