Here’s the translation of the Go rate limiting example to Standard ML, with explanations adapted for the language:
In this Standard ML implementation:
We use the Time and Thread structures for timing and delays.
The handleRequest function simulates handling a request by printing the request number and current time.
basicRateLimiting demonstrates simple rate limiting by processing requests with a fixed delay between each.
burstyRateLimiting implements a bursty rate limiter that allows up to 3 requests to be processed immediately before enforcing delays.
Instead of channels, we use lists to represent the requests and recursive functions to process them.
The burstyLimiter is implemented as a reference to an integer, which is decremented for each burst request and refilled after a delay.
Running this program will show the first batch of requests handled once every ~200 milliseconds as desired:
For the second batch of requests (bursty limiting), we serve the first 3 immediately because of the burstable rate limiting, then serve the remaining 2 with ~200ms delays each.
Note that Standard ML doesn’t have built-in concurrency primitives like goroutines, so this implementation uses a simpler, sequential approach. For more complex scenarios, you might need to use additional libraries or language extensions that provide better concurrency support.