I have about 15 fruits, that has to hit a url:
http://myurl/fruit1
http://myurl/fruit2
http://myurl/fruit3
...
http://myurl/fruit15
It can occur asynchronously, what is the best way to get all 15 without tanking the server? Each item should be added to a list as they are retrieved.
Note that this happens every time a user visits the page. The fruit data does not change. Its going out to fetch the data, and add to list. My concern is the fact that it has to make multiple requests, which I want to not affect the performance of the application/browser (i.e. freezing for moments while its waiting for an HTTp request to return as information for each fruit is about 1.5MB.
How frequently does the fruit data change?
If frequency of data change is low, then caching should solve a lot of problems outside of the initial retrieval of the data. If the frequency is high consider requesting a range or list of fruit from the server instead of individually. This will reduce a large amount of transfer overhead (1 request vs 15 requests).
Related
how can we keep fixed number of active concurrent users/requests at time for a scenario.
I have an unique testing problem where I am required to do the performance testing of services with fixed number of request at a given moment for a given time periods like 10 minutes or 30 minutes or 1 hour.
I am not looking for per second thing, what I am looking for is that we start with N number of requests and as any of request out of N requests completes we add one more so that at any given moment we have N concurrent requests only.
Things which I tried are rampUsers(100) over 10 seconds but what I see is sometimes there are more than 50 users at a given instance.
constantUsersPerSec(20) during (1 minute) also took the number of requests t0 50+ for sometime.
atOnceUsers(20) seems related but I don't see any way to keep it running for given number of seconds and adding more requests as previous ones completes.
Thankyou community in advance, expecting some direction from your side.
There is a throttling mechanism (https://gatling.io/docs/3.0/general/simulation_setup/#throttling) which allow you to set max number of requests, but you must remember that users are injected to simulation independently of that and you must inject enough users to produce that max number of request, without that you will end up with lower req/s. Also users that will be injected but won't be able to send request because of throttling will wait in queue for they turn. It may result in huge load just after throttle ends or may extend your simulation, so it is always better to have throttle time longer than injection time and add maxDuration() option to simulation setup.
You should also have in mind that throttled simulation is far from natural way how users behave. They never wait for other user to finish before opening page or making any action, so in real life you will always end up with variable number of requests per second.
Use the Closed Work Load Model injection supported by Gatling 3.0. In your case, to simulate and maintain 20 active users/requests for a minute, you can use an injection like,
Script.<Controller>.<Scenario>.inject(constantConcurrentUsers(20) during (60 seconds))
performance-wise which approach is better:
1) make a fetch and get 100 records all at once
2) make a fetch for each row of data individually (100 times)
P.S. I use axios
In 2019, any solution like this is less about performance and more about user experience.
Most users do not like delays, so you want to be as responsive as possible. If that is many small requests to enable to the user to do something (instead of waiting 1-2 seconds for the larger request to return) you should prefer that solution. It's dependant on what your on screen experience is like.
Having said that, 100 records is not a very big payload (generally), so if it's quite small and possibly cached, you could just get the whole 100 at once.
That will depend on the size of your row of data. There is no right answer to pick between the options you provided. I will think more along the lines of what is the maximum amount of records that I could fetch that won't slow down the client requesting them.
I don't understand something about mws throtlling.
For example with this api:
http://docs.developer.amazonservices.com/en_US/products/Products_GetMatchingProductForId.html
The Max request quota is 20. So I understand that I can submit 20 different ids on each request. But in the table there written that 'Maximum: Five Id values'.
So what the 20 represents?
20 represents the maximum about of requests you can make at a time. Each request can have a maximum of 5 Id values in the IdList. So, essentially you can submit requests for 100 (20 * 5) product Id's at a time. Then you have to wait until the quota is restored, which is 5 per second. You are also capped by an hourly request quota, in this case 18,000 requests per hour.
Do some math to figure out how many requests you need to make and space those out so enough time is given for the restore to kick in.
There are typically 2 or 3 components to Amazon throttling.
They use a modified leaky bucket algorithm. The Quota is how many separate requests you can submit at a given instant, assuming you have not already consumed any requests. This is how much the bucket can hold.
For every request you submit, the bucket 'leaks' one unit.
The restore rate, is how quickly the bucket refills.
For the API call you linked, how many requests can hypothetically be sent in 1 second? If my math is right (give or take 1) you should be capable of making 25 requests in that first second, because you exhaust the bucket, but in the first second, it also refills 5 requests.
Keep in mind that Amazon caps you on many API calls with an Hourly / Daily cap.
Edit
Keep in mind the throttling caps how many Requests you can make, not how many ID's, reports etc etc can be submitted inside of each request.
I have an application where you can select entries in a table to be updated. You can select 50 and hit 'send it' and it will send all 50 as 50 individual ajax calls, each of which calls controller X that updates the database table Y. The user said they selected 25 but I see 12 in the logs and no trace of the other 13. I was wondering if maybe I hit some limit with the number of requests or the length of the queue. Any Ideas?
(Running this locally it had no problem with 50-100 being sent at once it just took like 2 seconds for all of them to finally callback).
This question cannot really be answered as there's no "hard limit" that would cause your ajax calls to be lost. However, overloading the server (if you only have one) can cause requests to be queued up and/or take a long time which in turn may cause requests to timeout (depending on your settings). Chances are if you are making 50 ajax calls instead of just one then there is some room for optimization there and I'm not sure that classifies as premature.
In the end, I think the most and best advice you will get is to profile and load test your code and hardware to be sure otherwise we're all just guessing.
Firstly, let me explain what I'm building:
I have a D3.js Force Layout graph which is rooted at the center, and has a bunch of nodes spread around it. The center node is an Entity of some sort, the nodes around it are other Entities which are somehow related to the root. The edges are the actual relations (i.e. how the two are related).
The outer nodes can be clicked to center the target Entity and load its relations
This graph is "Egocentric" in the sense that every time a node is clicked, it becomes the center, and only relations directly involved with itself are displayed.
My Setup, in case any of it matters:
I'm serving an API through Node.js, which translates requests into queries to a CouchDB server with huge data sets.
D3.js is used for layout, and aside from jQuery and Bootstrap, I'm not using any other client-side libraries. If any would help with this caching task, I'm open to suggestions :)
My Ideas:
I could easily grab a few levels of the graph each time (recurse through the process of listing and expanding children a few times) but since clicking on any given node loads completely unrelated data, it is not guaranteed to yield a high percentage of the similar data as was loaded for the root. This seems like a complete waste, and actually a step in the opposite direction -- I'd end up doing more processing this way!
I can easily maintain a hash table of Entities that have already been retrieved, and check the list before requesting data for that entity from the server. I'll probably end up doing this regardless of the cache strategy I implement, since it's a really simple way of reducing queries.
Now, how do you suggest I cache this data?
Is there any super-effective strategy you can think of for doing this kind of caching? Both server-and-client-side options are greatly welcomed. A ton of data is involved in this process, and any reduction of querying/processing puts me miles ahead of the game.
Thanks!
On the client side I would have nodes, and have their children either be an array of children, or else a function that serves as a promise of those children. When you click on a given node, if you have data, display it immediately. Else send off an AJAX request that will fill it.
Whenever you display a node (not centered), create an asynchronous list of AJAX requests for the children of the displayed nodes and start requesting them. That way when the user clicks, there is a chance that you already have it cached. And if not, well, you tried and cost them nothing.
Once you have it working, decide how many levels deep it makes sense to go. My guess is that the magic number is likely to be 1. Beyond that the return in responsiveness falls off rapidly, while the server load rises rapidly. But having clicks come back ASAP is a pretty big UI win.
I think you need to do two things:
Reduce the number of requests you make
Reduce the cost of requests
As btilly points out, you're probably best requesting the related nodes for each visible node, so that if they are clicked the visualisation is immediately responsive -- you don't want the query plus transit time as a response lag.
However, if you have this great need to reduce the number of requests, it suggests your requests themselves are too costly, since the total load is requestCost * numRequests. Consider finding ways to pre-calculate the set of nodes related to each node, so that the request is a read request rather than a full DB query. If you're thinking that sounds hard, it's just what Google do every time you search for a new thing; they can't search the internet every time you start typing, so they do that ahead of time, and cache.
This may mean some amount of denormalisation; if you have a cache and a query, there is no guarantee they are in sync, but the question there is whether your dataset changes; is it write once, read many?
To minimise the space needed by all these nodes and their relations, see it more as a particle interaction problem; by partitioning the space you may be able to group nodes so that you only need query a group of nodes for its aggregate neighbours, and store that. That way you can do a much smaller filtration on each request rather than a full DB query. If it's O(n log n) and you make n a hundred times smaller, it's more than 100x faster.