def test_prometheus_exporter_basic_auth(): # The dpgen service just checks that basic auth is present, not correct with run_service("dpgen", environment={ "NUM_METRICS": 3, "REQUIRE_BASIC_AUTH": "yes" }) as dpgen_cont: with Agent.run( dedent(f""" monitors: - type: prometheus-exporter host: {container_ip(dpgen_cont)} port: 3000 intervalSeconds: 2 extraDimensions: source: prometheus """)) as agent: assert ensure_always( lambda: not has_datapoint(agent.fake_services, dimensions={"source": "prometheus"}), timeout_seconds=5 ), "got prometheus datapoint without basic auth (test setup is wrong)" agent.config["monitors"][0]["username"] = "******" agent.config["monitors"][0]["password"] = "******" agent.write_config() assert wait_for( p(has_datapoint, agent.fake_services, dimensions={"source": "prometheus" })), "didn't get prometheus datapoint"
def test_postgresql_database_filter(): with run_service("postgres", buildargs={"POSTGRES_VERSION": "11-alpine"}, environment=ENV, print_logs=False) as postgres_cont: host = container_ip(postgres_cont) assert wait_for(p(tcp_socket_open, host, 5432), 60), "service didn't start" with Agent.run( dedent(f""" monitors: - type: postgresql host: {host} port: 5432 connectionString: "user=test_user password=test_pwd dbname=postgres sslmode=disable" databases: ['*', '!postgres'] """)) as agent: for metric in METADATA.default_metrics: assert wait_for( p(has_datapoint, agent.fake_services, metric_name=metric, dimensions={"database": "dvdrental"}) ), f"Didn't get default postgresql metric {metric} for database dvdrental" assert ensure_always(lambda: not has_datapoint( agent.fake_services, dimensions={"database": "postgres"} )), f"Should not get metric for postgres default database"
def test_kubernetes_cluster_namespace_scope(agent_image, minikube, k8s_namespace): monitors = [{ "type": "kubernetes-cluster", "kubernetesAPI": { "authType": "serviceAccount" }, "namespace": "good" }] with run_k8s_with_agent( agent_image, minikube, monitors, namespace=k8s_namespace, yamls=[local_file("good-pod.yaml"), local_file("bad-pod.yaml")], ) as [backend, _]: assert wait_for( p(has_datapoint, backend, dimensions={"kubernetes_namespace": "good"})), "timed out waiting for good pod metrics" assert ensure_always(lambda: not has_datapoint( backend, dimensions={"kubernetes_namespace": "bad"}) ), "got pod metrics from unspecified namespace"
def test_signalfx_metadata(): with Agent.run(""" procPath: /proc etcPath: /etc monitors: - type: collectd/signalfx-metadata persistencePath: /var/run/signalfx-agent - type: collectd/cpu - type: collectd/disk - type: collectd/memory """) as agent: assert wait_for( p(has_datapoint, agent.fake_services, "cpu.utilization", {"plugin": "signalfx-metadata"})) assert wait_for( p(has_datapoint, agent.fake_services, "disk_ops.total", {"plugin": "signalfx-metadata"})) assert wait_for( p(has_datapoint, agent.fake_services, "memory.utilization", {"plugin": "signalfx-metadata"})) assert ensure_always( lambda: not has_datapoint(agent.fake_services, "cpu.utilization_per_core", {"plugin": "signalfx-metadata"}), timeout_seconds=5, ) assert not has_log_message(agent.output.lower(), "error"), "error found in agent output!"
def has_all_pod_datapoints(): for name in pod_names: if not has_datapoint( agent.fake_services, dimensions={"kubernetes_pod_name": name}): return False return True
def test_signalfx_metadata(): with run_agent(""" procPath: /proc etcPath: /etc monitors: - type: collectd/signalfx-metadata persistencePath: /var/run/signalfx-agent - type: collectd/cpu - type: collectd/disk - type: collectd/memory """) as [backend, get_output, _]: assert wait_for( p(has_datapoint, backend, "cpu.utilization", {"plugin": "signalfx-metadata"})) assert wait_for( p(has_datapoint, backend, "disk_ops.total", {"plugin": "signalfx-metadata"})) assert wait_for( p(has_datapoint, backend, "memory.utilization", {"plugin": "signalfx-metadata"})) assert ensure_always( lambda: not has_datapoint(backend, "cpu.utilization_per_core", {"plugin": "signalfx-metadata"})) assert not has_log_message(get_output().lower(), "error"), "error found in agent output!"
def test_endpoint_config_mapping(): with run_service("postgres", environment=[ "POSTGRES_USER=test_user", "POSTGRES_PASSWORD=test_pwd", "POSTGRES_DB=postgres" ]) as postgres_container: with Agent.run(f""" observers: - type: docker monitors: - type: postgresql host: {container_ip(postgres_container)} connectionString: "user=test_user password=test_pwd dbname=postgres sslmode=disable" port: 5432 dimensionTransformations: database: db """) as agent: assert wait_for( p(has_datapoint, agent.fake_services, dimensions={ "db": "dvdrental" })), "Didn't get properly transformed dimension name" assert not has_datapoint(agent.fake_services, dimensions={"database": "dvdrental"})
def test_overlapping_filter_with_monitor_type(): """ Test overlapping filters with different negation. Blacklist is favored """ with Agent.run( """ monitors: - type: collectd/memory - type: collectd/uptime metricsToExclude: - metricName: uptime negated: true monitorType: collectd/uptime - metricName: uptime monitorType: collectd/uptime """ ) as agent: assert wait_for(lambda: has_datapoint(agent.fake_services, "memory.used")) assert wait_for(lambda: has_datapoint(agent.fake_services, "memory.free")) assert ensure_always(lambda: not has_datapoint(agent.fake_services, "uptime"), 5)
def test_cpu_all(): agent = run_agent_verify_all_metrics( """ monitors: - type: cpu extraMetrics: ["*"] """, METADATA, ) assert has_datapoint(agent.fake_services, metric_name="cpu.utilization_per_core", dimensions={"cpu": "0"})
def test_docker_container_stats(): with run_service("nginx", cpu_period=100_000, cpu_quota=10000, cpu_shares=50, mem_limit=20 * 1024 * 1024) as nginx_container: with Agent.run(""" monitors: - type: cgroups extraMetrics: ['*'] """) as agent: verify(agent, METADATA.all_metrics) expected_cgroup = "/docker/" + nginx_container.id assert has_datapoint(agent.fake_services, metric_name="cgroup.cpu_shares", value=50, dimensions={"cgroup": expected_cgroup}) assert has_datapoint( agent.fake_services, metric_name="cgroup.cpu_cfs_period_us", value=100_000, dimensions={"cgroup": expected_cgroup}, ) assert has_datapoint( agent.fake_services, metric_name="cgroup.cpu_cfs_quota_us", value=10000, dimensions={"cgroup": expected_cgroup}, ) assert has_datapoint( agent.fake_services, metric_name="cgroup.memory_limit_in_bytes", value=20 * 1024 * 1024, dimensions={"cgroup": expected_cgroup}, )
def test_process_monitor_executable_filter(): proc = psutil.Process(os.getpid()) self_proc_exec = proc.exe() with Agent.run(f""" monitors: - type: process executables: - {self_proc_exec} """) as agent: verify(agent, METADATA.all_metrics) assert has_datapoint(agent.fake_services, dimensions={"executable": self_proc_exec})
def test_process_monitor_process_name_filter(): proc = psutil.Process(os.getpid()) self_proc_name = proc.name() with Agent.run(f""" monitors: - type: process processes: - {self_proc_name} """) as agent: verify(agent, METADATA.all_metrics) assert has_datapoint(agent.fake_services, dimensions={"command": self_proc_name})
def test_kubernetes_cluster_namespace_scope(k8s_cluster): yamls = [SCRIPT_DIR / "good-pod.yaml", SCRIPT_DIR / "bad-pod.yaml"] with k8s_cluster.create_resources(yamls): config = """ monitors: - type: kubernetes-cluster kubernetesAPI: authType: serviceAccount namespace: good """ with k8s_cluster.run_agent(agent_yaml=config) as agent: assert wait_for( p(has_datapoint, agent.fake_services, dimensions={"kubernetes_namespace": "good"}) ), "timed out waiting for good pod metrics" assert ensure_always( lambda: not has_datapoint(agent.fake_services, dimensions={"kubernetes_namespace": "bad"}) ), "got pod metrics from unspecified namespace"
def test_does_not_set_hostname_on_monitor_if_not_host_specific(): with Agent.run( """ hostname: acmeinc.com monitors: - type: cpu disableHostDimensions: true - type: memory """ ) as agent: assert wait_for( p(has_datapoint, agent.fake_services, dimensions={"host": "acmeinc.com"}, metric_name="memory.utilization") ), "Didn't get overridden hostname in datapoint" assert wait_for(p(has_datapoint, agent.fake_services, metric_name="cpu.utilization")), "Didn't get cpu metric" assert ensure_always( lambda: not has_datapoint( agent.fake_services, metric_name="cpu.utilization", dimensions={"host": "acmeinc.com"} ) ), "Got overridden hostname in cpu datapoint"
def test_kubernetes_cluster_namespace_scope(agent_image, minikube, k8s_namespace): yamls = [local_file("good-pod.yaml"), local_file("bad-pod.yaml")] with minikube.create_resources(yamls, namespace=k8s_namespace): config = """ monitors: - type: kubernetes-cluster kubernetesAPI: authType: serviceAccount namespace: good """ with minikube.run_agent(agent_image, config=config, namespace=k8s_namespace) as [_, backend]: assert wait_for( p(has_datapoint, backend, dimensions={"kubernetes_namespace": "good" })), "timed out waiting for good pod metrics" assert ensure_always(lambda: not has_datapoint( backend, dimensions={"kubernetes_namespace": "bad"} )), "got pod metrics from unspecified namespace"
def test_elasticsearch_included(): with run_elasticsearch( environment={"cluster.name": "testCluster"}) as es_container: host = container_ip(es_container) config = f""" monitors: - type: collectd/elasticsearch host: {host} port: 9200 username: elastic password: testing123 """ with Agent.run(config) as agent: verify(agent, METADATA.default_metrics - EXCLUDED) assert has_datapoint( agent.fake_services, dimensions={ "plugin_instance": "testCluster", "plugin": "elasticsearch", "index": "twitter" }, ) assert not has_log_message(agent.output.lower(), "error"), "error found in agent output!"
def no_node_uid_dim(): return not has_datapoint(agent.fake_services, dimensions={"kubernetes_node_uid": node.metadata.uid})
def has_all_pod_datapoints(): for name in pod_names: if not has_datapoint( backend, dimensions={"kubernetes_pod_name": name}): return False return True
def test(): assert has_datapoint(agent.fake_services, metric_name=target_metric)
def test_pcf_nozzle(): firehose_envelopes = [ { "batch": [ { "timestamp": "1580228407476075606", "source_id": "uaa", "instance_id": "", "deprecated_tags": {}, "tags": { "deployment": "cf-389cbac3d7a2c6c990c8", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "control", "origin": "uaa", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, "gauge": {"metrics": {"vitals.jvm.cpu.load": {"unit": "gauge", "value": 0}}}, } ] }, { "batch": [ { "timestamp": "1580228407476126130", "source_id": "uaa", "instance_id": "", "deprecated_tags": {}, "tags": { "deployment": "cf-389cbac3d7a2c6c990c8", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "control", "origin": "uaa", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, "gauge": {"metrics": {"vitals.jvm.thread.count": {"unit": "gauge", "value": 47}}}, } ] }, { "batch": [ { "timestamp": "1580228407476264719", "source_id": "uaa", "instance_id": "", "deprecated_tags": {}, "tags": { "deployment": "cf-389cbac3d7a2c6c990c8", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "control", "origin": "uaa", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, "gauge": {"metrics": {"vitals.jvm.non-heap.init": {"unit": "gauge", "value": 7_667_712}}}, } ] }, { "batch": [ { "timestamp": "1580428783743352757", "source_id": "doppler", "instance_id": "", "deprecated_tags": {}, "tags": { "deployment": "cf-389cbac3d7a2c6c990c8", "direction": "egress", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "control", "metric_version": "2.0", "origin": "loggregator.doppler", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, "counter": {"name": "dropped", "delta": "0", "total": "149000"}, }, { "timestamp": "1580428783743352757", "source_id": "712c7c06-62eb-4cd4-92e3-1a58683d1866", "instance_id": "0", "deprecated_tags": {}, "tags": { "deployment": "cf-389cbac3d7a2c6c990c8", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "compute", "origin": "rep", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, "gauge": {"metrics": {"cpu": {"unit": "gauge", "value": 555}}}, }, ] }, { "batch": [ { "timestamp": "1580428783743496839", "source_id": "doppler", "instance_id": "", "deprecated_tags": {}, "tags": { "deployment": "cf-389cbac3d7a2c6c990c8", "direction": "ingress", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "control", "metric_version": "2.0", "origin": "loggregator.doppler", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, "counter": {"name": "dropped", "delta": "0", "total": "0"}, }, { "timestamp": "1580428783744624100", "source_id": "doppler", "instance_id": "", "deprecated_tags": {}, "tags": { "deployment": "cf-389cbac3d7a2c6c990c8", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "control", "metric_version": "2.0", "origin": "loggregator.doppler", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, "counter": {"name": "egress", "delta": "0", "total": "1075978016"}, }, { "timestamp": "1580428783744924877", "source_id": "doppler", "instance_id": "", "deprecated_tags": {}, "tags": { "deployment": "cf-389cbac3d7a2c6c990c8", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "control", "metric_version": "2.0", "origin": "loggregator.doppler", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, "counter": {"name": "egress", "delta": "7457", "total": "1075985473"}, }, { "timestamp": "1580428783833603896", "source_id": "system_metrics_agent", "instance_id": "", "deprecated_tags": {}, "tags": { "deployment": "service-instance_a474d20d-9a64-4bac-993d-e0f644604083", "index": "2cc60900-9c39-4ec3-80bb-2c1d22c10130", "ip": "10.0.8.28", "job": "mongodb-config-agent", "origin": "system_metrics_agent", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, "gauge": {"metrics": {"system_cpu_sys": {"unit": "Percent", "value": 0.315_324_026_576_374_3}}}, }, { "timestamp": "1580428783833625031", "source_id": "system_metrics_agent", "instance_id": "", "deprecated_tags": {}, "tags": { "deployment": "service-instance_a474d20d-9a64-4bac-993d-e0f644604083", "index": "2cc60900-9c39-4ec3-80bb-2c1d22c10130", "ip": "10.0.8.28", "job": "mongodb-config-agent", "origin": "system_metrics_agent", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, "gauge": { "metrics": { "system_disk_ephemeral_inode_percent": {"unit": "Percent", "value": 0.103_100_393_700_787_4} } }, }, ] }, ] with run_fake_rlp_gateway(firehose_envelopes) as [gateway_url, _], run_fake_uaa() as [uaa_url, _]: with Agent.run( f""" disableHostDimensions: true monitors: - type: cloudfoundry-firehose-nozzle uaaUrl: {uaa_url} rlpGatewayUrl: {gateway_url} uaaUser: myusername uaaPassword: mypassword extraMetrics: - "*" """ ) as agent: expected_time_series = [ [ "uaa.vitals.jvm.non-heap.init", { "deployment": "cf-389cbac3d7a2c6c990c8", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "control", "origin": "uaa", "product": "Small Footprint Pivotal Application Service", "source_id": "uaa", "system_domain": "sys.industry.cf-app.com", }, ], [ "uaa.vitals.jvm.cpu.load", { "source_id": "uaa", "deployment": "cf-389cbac3d7a2c6c990c8", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "control", "origin": "uaa", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, ], [ "uaa.vitals.jvm.thread.count", { "source_id": "uaa", "deployment": "cf-389cbac3d7a2c6c990c8", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "control", "origin": "uaa", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, ], [ "doppler.dropped", { "source_id": "doppler", "deployment": "cf-389cbac3d7a2c6c990c8", "direction": "egress", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "control", "metric_version": "2.0", "origin": "loggregator.doppler", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, ], [ "doppler.dropped", { "source_id": "doppler", "deployment": "cf-389cbac3d7a2c6c990c8", "direction": "ingress", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "control", "metric_version": "2.0", "origin": "loggregator.doppler", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, ], [ "rep.cpu", { "source_id": "712c7c06-62eb-4cd4-92e3-1a58683d1866", "instance_id": "0", "deployment": "cf-389cbac3d7a2c6c990c8", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "compute", "origin": "rep", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, ], [ "doppler.egress", { "source_id": "doppler", "deployment": "cf-389cbac3d7a2c6c990c8", "index": "ba5499ed-129c-48f2-877c-e270e5bd2648", "ip": "10.0.4.7", "job": "control", "metric_version": "2.0", "origin": "loggregator.doppler", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, ], [ "system_metrics_agent.system_cpu_sys", { "source_id": "system_metrics_agent", "deployment": "service-instance_a474d20d-9a64-4bac-993d-e0f644604083", "index": "2cc60900-9c39-4ec3-80bb-2c1d22c10130", "ip": "10.0.8.28", "job": "mongodb-config-agent", "origin": "system_metrics_agent", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, ], [ "system_metrics_agent.system_disk_ephemeral_inode_percent", { "source_id": "system_metrics_agent", "deployment": "service-instance_a474d20d-9a64-4bac-993d-e0f644604083", "index": "2cc60900-9c39-4ec3-80bb-2c1d22c10130", "ip": "10.0.8.28", "job": "mongodb-config-agent", "origin": "system_metrics_agent", "product": "Small Footprint Pivotal Application Service", "system_domain": "sys.industry.cf-app.com", }, ], ] for metric_name, dimensions in expected_time_series: assert wait_for(p(has_time_series, agent.fake_services, metric_name=metric_name, dimensions=dimensions)) assert has_datapoint(agent.fake_services, metric_type=sf_pbuf.GAUGE, metric_name="uaa.vitals.jvm.cpu.load") assert has_datapoint( agent.fake_services, metric_type=sf_pbuf.CUMULATIVE_COUNTER, metric_name="doppler.dropped" )