How to limit the number of API methods calls in test?

Hello, guys!
I am newbie in k6. Could you help me with a support request ? I need to test three different API methods sequentially under the same user. Each of these methods must be called once. The test should be run once a minute. I have already configured the vus parameter to limit the number of users, but the API methods are called several times during the test run. What parameter should I use to limit the number of method calls ? The screenshot below shows the results of the test.

Hi @Daniil,
the way k6 works is that it does as many iterations of the default function as fast as possible.
From what see, I can only guess that you are running for a duration of 2 seconds and manage to finish 2 iterations and do 7 requests. I would expect the 7th request to be the first in the 3rd iteration but your test runs out of time as you have specified 2 seconds.

If what you want is to do 1 iteration you can instead of specifying duration:2s (doc) to specify iterations:1 (doc). This will mean that k6 will do 1 iteration and then stop. Alternatively (especially if you want to run this for a long time) you can specify minIterationDuration: 60s (doc). This will mean that every time an iteration is finished k6 will check if it took at least minIterationDuration and wait/sleep for the remaining time.

More info about options can be find in the documentation.

1 Like

@mstoykov, much appreciate for your help. I’ll make changes to my test.

@mstoykov,
I checked documentation and I have one more question about test duration. Could you clarify, can i set total test time for my test (for example: 5 minutes) and repeat my actions after each minute until the test is completed ?

If you configure duration: 5min and minIterationDuration:60s, each VU (no matter how many you’ve configured, if there is no iterations configured) will start 1 iteration right away. When it finishes it will check if since the beginning of the iteration 60seconds have passed and if not sleep for the rest. If 60 seconds have passed it will just continue and make another iteration directly.
The duration:5min will mean that after 5min the whole k6 process will start stopping so with that configuration you will at most finish 4 iterations per VU as when the time comes for them to start the 5th the whole k6 process will start shutting down and they will stopped.

If you are doing some kind of monitoring and want this script to run forever I would recommend disabling the summary(--no-summary) and thresholds (--no-thresholds) as that will eat a lot of memory in the long run and also running with some duration such as 1000000000000s which will be around 30k years :smiley: . Alternatively you can just start a new process every 1 minute, if your script is simple enough and you use 1 VU this might be sufficiently fast.
Although I guess if you will be making 2-3 request a minute the memory will raise pretty slowly even if you keep thresholds and summary enabled, you will probably need to test and see if the memory increase over 24hours is too big … although again if you are doing 1/min and 3requests/iteration that would probably not be a problem :wink:

If on the other hand you want to do X number of iterations with N number of times between them on a single VU, I would argue you should do iterations:X and minDuration:N.

@mstoykov, thank you again for your help.

1 Like

Hi Daniil,

meanwhile in trying to figuring out how to work with trends and limiting your number of API requests, you can have have a look at our blog post about the same topic. Hope it helps!

How to generate a constant request rate in k6?

@mostafa, thank you.
But I’m looking how to implement a unique counter for each VU to unify each of tokens i use for my signIn requests.

Then, have a look at execution context variables to help with the unique counter.

1 Like

@mostafa, thank you!
For generating unique token, I used the __VU parameter. But there is still a question about caching requests in k6. Now in my test i’m trying to call SignIn method using 2 vus with 2 min duration and minIterationDuration: 60s. Method always returns the same JWT accessToken. Could you tell me whether the tool can cache requests by default? How can I avoid this if this is the case ?
Thank you in advance for your response.

Hi @Daniil,
k6 does not cache any responses … it is actually a thing people have requested that it does.
In your case Access token seems to be a JWT web token, which is used to sign (parts of) contents of a json, AFAIK. As the json doesn’t change the token shouldn’t either.

@mstoykov, thank you for the answer. I check it in my test.

I’m sorry guys for bother you again. Can I clarify more about the restrictions on the number of requests? For example, I have three methods which i want to use for load testing: a(), b(), and c(). For the test i want to set 10 vus. I need to call method b() 6 times in a minute, a() and c() once each. Is it possible to flexibly configure this via k6 using the RPS parameter ?

Given your requirements, I would argue that the rps parameter is not what you want :D.

If you are pretty sure your request will finish in up to a minute I would argue that you should:

  1. use 8 vus (or 3 loook below)
  2. set minIterationDuration to 60s
  3. have a default func such as:
export default function() {
  if __VU == 0{
    a();
  } else if __VU == 1 {
    c();
  } else {
    b();
     // or call it 6 times here if it will always take less then 10 seconds and you don't want to call them in parallel
   // if you don't care or if not certain I would argue it is fine to use 5 more VUs :D 
  }
}

This way all VUs will execute at most 1 iteration each minute, which if your requests are fast enough will be sufficient.
The first VU (with index 0 ) will execute a() once each minute, the second (with index 1) will do the same for c(). All other (6 VUs) will execute b() once.

As I noted in the comments if b() and you don’t require b() to be called in parallel you can save 5 VUs and call b sequentially 6 times in the else clause :smiley:. Or use http.batch if it is truly one http request.

2 Likes

Hello, guys!

Thank you so much for your answers. I have another one with k6 scenarios. Can I pause k6 until the iteration ends using minIterationDuration with k6 scenario https://k6.io/docs/using-k6/scenarios#per-vu-iterations or maybe with another k6 scenario executor?

@Daniil, I’m not sure I completely understand the question, but I’ll try to answer anyway. If you have minIterationDuration: "Xs", then each duration in your script will take at least X seconds. If your script takes less than X seconds, then k6 will wait and not start the next iteration until they pass, and if it takes more than X seconds, it will start the next iteration immediately. And this applies for all executor types.

@ned, ok, thank you.

To use k6 executors is a new experience for me. I’ll check it out.

чт, 10 сент. 2020 г. в 19:51, ned via k6 community forum <k6@discoursemail.com>: