Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to handle API calls in a row in Locust ? #2658

Closed
2 tasks done
chunji08 opened this issue Mar 28, 2024 · 3 comments
Closed
2 tasks done

How to handle API calls in a row in Locust ? #2658

chunji08 opened this issue Mar 28, 2024 · 3 comments
Labels
feature request stale Issue had no activity. Might still be worth fixing, but dont expect someone else to fix it

Comments

@chunji08
Copy link

chunji08 commented Mar 28, 2024

Prerequisites

Description

In my test case, I am trying to make multiple API calls in a sequence, where the current API call's URL value is from the previous call's response body

Here is my current code:

from locust import User, task, between, events

class SAMLUser(User):
    wait_time = between(5, 9)

    @task
    def idpfdc_sequence(self):
        idp_redirect_url = "..." 
        response1 = self.client.get(idp_redirect_url,headers=headers,verify=False, allow_redirects=False)

        # if current call fails, needs to restart from scratch.  
        if response1.status_code != 200:
           return

        response2 = self.client.get(response1.headers['Location'], headers=headers,verify=False, allow_redirects=False)
        
        # rest of the test sequence 
        pass 

    def on_start(self):
        # Initialization code goes here
        pass

  1. If I was to have it executed with limited users, everything executed smoothly, since I did not hit the failure in the response1 API call.

  2. If I was to have it executed with extra users, in some running session, the first API call hits the failure, and return back 400 code. In my current code, I was doing "return", which hopes the current session to be stopped, and a new one would be started. But I don't see it happens. What I have noticed is, all the API call hangs until the time running out.

  3. So I have tried this instead of "return",
    raise StopUser("1st API call fails!")

I do see the tests are keep going, and the 2nd API calls are being executed until the time-out. But In the locust "number of user" diagram, I am getting this,
image

As if it decrease the number of users, to make the testing moving .

So I guess my question are,
A) Is "return" the correct solution in such case ?
B) If I was to use StopUser(..), is there a way for me to spawn a new user on the fly ?
C) Any better solutions for my case ?

Thanks,

Jack

@cyberw
Copy link
Collaborator

cyberw commented Mar 29, 2024

If I was to have it executed with extra users, in some running session, the first API call hits the failure, and return back 400 code. In my current code, I was doing "return", which hopes the current session to be stopped, and a new one would be started. But I don't see it happens. What I have noticed is, all the API call hangs until the time running out.

What do you mean "the api call hangs until the time running out"?

I recommend running the test in a debugger or adding some print statements.

a) return is fine, should work pretty much the way you expect, unless you mean you want to run on_start again
b) dont throw StopUser, it is an internal thing (we should probably rename it _StopUser or something...)
c) not really. The one thing that I think you may be confused about is the fact that Users loop forever. Their session is never terminated and on_start only happens once. If you need fine grained control use a flag:

class MyUser(HttpUser):
    first_run = True

    @task
    def t(self):
        if self.first_run:
            self.first_run = False
            # Initialization code goes here      
        ...
        # if current call fails, needs to restart from scratch.  
        if response1.status_code != 200:
           self.first_run = True
           return

Another way to do it is just to call on start directly:

    # if current call fails, needs to restart from scratch.  
    if response1.status_code != 200:
       self.on_start()
       return

@chunji08
Copy link
Author

chunji08 commented Mar 29, 2024

What do you mean "the api call hangs until the time running out"?

In the middle my Locust running, if the response1 failure happened, and I had it "return", then till the end of this locust running, I don't see any extra response1 or response2 calls are made.

Thanks for the tips, I will give a try.

Thanks.

Jack

@cyberw cyberw added the stale Issue had no activity. Might still be worth fixing, but dont expect someone else to fix it label May 10, 2024
Copy link

This issue was closed because it has been stalled for 10 days with no activity. This does not necessarily mean that the issue is bad, but it most likely means that nobody is willing to take the time to fix it. If you have found Locust useful, then consider contributing a fix yourself!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
feature request stale Issue had no activity. Might still be worth fixing, but dont expect someone else to fix it
Projects
None yet
Development

No branches or pull requests

2 participants