In a system design interview question, I was given the QPS of incoming request and each of these request will need to be processed async so I have a message queue which dispatches these requests to workers.
What is the common way in industry to configure the number of workers for processing? Or how to calculate this number?
Related
I have a system as shown in the diagram. Multiple clients request to the web pod, web pod pushes the request to a shared queue.
Messages from the queue are de-queued based on the rate at which process_task_worker processes the request.
Once the processing is done, it sends the message to the shared queue. These messages are then dequeued by the webhook_worker and webhook (API call) is fired to respective clients.
I would like to add rate limiter to rate limit the number of webhook sent by the webhook_worker per client. rate limiting factor could be a generic count across all the clients.
But if rate limit is breached, that message should be re-enqueued to the queue instead of discarding it.
What all techniques can i employ to solve this? What is the term called for such thing since we are not discarding it but rather re-enqueuing it?
We are building an outbound IVR that will receive a payload, in bulk, via REST API, and place an outbound call to the recipient. We are attempting to limit the number of concurrent flow executions, or calls placed at a time, to prevent transfers by the called parties from flooding the shared inbound queue. Is there any way to accomplish this internally to Twilio?
If my assumptions are correct, the limiting factors when placing outbound API calls via Twilio Studio are the inbound API queue, the number of concurrent flow executions, and the number of Calls Per Second (CPS).
My understanding is that the queued API requests are executed 30 at a time, on a FIFO basis- as one execution is completed, another begins.
Each execution can then place a call at a rate of no more than 1 CPS, so 30 seconds for all calls to be sent.
Is this correct?
Is there any means of throttling these executions, or outbound calls?
A CPS limitation would be ideal, however the minimum number is 1 CPS, which is still 3600 Calls Per Hour, far too many for this call center to handle. Can this be lowered to less than 1 CPS?
Your assumptions are correct, as far as I can tell, but Twilio is built to, within those limits, make the calls you want to make as fast as it can.
If you don't want to Twilio to place the outbound calls, you need to not send the API request to start the call until you are ready. You can do this by knowing the concurrency that you can handle in your own application and by subscribing to call status webhooks so that you know when a call is complete and you can then place a new outbound call.
I tried using parallel requests but the due to retention by AWS, it does not allow to poll back the same queue unless previously polled messages are deleted.
I however achieved doing the same using the FIFO, but not the standard queue.
Thanks in Advance!
:)
When you say "it does not allow to poll back the same queue unless previously polled messages are deleted", I assume you're talking about the inflight messages per queue limit, which is pretty high at 120,000:
For most standard queues (depending on queue traffic and message backlog), there can be a maximum of approximately 120,000 inflight messages (received from a queue by a consumer, but not yet deleted from the queue). If you reach this limit, Amazon SQS returns the OverLimit error message. To avoid reaching the limit, you should delete messages from the queue after they're processed. You can also increase the number of queues you use to process your messages. To request a limit increase, file a support request.
The expected use case of SQS is to have workers that receive a message, do some work, then delete the message. If you're not following this pattern, I'd strongly recommend reevaluating whether SQS is the right tool for what you're trying to do.
However, if you really have a valid use case for having more than 120K messages inflight at once, you'll need to describe your use case to AWS and get their approval to increase that limit.
I am going to make the rails application which integrates the Amazon's cloud services.
I have explore amazon's SNS service which gives the facility of public subscription which i don't want to do. I want to notify only particular subscriber.
For example if I have 5 subscriber in one topic then the notification should be goes to particular subscriber.
I have also explored amazon's SQS in which i have to write a poller which monitor the queue for message. SQS has also a lock mechanism but the problem is that it is distributed so there would be a chance of getting same message from another copy of queue for process.
I want to know that what would be the possible approach to go.
SQS sounds like what you want.
You can run multiple "worker" processes that compete over messages in the queue. Each message is only consumed once. The logic behind the "lock" / timeout that you mention is as follows: if one of your workers were to die after downloading a message, but before processing it, then you want that message to eventually time out and be re-downloaded for processing on another node.
Yes, SQS is built on a polling model. For example, I have a number of use cases in which I use a minutely cron job to poll for new messages in the queue and take action on any messages found. This pattern is stupid simple to build and works wonders for a bunch of use cases -- a handy little "client" script that pushes a message into the queue, and the cron activated script that will process that message within a minute or so.
If your message pattern is extremely sparse -- eg, only a few messages a day -- it may seem wasteful to poll constantly while the queue is empty. It hardly matters.
My original calculation was that a minutely cron job would cost $0.04 (now $0.02) per month. Since then, SQS added a "Long-Polling" feature that lets you achieve sub-second latency on processing new messages by sending 1 "long-poll" message every 20 seconds to poll an idle queue. Plus, they dropped the price 50%. So per month, that's 131k messages (~$0.06), a little bit more expensive, but with near realtime request processing.
Keep in mind that a minutely cron job I described only costs ~$0.04 / month in request load (30d*24h*60m * 1c / 10k msgs). So at a minutely clip, cost shouldn't really be a concern here. Even polling every second, the price rises only to $2.59 / mo, not exactly a bank buster.
However, it is possible to avoid frequent polling using a webservice that takes an SNS HTTP message. Such an architecture would work as follows: client pushes message to SNS, which pushes message to SQS and routes an HTTP request to your webservice, triggering it to drain the queue. You'd still want to poll the queue hourly or daily, just in case an HTTP request was dropped. In the end though, I'm not sure I can think of any scenario which really justifies such complexity. I'd much rather pay $0.04 a month to have a dirt simple cron job polling my queue.
I have 'Maximum send rate' quota on Amazon-SES service, which means the maximum number of emails that I can send per second.
What is the best way to organize my mailing in Ruby on Rails considering this quota?
Well, queue them and schedule a batch process to consume from this queue and send them in a timely way, considering the quota. I haven't worked with queues in RoR but I believe there are some solutions out there. Worst case scenario, queue them on the database.
One point you should consider is the batch is not fast enough to fullfil all the mailing requestes he receives. You might them notify the admin, drop or persist the mailing for further attempt. If notified you can buy more throughput from Amazon or something like that.