<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
</head>
<body>
<p>In case someone is interested this is the final version of the
script:</p>
<pre style="background-color:#ffffff;color:#000000;font-family:'JetBrains Mono',monospace;font-size:9,8pt;"><span style="color:#808080;font-style:italic;">-- To use
</span><span style="color:#808080;font-style:italic;">--
</span><span style="color:#808080;font-style:italic;">-- plugin {
</span><span style="color:#808080;font-style:italic;">-- push_notification_driver = lua:file=/etc/dovecot/dovecot-push.lua
</span><span style="color:#808080;font-style:italic;">-- push_lua_url = <a class="moz-txt-link-freetext" href="https://Bearer">https://Bearer</a>:<push-token>@<egroupware-domain>/egroupware/push
</span><span style="color:#808080;font-style:italic;">-- }
</span><span style="color:#808080;font-style:italic;">--
</span><span style="color:#808080;font-style:italic;">-- server is sent a PUT message with JSON body like push_notification_driver = ox:url=<push_lua_url> user_from_metadata
</span><span style="color:#808080;font-style:italic;">-- plus additionally the events MessageAppend, MessageExpunge, FlagsSet and FlagsClear
</span><span style="color:#808080;font-style:italic;">-- MessageTrash and MessageRead are ignored, so are empty FlagSet/Clear or FlagSet NonJunk (TB)
</span><span style="color:#808080;font-style:italic;">--
</span><span style="color:#808080;font-style:italic;">
</span><span style="color:#000080;font-weight:bold;">local </span>http = <span style="color:#cc542e;">require </span><span style="color:#008000;font-weight:bold;">"socket.http"
</span><span style="color:#000080;font-weight:bold;">local </span>ltn12 = <span style="color:#cc542e;">require </span><span style="color:#008000;font-weight:bold;">"ltn12"
</span><span style="color:#808080;font-style:italic;">-- luarocks install json-lua
</span><span style="color:#000080;font-weight:bold;">local </span>json = <span style="color:#cc542e;">require </span><span style="color:#008000;font-weight:bold;">"JSON"
</span><span style="color:#008000;font-weight:bold;">
</span><span style="color:#000080;font-weight:bold;">function </span><span style="color:#660e7a;font-style:italic;">table_get</span>(<span style="color:#006666;font-weight:bold;">t</span>, <span style="color:#006666;font-weight:bold;">k</span>, <span style="color:#006666;font-weight:bold;">d</span>)
<span style="color:#000080;font-weight:bold;">return </span><span style="color:#006666;font-weight:bold;">t</span>[<span style="color:#006666;font-weight:bold;">k</span>] <span style="color:#000080;font-weight:bold;">or </span><span style="color:#006666;font-weight:bold;">d
</span><span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;">
</span><span style="color:#000080;font-weight:bold;">function </span><span style="color:#660e7a;font-style:italic;">script_init</span>()
<span style="color:#000080;font-weight:bold;">return </span><span style="color:#0000ff;">0
</span><span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;">
</span><span style="color:#000080;font-weight:bold;">function </span><span style="color:#660e7a;font-style:italic;">dovecot_lua_notify_begin_txn</span>(<span style="color:#006666;font-weight:bold;">user</span>)
<span style="color:#000080;font-weight:bold;">local </span>meta = <span style="color:#006666;font-weight:bold;">user</span>:metadata_get(<span style="color:#008000;font-weight:bold;">"/private/vendor/vendor.dovecot/http-notify"</span>)
<span style="color:#000080;font-weight:bold;">if </span>(meta == <span style="color:#d700ff;">nil </span><span style="color:#000080;font-weight:bold;">or </span>meta:sub(<span style="color:#0000ff;">1</span>,<span style="color:#0000ff;">5</span>) ~= <span style="color:#008000;font-weight:bold;">"user="</span>)
<span style="color:#000080;font-weight:bold;">then
</span><span style="color:#000080;font-weight:bold;"> </span>meta = <span style="color:#d700ff;">nil</span>;
<span style="color:#000080;font-weight:bold;">else
</span><span style="color:#000080;font-weight:bold;"> </span>meta = meta:sub(<span style="color:#0000ff;">6</span>)
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;"> return </span>{user=<span style="color:#006666;font-weight:bold;">user</span>, event=<span style="color:#660e7a;font-style:italic;">dovecot</span>.<span style="font-style:italic;">event</span>(), ep=<span style="color:#006666;font-weight:bold;">user</span>:plugin_getenv(<span style="color:#008000;font-weight:bold;">"push_lua_url"</span>), messages={}, meta=meta}
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;">
</span><span style="color:#000080;font-weight:bold;">function </span><span style="color:#660e7a;font-style:italic;">dovecot_lua_notify_event_message_new</span>(<span style="color:#006666;font-weight:bold;">ctx</span>, <span style="color:#006666;font-weight:bold;">event</span>)
<span style="color:#808080;font-style:italic;">-- check if there is a push token registered
</span><span style="color:#808080;font-style:italic;"> </span><span style="color:#000080;font-weight:bold;">if </span>(<span style="color:#006666;font-weight:bold;">ctx</span>.meta == <span style="color:#d700ff;">nil</span>) <span style="color:#000080;font-weight:bold;">then
</span><span style="color:#000080;font-weight:bold;"> return
</span><span style="color:#000080;font-weight:bold;"> end
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#808080;font-style:italic;">-- get mailbox status
</span><span style="color:#808080;font-style:italic;"> </span><span style="color:#000080;font-weight:bold;">local </span>mbox = <span style="color:#006666;font-weight:bold;">ctx</span>.user:mailbox(<span style="color:#006666;font-weight:bold;">event</span>.mailbox)
mbox:sync()
<span style="color:#000080;font-weight:bold;">local </span>status = mbox:status(<span style="color:#660e7a;font-style:italic;">dovecot</span>.storage.STATUS_RECENT, <span style="color:#660e7a;font-style:italic;">dovecot</span>.storage.STATUS_UNSEEN, <span style="color:#660e7a;font-style:italic;">dovecot</span>.storage.STATUS_MESSAGES)
mbox:free()
<span style="color:#cc542e;">table</span>.insert(<span style="color:#006666;font-weight:bold;">ctx</span>.messages, {
user = <span style="color:#006666;font-weight:bold;">ctx</span>.meta,
[<span style="color:#008000;font-weight:bold;">"imap-uidvalidity"</span>] = <span style="color:#006666;font-weight:bold;">event</span>.uid_validity,
[<span style="color:#008000;font-weight:bold;">"imap-uid"</span>] = <span style="color:#006666;font-weight:bold;">event</span>.uid,
folder = <span style="color:#006666;font-weight:bold;">event</span>.mailbox,
event = <span style="color:#006666;font-weight:bold;">event</span>.name,
from = <span style="color:#006666;font-weight:bold;">event</span>.from,
subject = <span style="color:#006666;font-weight:bold;">event</span>.subject,
snippet = <span style="color:#006666;font-weight:bold;">event</span>.snippet,
unseen = status.unseen,
messages = status.messages
})
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;">
</span><span style="color:#000080;font-weight:bold;">function </span><span style="color:#660e7a;font-style:italic;">dovecot_lua_notify_event_message_append</span>(<span style="color:#006666;font-weight:bold;">ctx</span>, <span style="color:#006666;font-weight:bold;">event</span>)
<span style="color:#660e7a;font-style:italic;">dovecot_lua_notify_event_message_new</span>(<span style="color:#006666;font-weight:bold;">ctx</span>, <span style="color:#006666;font-weight:bold;">event</span>)
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;">
</span><span style="color:#808080;font-style:italic;">-- ignored, as FlagSet flags=[\Seen] is sent anyway too
</span><span style="color:#808080;font-style:italic;">-- function dovecot_lua_notify_event_message_read(ctx, event)
</span><span style="color:#808080;font-style:italic;">-- dovecot_lua_notify_event_message_expunge(ctx, event)
</span><span style="color:#808080;font-style:italic;">-- end
</span><span style="color:#808080;font-style:italic;">
</span><span style="color:#808080;font-style:italic;">-- ignored, as most MUA nowadays expunge immediatly
</span><span style="color:#808080;font-style:italic;">-- function dovecot_lua_notify_event_message_trash(ctx, event)
</span><span style="color:#808080;font-style:italic;">-- dovecot_lua_notify_event_message_expunge(ctx, event)
</span><span style="color:#808080;font-style:italic;">-- end
</span><span style="color:#808080;font-style:italic;">
</span><span style="color:#000080;font-weight:bold;">function </span><span style="color:#660e7a;font-style:italic;">dovecot_lua_notify_event_message_expunge</span>(<span style="color:#006666;font-weight:bold;">ctx</span>, <span style="color:#006666;font-weight:bold;">event</span>)
<span style="color:#808080;font-style:italic;">-- check if there is a push token registered
</span><span style="color:#808080;font-style:italic;"> </span><span style="color:#000080;font-weight:bold;">if </span>(<span style="color:#006666;font-weight:bold;">ctx</span>.meta == <span style="color:#d700ff;">nil</span>) <span style="color:#000080;font-weight:bold;">then
</span><span style="color:#000080;font-weight:bold;"> return
</span><span style="color:#000080;font-weight:bold;"> end
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#808080;font-style:italic;">-- get mailbox status
</span><span style="color:#808080;font-style:italic;"> </span><span style="color:#000080;font-weight:bold;">local </span>mbox = <span style="color:#006666;font-weight:bold;">ctx</span>.user:mailbox(<span style="color:#006666;font-weight:bold;">event</span>.mailbox)
mbox:sync()
<span style="color:#000080;font-weight:bold;">local </span>status = mbox:status(<span style="color:#660e7a;font-style:italic;">dovecot</span>.storage.STATUS_RECENT, <span style="color:#660e7a;font-style:italic;">dovecot</span>.storage.STATUS_UNSEEN, <span style="color:#660e7a;font-style:italic;">dovecot</span>.storage.STATUS_MESSAGES)
mbox:free()
<span style="color:#808080;font-style:italic;">-- agregate multiple Expunge (or Trash or Read)
</span><span style="color:#808080;font-style:italic;"> </span><span style="color:#000080;font-weight:bold;">if </span>(#<span style="color:#006666;font-weight:bold;">ctx</span>.messages == <span style="color:#0000ff;">1 </span><span style="color:#000080;font-weight:bold;">and </span><span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>].user == <span style="color:#006666;font-weight:bold;">ctx</span>.meta <span style="color:#000080;font-weight:bold;">and </span><span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>].folder == <span style="color:#006666;font-weight:bold;">event</span>.mailbox <span style="color:#000080;font-weight:bold;">and
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>][<span style="color:#008000;font-weight:bold;">"imap-uidvalidity"</span>] == <span style="color:#006666;font-weight:bold;">event</span>.uid_validity <span style="color:#000080;font-weight:bold;">and </span><span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>].event == <span style="color:#006666;font-weight:bold;">event</span>.name)
<span style="color:#000080;font-weight:bold;">then
</span><span style="color:#000080;font-weight:bold;"> if </span>(<span style="color:#cc542e;">type</span>(<span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>][<span style="color:#008000;font-weight:bold;">"imap-uid"</span>]) ~= <span style="color:#008000;font-weight:bold;">'table'</span>) <span style="color:#000080;font-weight:bold;">then
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>][<span style="color:#008000;font-weight:bold;">"imap-uid"</span>] = {<span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>][<span style="color:#008000;font-weight:bold;">"imap-uid"</span>]}
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#cc542e;">table</span>.insert(<span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>][<span style="color:#008000;font-weight:bold;">"imap-uid"</span>], <span style="color:#006666;font-weight:bold;">event</span>.uid)
<span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>].unseen = status.unseen
<span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>].messages = status.messages
<span style="color:#000080;font-weight:bold;">return</span>;
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#cc542e;">table</span>.insert(<span style="color:#006666;font-weight:bold;">ctx</span>.messages, {
user = <span style="color:#006666;font-weight:bold;">ctx</span>.meta,
[<span style="color:#008000;font-weight:bold;">"imap-uidvalidity"</span>] = <span style="color:#006666;font-weight:bold;">event</span>.uid_validity,
[<span style="color:#008000;font-weight:bold;">"imap-uid"</span>] = <span style="color:#006666;font-weight:bold;">event</span>.uid,
folder = <span style="color:#006666;font-weight:bold;">event</span>.mailbox,
event = <span style="color:#006666;font-weight:bold;">event</span>.name,
unseen = status.unseen,
messages = status.messages
})
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;">
</span><span style="color:#000080;font-weight:bold;">function </span><span style="color:#660e7a;font-style:italic;">dovecot_lua_notify_event_flags_set</span>(<span style="color:#006666;font-weight:bold;">ctx</span>, <span style="color:#006666;font-weight:bold;">event</span>)
<span style="color:#808080;font-style:italic;">-- check if there is a push token registered
</span><span style="color:#808080;font-style:italic;"> </span><span style="color:#000080;font-weight:bold;">if </span>(<span style="color:#006666;font-weight:bold;">ctx</span>.meta == <span style="color:#d700ff;">nil </span><span style="color:#000080;font-weight:bold;">or
</span><span style="color:#000080;font-weight:bold;"> </span>(#<span style="color:#006666;font-weight:bold;">event</span>.flags == <span style="color:#0000ff;">0 </span><span style="color:#000080;font-weight:bold;">and </span>#<span style="color:#006666;font-weight:bold;">event</span>.keywords == <span style="color:#0000ff;">0</span>) <span style="color:#000080;font-weight:bold;">or </span><span style="color:#808080;font-style:italic;">-- ignore TB sends it empty
</span><span style="color:#808080;font-style:italic;"> </span>(#<span style="color:#006666;font-weight:bold;">event</span>.keywords == <span style="color:#0000ff;">1 </span><span style="color:#000080;font-weight:bold;">and </span><span style="color:#006666;font-weight:bold;">event</span>.keywords[<span style="color:#0000ff;">1</span>] == <span style="color:#008000;font-weight:bold;">"NonJunk"</span>)) <span style="color:#808080;font-style:italic;">-- ignore TB NonJunk
</span><span style="color:#808080;font-style:italic;"> </span><span style="color:#000080;font-weight:bold;">then
</span><span style="color:#000080;font-weight:bold;"> return
</span><span style="color:#000080;font-weight:bold;"> end
</span><span style="color:#000080;font-weight:bold;"> local </span>status = <span style="color:#d700ff;">nil</span>;
<span style="color:#000080;font-weight:bold;">if </span>(#<span style="color:#006666;font-weight:bold;">event</span>.flags == <span style="color:#0000ff;">1 </span><span style="color:#000080;font-weight:bold;">and </span><span style="color:#006666;font-weight:bold;">event</span>.flags[<span style="color:#0000ff;">1</span>] == <span style="color:#008000;font-weight:bold;">"</span><span style="color:#000080;font-weight:bold;">\\</span><span style="color:#008000;font-weight:bold;">Seen"</span>)
<span style="color:#000080;font-weight:bold;">then
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#808080;font-style:italic;">-- get mailbox status
</span><span style="color:#808080;font-style:italic;"> </span><span style="color:#000080;font-weight:bold;">local </span>mbox = <span style="color:#006666;font-weight:bold;">ctx</span>.user:mailbox(<span style="color:#006666;font-weight:bold;">event</span>.mailbox)
mbox:sync()
status = mbox:status(<span style="color:#660e7a;font-style:italic;">dovecot</span>.storage.STATUS_RECENT, <span style="color:#660e7a;font-style:italic;">dovecot</span>.storage.STATUS_UNSEEN, <span style="color:#660e7a;font-style:italic;">dovecot</span>.storage.STATUS_MESSAGES)
mbox:free()
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#808080;font-style:italic;">-- agregate multiple FlagSet
</span><span style="color:#808080;font-style:italic;"> </span><span style="color:#000080;font-weight:bold;">if </span>(#<span style="color:#006666;font-weight:bold;">ctx</span>.messages == <span style="color:#0000ff;">1 </span><span style="color:#000080;font-weight:bold;">and </span><span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>].user == <span style="color:#006666;font-weight:bold;">ctx</span>.meta <span style="color:#000080;font-weight:bold;">and </span><span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>].folder == <span style="color:#006666;font-weight:bold;">event</span>.mailbox <span style="color:#000080;font-weight:bold;">and
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>][<span style="color:#008000;font-weight:bold;">"imap-uidvalidity"</span>] == <span style="color:#006666;font-weight:bold;">event</span>.uid_validity <span style="color:#000080;font-weight:bold;">and </span><span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>].event == <span style="color:#006666;font-weight:bold;">event</span>.name <span style="color:#000080;font-weight:bold;">and
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#660e7a;font-style:italic;">arrayEqual</span>(<span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>].flags, <span style="color:#006666;font-weight:bold;">event</span>.flags) <span style="color:#000080;font-weight:bold;">and </span><span style="color:#660e7a;font-style:italic;">arrayEqual</span>(<span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>].keywords, <span style="color:#006666;font-weight:bold;">event</span>.keywords))
<span style="color:#000080;font-weight:bold;">then
</span><span style="color:#000080;font-weight:bold;"> if </span>(<span style="color:#cc542e;">type</span>(<span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>][<span style="color:#008000;font-weight:bold;">"imap-uid"</span>]) ~= <span style="color:#008000;font-weight:bold;">'table'</span>) <span style="color:#000080;font-weight:bold;">then
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>][<span style="color:#008000;font-weight:bold;">"imap-uid"</span>] = {<span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>][<span style="color:#008000;font-weight:bold;">"imap-uid"</span>]}
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#cc542e;">table</span>.insert(<span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>][<span style="color:#008000;font-weight:bold;">"imap-uid"</span>], <span style="color:#006666;font-weight:bold;">event</span>.uid)
<span style="color:#000080;font-weight:bold;">if </span>(status ~= <span style="color:#d700ff;">nil</span>)
<span style="color:#000080;font-weight:bold;">then
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#006666;font-weight:bold;">ctx</span>.messages[<span style="color:#0000ff;">1</span>].unseen = status.unseen
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;"> return</span>;
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#cc542e;">table</span>.insert(<span style="color:#006666;font-weight:bold;">ctx</span>.messages, {
user = <span style="color:#006666;font-weight:bold;">ctx</span>.meta,
[<span style="color:#008000;font-weight:bold;">"imap-uidvalidity"</span>] = <span style="color:#006666;font-weight:bold;">event</span>.uid_validity,
[<span style="color:#008000;font-weight:bold;">"imap-uid"</span>] = <span style="color:#006666;font-weight:bold;">event</span>.uid,
folder = <span style="color:#006666;font-weight:bold;">event</span>.mailbox,
event = <span style="color:#006666;font-weight:bold;">event</span>.name,
flags = <span style="color:#006666;font-weight:bold;">event</span>.flags,
keywords = <span style="color:#006666;font-weight:bold;">event</span>.keywords,
unseen = status.unseen
})
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;">
</span><span style="color:#000080;font-weight:bold;">function </span><span style="color:#660e7a;font-style:italic;">arrayEqual</span>(<span style="color:#006666;font-weight:bold;">t1</span>, <span style="color:#006666;font-weight:bold;">t2</span>)
<span style="color:#000080;font-weight:bold;">if </span>(#<span style="color:#006666;font-weight:bold;">t1 </span>~= #<span style="color:#006666;font-weight:bold;">t2</span>)
<span style="color:#000080;font-weight:bold;">then
</span><span style="color:#000080;font-weight:bold;"> return </span><span style="color:#d700ff;">false
</span><span style="color:#d700ff;"> </span><span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;"> if </span>(#<span style="color:#006666;font-weight:bold;">t1 </span>== <span style="color:#0000ff;">1 </span><span style="color:#000080;font-weight:bold;">and </span><span style="color:#006666;font-weight:bold;">t1</span>[<span style="color:#0000ff;">1</span>] == <span style="color:#006666;font-weight:bold;">t2</span>[<span style="color:#0000ff;">1</span>])
<span style="color:#000080;font-weight:bold;">then
</span><span style="color:#000080;font-weight:bold;"> return </span><span style="color:#d700ff;">true
</span><span style="color:#d700ff;"> </span><span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;"> return </span><span style="font-weight:bold;font-style:italic;">json</span>:encode(<span style="color:#006666;font-weight:bold;">t1</span>) == <span style="font-weight:bold;font-style:italic;">json</span>:encode(<span style="color:#006666;font-weight:bold;">t2</span>)
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;">
</span><span style="color:#000080;font-weight:bold;">function </span><span style="color:#660e7a;font-style:italic;">dovecot_lua_notify_event_flags_clear</span>(<span style="color:#006666;font-weight:bold;">ctx</span>, <span style="color:#006666;font-weight:bold;">event</span>)
<span style="color:#808080;font-style:italic;">-- check if there is a push token registered AND something to clear (TB sends it empty)
</span><span style="color:#808080;font-style:italic;"> </span><span style="color:#000080;font-weight:bold;">if </span>(<span style="color:#006666;font-weight:bold;">ctx</span>.meta == <span style="color:#d700ff;">nil </span><span style="color:#000080;font-weight:bold;">or </span>(#<span style="color:#006666;font-weight:bold;">event</span>.flags == <span style="color:#0000ff;">0 </span><span style="color:#000080;font-weight:bold;">and </span>#<span style="color:#006666;font-weight:bold;">event</span>.keywords == <span style="color:#0000ff;">0</span>)) <span style="color:#000080;font-weight:bold;">then
</span><span style="color:#000080;font-weight:bold;"> return
</span><span style="color:#000080;font-weight:bold;"> end
</span><span style="color:#000080;font-weight:bold;"> </span><span style="color:#cc542e;">table</span>.insert(<span style="color:#006666;font-weight:bold;">ctx</span>.messages, {
user = <span style="color:#006666;font-weight:bold;">ctx</span>.meta,
[<span style="color:#008000;font-weight:bold;">"imap-uidvalidity"</span>] = <span style="color:#006666;font-weight:bold;">event</span>.uid_validity,
[<span style="color:#008000;font-weight:bold;">"imap-uid"</span>] = <span style="color:#006666;font-weight:bold;">event</span>.uid,
folder = <span style="color:#006666;font-weight:bold;">event</span>.mailbox,
event = <span style="color:#006666;font-weight:bold;">event</span>.name,
flags = <span style="color:#006666;font-weight:bold;">event</span>.flags,
[<span style="color:#008000;font-weight:bold;">"flags-old"</span>] = <span style="color:#006666;font-weight:bold;">event</span>.flags_old,
keywords = <span style="color:#006666;font-weight:bold;">event</span>.keywords,
[<span style="color:#008000;font-weight:bold;">"keywords-old"</span>] = <span style="color:#006666;font-weight:bold;">event</span>.keywords_old
})
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;">
</span><span style="color:#000080;font-weight:bold;">function </span><span style="color:#660e7a;font-style:italic;">dovecot_lua_notify_end_txn</span>(<span style="color:#006666;font-weight:bold;">ctx</span>)
<span style="color:#808080;font-style:italic;">-- report all states
</span><span style="color:#808080;font-style:italic;"> </span><span style="color:#000080;font-weight:bold;">for </span><span style="color:#006666;font-weight:bold;">i</span>,<span style="color:#006666;font-weight:bold;">msg </span><span style="color:#000080;font-weight:bold;">in </span><span style="color:#cc542e;">ipairs</span>(<span style="color:#006666;font-weight:bold;">ctx</span>.messages) <span style="color:#000080;font-weight:bold;">do
</span><span style="color:#000080;font-weight:bold;"> local </span>e = <span style="color:#660e7a;font-style:italic;">dovecot</span>.<span style="font-style:italic;">event</span>(<span style="color:#006666;font-weight:bold;">ctx</span>.event)
e:set_name(<span style="color:#008000;font-weight:bold;">"lua_notify_mail_finished"</span>)
<span style="color:#660e7a;font-style:italic;">reqbody </span>= <span style="font-weight:bold;font-style:italic;">json</span>:encode(<span style="color:#006666;font-weight:bold;">msg</span>)
e:log_debug(<span style="color:#006666;font-weight:bold;">ctx</span>.ep .. <span style="color:#008000;font-weight:bold;">" - sending " </span>.. <span style="color:#660e7a;font-style:italic;">reqbody</span>)
<span style="color:#660e7a;font-style:italic;">res</span>, <span style="color:#660e7a;font-style:italic;">code </span>= <span style="font-weight:bold;font-style:italic;">http</span>.<span style="font-style:italic;">request</span>({
method = <span style="color:#008000;font-weight:bold;">"PUT"</span>,
url = <span style="color:#006666;font-weight:bold;">ctx</span>.ep,
source = <span style="font-weight:bold;font-style:italic;">ltn12</span>.source.<span style="font-style:italic;">string</span>(<span style="color:#660e7a;font-style:italic;">reqbody</span>),
headers={
[<span style="color:#008000;font-weight:bold;">"content-type"</span>] = <span style="color:#008000;font-weight:bold;">"application/json; charset=utf-8"</span>,
[<span style="color:#008000;font-weight:bold;">"content-length"</span>] = <span style="color:#cc542e;">tostring</span>(#<span style="color:#660e7a;font-style:italic;">reqbody</span>)
}
})
e:add_int(<span style="color:#008000;font-weight:bold;">"result_code"</span>, <span style="color:#660e7a;font-style:italic;">code</span>)
e:log_info(<span style="color:#008000;font-weight:bold;">"Mail notify status " </span>.. <span style="color:#cc542e;">tostring</span>(<span style="color:#660e7a;font-style:italic;">code</span>))
<span style="color:#000080;font-weight:bold;">end
</span><span style="color:#000080;font-weight:bold;">end
</span></pre>
<p>It's also in our Github repo:
<a class="moz-txt-link-freetext" href="https://raw.githubusercontent.com/EGroupware/swoolepush/master/doc/dovecot-push.lua">https://raw.githubusercontent.com/EGroupware/swoolepush/master/doc/dovecot-push.lua</a></p>
<p>Ralf<br>
</p>
<pre class="moz-signature" cols="72">--
Ralf Becker
EGroupware GmbH [<a class="moz-txt-link-abbreviated" href="http://www.egroupware.org">www.egroupware.org</a>]
Handelsregister HRB Kaiserslautern 3587
Geschäftsführer Birgit und Ralf Becker
Leibnizstr. 17, 67663 Kaiserslautern, Germany
Telefon +49 631 31657-0
</pre>
</body>
</html>