Forum Discussion

nielswinters's avatar
nielswinters
Icon for Neophyte rankNeophyte
2 months ago

How to handle rate limiting in the LogicMonitor SDK v3?

In order to prevent running into 429 errors, I would like to check the 'x-rate-limit-remaining' in the response headers when I have made a call. But it appears these headers are only returned when an exception already has taken place.

Is it possible to check these values or are these simply not returned unless there is an error? In the latter case, please consider this a feature request. :) 

Screenshot for reference:

Thanks!

  • I very much disliked the SDK so I went and wrote my own lol.

    But if memory serves you need to use the calls that have something like http in the name. Those return the headers as well. Then you can look at the limit where you are in the limit and the wait time and work with that.

    • Joe_Williams's avatar
      Joe_Williams
      Icon for Professor rankProfessor

      From a quick search, it looks like its "with_http_info" that you are looking for.

  • Thank you for your reply, very much appreciated. I will take a look at that call.

  • Hey Joe_Williams 

    I'm probably being super dumb but i don't see anything like with_http_info as an attribute on the object that is returned from the call i make to update_device_datasource_instance_by_id

    any thoughts?

  • ['__cause__', '__class__', '__context__', '__delattr__', '__dict__', '__dir__', '__doc__', '__eq__', '__firstlineno__', '__format__', '__ge__', '__getattribute__', '__getstate__', '__gt__', '__hash__', '__init__', '__init_subclass__', '__le__', '__lt__', '__module__', '__ne__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__setstate__', '__sizeof__', '__static_attributes__', '__str__', '__subclasshook__', '__suppress_context__', '__traceback__', '__weakref__', 'add_note', 'args', 'body', 'headers', 'reason', 'status', 'with_traceback']

    so i see when it throws the exception i can access the headers, but i'd rather handle it before then.

    i think I'll just re-write the script to chunk it up to blocks of 200 and sleep for 60 between each block.

    still would appreciate any insight :)

    • Joe_Williams's avatar
      Joe_Williams
      Icon for Professor rankProfessor

      So the idea is, for each call you make, you use the one that has the with_http_info. That then returns the headers. You then look for the x-rate-limit-remaining and do something like if x-rate-limit-remaining < 2 then sleep for 30 seconds. If you want I can work up a working example here shortly.

      • Joe_Williams's avatar
        Joe_Williams
        Icon for Professor rankProfessor

        llama Here is a working example. This will never trigger the sleep, but gives you an idea of how it works.

        import os
        import logicmonitor_sdk
        import time
        lmsdkconfig = logicmonitor_sdk.Configuration()
        lmsdkconfig.company = os.getenv("LM_PORTAL")
        lmsdkconfig.auth_type = 'Bearer'
        lmsdkconfig.bearer_token = os.getenv("LM_BEARER")
        
        lmsdk = logicmonitor_sdk.LMApi(logicmonitor_sdk.ApiClient(lmsdkconfig))
        
        x = 0
        while x < 10:
            user = lmsdk.get_admin_list_with_http_info(size=1,offset=x)
            user_id = user[0].items[0].id
            print(f'user_id: {user_id}')
            headerinfo = user[2]
            lm_api_limit = int(user[2].get('x-rate-limit-limit'))
            lm_api_remaining = int(user[2].get('x-rate-limit-remaining'))
            lm_api_window = int(user[2].get('x-rate-limit-window'))
            
            # print(f"lm_api_limit: {lm_api_limit}")
            print(f"lm_api_remaining: {lm_api_remaining}")
            # print(f"lm_api_window: {lm_api_window}")
            x += 1
            if lm_api_remaining < 2:
                print(f"Rate limit is almost reached, sleeping for {lm_api_window} seconds")
                time.sleep(lm_api_window)