0

After few days of attempts, I decided to request your help on this. I am struggled to send locust's realtime data like, current rps, current active users count to the influxDB.

User Class : starter.py

class Users(HttpUser):
wait_time = constant(1)
host = 'https://DOMAIN.jp'
tasks = [UserBehaviour.get_miniapp]

events.request_success.add_listener(FluxdbEvents.success_events_handle)
events.request_failure.add_listener(FluxdbEvents.failed_events_handle)
events.quitting.add_listener(FluxdbEvents.quitting_events_handle)

Tasks class : sdkApis.py

from locust import task, TaskSet

class UserBehaviour(TaskSet):
@task
def get_miniapp(self):
    self.client.headers = {"apiKey": "ras-xxxxxxxxxxxx"}
    proxies = {
        'http': 'http://XXX.XXX.XXX.XXX:10080',
        'https': 'http://XXX.XXX.XXX.XXX:10080',
    }
    with self.client.get(
            url='/novalue-stg/novalue-publishing',
            name='get mini app details',
            auth=None,
            catch_response=True,
            proxies=proxies
    ) as response:
        if response.status_code == 200:
            response.success()
        else:
            response.failure("Failed")

Database Connection class : influxdb.py

from influxdb import InfluxDBClient
import json
import socket
import datetime
import pytz
from locust.stats import stats_printer
import gevent

class FluxdbEvents:

client = InfluxDBClient(host="localhost", port="8086", username="telegraf", password="xxxxxx", database="miniapp_metrics")

def success_events_handle(request_type, name, response_time, response_length, **kwargs):
    SUCCESS_TEMPLATE = '[{"measurement":"%s","tags":{"hostname":"%s","requestName":"%s","requestType":"%s","status":"%s","excution_num":"1"},"time":"%s","fields":{"responseTime":"%s","responseLength":"%s", "other":"%s"}}]'
    json_string = SUCCESS_TEMPLATE%("runtime_stats", socket.gethostname(), name, request_type, "OK", datetime.datetime.now(tz=pytz.UTC), response_time, response_length, kwargs)
    gevent.spawn(stats_printer(env.stats))
    FluxdbEvents.client.write_points((json.loads(json_string)))

def failed_events_handle(request_type, name, response_time, response_length, exception, **kwargs):
    FAIL_TEMPLATE = '[{"measurement":"%s", "tags":{"hostname":"%s","requestName":"%s","requestType":"%s","exception":"%s","status":"%s","excution_num":"1"}, "time":"%s", "fields": {"responseTime":"%s","responseLength":"%s","other":"%s"}}]'
    json_string = FAIL_TEMPLATE%("runtime_stats", socket.gethostname(), name, request_type, exception, "FAILED", datetime.datetime.now(tz=pytz.UTC), response_time, response_length, kwargs)
    FluxdbEvents.client.write_points((json.loads(json_string)))

def quitting_events_handle(environment):
    SUCCESS_TEMPLATE = '[{"measurement":"%s","tags":{"hostname":"%s","requestName":"%s","requestType":"%s","status":"%s","startTime":"%s"},"time":"%s","fields":{"name": "%s", "method":"%s", "num_requests":"%s", "num_failures":"%s", "avg_response_time":"%s", "min_response_time":"%s", "max_response_time": "%s", "median_response_time":"%s", "current_rps":"%s", "total_rps":"%s", "fail_ratio":"%s","50percentile":"%s", "66percentile":"%s","75percentile":"%s", "80percentile":"%s","90percentile":"%s", "95percentile":"%s", "98percentile":"%s","99percentile":"%s", "999percentile":"%s", "9999percentile":"%s", "100_percentile":"%s" }}]'
    json_string = SUCCESS_TEMPLATE%("global_stats", socket.gethostname(), environment.stats.total.name, environment.stats.total.method, "OK", environment.stats.total.start_time, datetime.datetime.now(tz=pytz.UTC), environment.stats.total.name, environment.stats.total.method, environment.stats.total.num_requests, environment.stats.total.num_failures,environment.stats.total.avg_response_time, environment.stats.total.min_response_time, environment.stats.total.max_response_time, environment.stats.total.median_response_time, environment.stats.total.current_rps, environment.stats.total.total_rps, environment.stats.total.fail_ratio, environment.stats.total.get_response_time_percentile(0.50), environment.stats.total.get_response_time_percentile(0.66), environment.stats.total.get_response_time_percentile(0.75), environment.stats.total.get_response_time_percentile(0.80), environment.stats.total.get_response_time_percentile(0.90),  environment.stats.total.get_response_time_percentile(0.95), environment.stats.total.get_response_time_percentile(0.98), environment.stats.total.get_response_time_percentile(0.99), environment.stats.total.get_response_time_percentile(0.999), environment.stats.total.get_response_time_percentile(0.9999),  environment.stats.total.get_response_time_percentile(1))
    FluxdbEvents.client.write_points((json.loads(json_string)))

If you notice, my success_events_handle & failed_events_handle only returns few metrics like, request_type, name, response_time, response_length, Is there any way that I can send more data like , current rps and current user count, OR Is there any better way to handle this ?

PLEASE NOTE quitting.add_listener work perfectly and send stats metrics to database.

Please help me

UtpMahesh
  • 410
  • 10
  • 25
  • Hello, I'm currently trying to write a code similar to what you are showing. At the moment I'm using the "locust_influxdb_listener" and it works fine, but I would like to expand it in order to get a more constant stream of data. Some of the information I would like to obtain is the ones you have written ('current rps' and 'current user count'), because currently, the code writes in the influx DB only a one-time event when the spawning is finished. Did you implement one of the ideas suggested by @Cyberwiz? Thank you – Henry Apr 24 '22 at 13:44

1 Answers1

0

I dont have a copy paste solution for that, but there are basically two options, both implemented in Locust Plugins

Cyberwiz
  • 11,027
  • 3
  • 20
  • 40