Promise Keeper - Silverfeelin/Starbound-MessageHandling-Demo GitHub Wiki
The PromiseKeeper
class can be used to keep track of RpcPromise
objects.
Whenever a message is sent using world.sendEntityMessage
, it will take a while before the message handler responds with a value. The RpcPromise
returned by this function allows us to keep track of this response.
The goal of the PromiseKeeper is to hide the busy work of checking promises, so you can focus on handling the results.
The promise keeper class can be found in the messageutil
script. To access it, simply require the script in your code.
require "/scripts/messageutil.lua"
Description
Creates and returns a new PromiseKeeper. You'll generally only need one.
By requiring the messageutil
script, a global PromiseKeeper named promises
is made for you. This means for most use cases you won't need to create a new PromiseKeeper.
All functions from now on should be called on this object, by using :
instead of .
.
See Programming in Lua : 16 - Object-Oriented Programming if you don't know what this does.
Return value
Empty PromiseKeeper object.
Description
Updates the promise keeper, handling any finished promises. The promise keeper will automatically clean up finished promises and call the onSuccess
or onError
callback (see PromiseKeeper:add).
You'll generally want to update the promise keeper inside your update
function.
Description
Adds a new RpcPromise
to keep track of. The onSuccess
and onError
will fire after the promise has finished, based on the promise result.
Arguments
- promise
Unfinished RpcPromise
to start tracking. This is the value returned by world.sendEntityMessage
(see Sending Messages).
- onSuccess
Function to call when the promise has finished and succeeded. The results of the message handler are passed to the onSuccess
function (if any) (see [Message Handler]]).
- onError
Function to call when the promise has finished due to an error. The error message is passed to the onError
function.
Description
Checks if the PromiseKeeper is holding any unfinished RpcPromise
.
Return value
True if the PromiseKeeper has no pending RpcPromise
objects, false otherwise.
If there are unhandled but finished promises (usually a result of not calling promiseKeeper:update()
in a timely manner), this will still return false.
require "/scripts/messageutil.lua"
local promiseKeeper = promises -- We use the promise keeper created by requiring messageutil.
-- Update the promise keeper periodically.
function update()
-- This check for emptiness isn't necessary, and is only here to show that it works.
if not promiseKeeper:empty() then
promiseKeeper:update()
end
end
-- Under some condition (not init), send the messages and wait for the answer.
function sendMessages()
askMultiply(3, 3)
askMultiply(5, 10)
askMultiply(5, 20)
end
-- Send a message to multiply a with b.
function askMultiply(a, b)
-- By defining the functions inline, we can match the numbers known in this function together with the answer.
-- If we set onMultiply and onMultiplyFailed as the callbacks, we could only see the answer or error message.
promiseKeeper:add(
world.sendEntityMessage(entity.id(), "multiply", a, b), -- promise
function(answer) -- onSuccess
onMultiply(a, b, answer)
end,
function(err) -- onError
onMultiplyFailed(a, b, err)
end
)
end
-- Log answer
function onMultiply(a, b, answer)
sb.logInfo("%s * %s = %s", a, b, answer)
end
-- Log error message
function onMultiplyFailed(a, b, err)
sb.logWarn("Multiplying %s by %s failed: %s", a, b, err)
end