view util/smqueue.lua @ 13994:8baaefc4db79

util.smqueue: Minor reformatting for code style, add some comments The `smqueue` table (of methods) is no longer exported, as I couldn't see it being used anywhere and it is unconventional (only new() is exported, and methods should be called on the objects returned from that).
author Matthew Wild <mwild1@gmail.com>
date Thu, 04 Dec 2025 11:39:34 +0000
parents d10957394a3c
children df970d2dac45
line wrap: on
line source

-- Represents an outgoing reliable stanza queue

local queue = require("prosody.util.queue");

-- SM queue methods
local smqueue = {};

function smqueue:push(v)
	self._head = self._head + 1;

	assert(self._queue:push(v));
end

-- Call when receiver has acknowledged some stanzas
-- `h` (sent by the receiver) is the running count of
-- successfully received stanzas
function smqueue:ack(h)
	if h < self._tail then
		-- h is less than a previous h
		return nil, "tail"
	elseif h > self._head then
		-- h is greater than the number of stanzas we sent
		return nil, "head"
	end

	local acked = {};
	self._tail = h;
	local expect = self._head - self._tail;
	while expect < self._queue:count() do
		local v = self._queue:pop();
		if not v then return nil, "pop" end
		table.insert(acked, v);
	end

	return acked
end

function smqueue:count_unacked() return self._head - self._tail end

function smqueue:count_acked() return self._tail end

function smqueue:resumable() return self._queue:count() >= (self._head - self._tail) end

function smqueue:resume() return self._queue:items() end

function smqueue:consume() return self._queue:consume() end

function smqueue:table()
	local t = {};
	for i, v in self:resume() do t[i] = v; end
	return t
end

local smqueue_mt = {
	__name = "smqueue";
	__index = smqueue;
	__len = smqueue.count_unacked;
	-- Return a simple object for serialization
	__freeze = function (q) return { head = q._head; tail = q._tail } end;
};

local lib = {};

function lib.new(size)
	assert(size > 0);
	return setmetatable({
		_head = 0;
		_tail = 0;
		_queue = queue.new(size, true);
	}, smqueue_mt)
end

return lib