time_queue v0.7.0 TimeQueue
Implements a timers queue based on a list of maps. The queue can be encoded as JSON.
The performance will be worse for large queues in regard to the previous gb_trees based implementation, although the difference is negligible for small queues (<= 1000 entries).
All map keys are shrinked to a single letter as this queue is intended to be encoded and published to HTTP clients over the wire, mutiple times.
The queue keys are a map composed of the timestamp (t
) of an entry
and an unique integer (u
).
No erlang timers or processes are used, as the queue is only a data structure. The advantage is that the queue can be persisted on storage and keeps working after restarting the runtime. The queue maintain its own list of unique integers to avoir relying on BEAM unique integers as they are reset on VM restarts.
The main drawback of a functional queue is that the queue entries must be manually checked for expired timers.
Link to this section Summary
Functions
Deletes an entry from the queue and returns the new queue.
Deletes all entries from the queue whose values are equal to unwanted
.
Adds a new entry to the queue with a TTL and the current system time as now/0
.
Adds a new entry to the queue with a TTL relative to the given timestamp in milliseconds.
Adds a new entry to the queue with an absolute timestamp.
Returns a new queue with entries for whom the given callback returned a truthy value.
Returns a new queue with entries for whom the given callback returned a truthy value.
Creates an empty time queue.
Returns the next event of the queue according to the given current time in milliseconds.
Extracts the next event of the queue according to the given current time in milliseconds.
Returns the numer of entries in the queue.
Returns the time reference of an queue entry. This reference is used as a key to identify a unique entry.
Returns the value of an queue entry.
Link to this section Types
peek_return()
peek_return() :: :empty | {:delay, tref(), non_neg_integer()} | {:ok, entry()}
pop_return(tq)
pop_return(tq) :: :empty | {:delay, tref(), non_neg_integer()} | {:ok, entry(), tq}
timespec_unit()
timespec_unit() :: :ms | :second | :seconds | :minute | :minutes | :hour | :hours | :day | :days | :week | :weeks
Link to this section Functions
Deletes an entry from the queue and returns the new queue.
It accepts a time reference or a full entry. When an entry is given, its time reference will be used to find the entry to delete, meaning the queue entry will be deleted even if the value of the passed entry was tampered.
The function does not fail if the entry cannot be found and simply returns the queue as-is.
Deletes all entries from the queue whose values are equal to unwanted
.
Adds a new entry to the queue with a TTL and the current system time as now/0
.
See enqueue/4
.
enqueue(tq, ttl, val, now_ms)
Adds a new entry to the queue with a TTL relative to the given timestamp in milliseconds.
Returns {:ok, tref, new_queue}
where tref
is a timer reference.
enqueue_abs(tq, ts, val)
enqueue_abs(t(), end_time :: integer(), value :: any()) :: enqueue_return(t())
Adds a new entry to the queue with an absolute timestamp.
Returns {:ok, tref, new_queue}
where tref
is a timer reference.
Returns a new queue with entries for whom the given callback returned a truthy value.
Use filter_val/2
to filter only using values.
Returns a new queue with entries for whom the given callback returned a truthy value.
Unlinke filter/2
, the callback is only passed the entry value.
Creates an empty time queue.
iex> tq = TimeQueue.new()
iex> TimeQueue.peek(tq)
:empty
This function is used internally to determine the current time when it is
not given in the arguments to enqueue/3
, pop/1
and peek/1
.
It is a simple alias to :erlang.system_time(:millisecond)
. TimeQueue does
not use monotonic time since it already manages its own unique identifiers for
queue entries.
Returns the next event of the queue with the current system time as now/0
.
See peek/2
.
Returns the next event of the queue according to the given current time in milliseconds.
Possible return values are:
:empty
{:ok, entry}
if the timestamp of the first entry is<=
to the given current time.{:delay, tref, ms}
if the timestamp of the first entry is>
to the given current time. The remaining amount of milliseconds is returned.
Example
iex> {:ok, tref, tq} = TimeQueue.new() |> TimeQueue.enqueue(100, :hello, _now = 0)
iex> {:delay, ^tref, 80} = TimeQueue.peek(tq, _now = 20)
iex> {:ok, _} = TimeQueue.peek(tq, _now = 100)
Extracts the next event of the queue with the current system time as now/0
.
See pop/2
.
Extracts the next event of the queue according to the given current time in milliseconds.
Possible return values are:
:empty
{:ok, entry, new_queue}
if the timestamp of the first entry is<=
to the given current time. The entry is deleted fromnew_queue
.{:delay, tref, ms}
if the timestamp of the first entry is>
to the given current time. The remaining amount of milliseconds is returned.
Example
iex> {:ok, tref, tq} = TimeQueue.new() |> TimeQueue.enqueue(100, :hello, _now = 0)
iex> {:delay, ^tref, 80} = TimeQueue.pop(tq, _now = 20)
iex> {:ok, _, _} = TimeQueue.pop(tq, _now = 100)
Returns the numer of entries in the queue.
supports_encoding(arg1)
Returns the time reference of an queue entry. This reference is used as a key to identify a unique entry.
iex> tq = TimeQueue.new()
iex> {:ok, tref, tq} = TimeQueue.enqueue(tq, 10, :my_value)
iex> Process.sleep(10)
iex> {:ok, entry} = TimeQueue.peek(tq)
iex> tref == TimeQueue.tref(entry)
true
Returns the value of an queue entry.
iex> tq = TimeQueue.new()
iex> {:ok, _, tq} = TimeQueue.enqueue(tq, 10, :my_value)
iex> Process.sleep(10)
iex> {:ok, entry} = TimeQueue.peek(tq)
iex> TimeQueue.value(entry)
:my_value