plugins/mod_muc_mam.lua
author Matthew Wild <mwild1@gmail.com>
Wed, 27 Mar 2024 15:35:15 +0000
branch0.12
changeset 13469 54a936345aaa
parent 13271 7ae000fc8c07
child 13272 081f8f9b3b81
permissions -rw-r--r--
prosodyctl check: Warn about invalid domain names in the config file This ensures that domain names of virtual hosts and components are valid in XMPP, and that they are encoded correctly.
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
     1
-- XEP-0313: Message Archive Management for Prosody MUC
11286
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
     2
-- Copyright (C) 2011-2021 Kim Alvefur
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
     3
--
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
     4
-- This file is MIT/X11 licensed.
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
     5
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
     6
if module:get_host_type() ~= "component" then
9876
e1d68f32ce29 mod_muc_mam: Set error status if loaded on incorrect host type
Matthew Wild <mwild1@gmail.com>
parents: 9849
diff changeset
     7
	module:log_status("error", "mod_%s should be loaded only on a MUC component, not normal hosts", module.name);
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
     8
	return;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
     9
end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    10
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    11
local xmlns_mam     = "urn:xmpp:mam:2";
11286
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
    12
local xmlns_mam_ext = "urn:xmpp:mam:2#extended";
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    13
local xmlns_delay   = "urn:xmpp:delay";
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    14
local xmlns_forward = "urn:xmpp:forward:0";
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    15
local xmlns_st_id   = "urn:xmpp:sid:0";
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    16
local xmlns_muc_user = "http://jabber.org/protocol/muc#user";
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    17
local muc_form_enable = "muc#roomconfig_enablearchiving"
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    18
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    19
local st = require "util.stanza";
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    20
local rsm = require "util.rsm";
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    21
local jid_bare = require "util.jid".bare;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    22
local jid_split = require "util.jid".split;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    23
local jid_prep = require "util.jid".prep;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    24
local dataform = require "util.dataforms".new;
9848
3de80fc511ab mod_muc_mam: Validate that the FORM_TYPE of a query is as expected
Kim Alvefur <zash@zash.se>
parents: 9555
diff changeset
    25
local get_form_type = require "util.dataforms".get_type;
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    26
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    27
local mod_muc = module:depends"muc";
8726
f3bdb20214ab mod_muc_mam: Remove 0.10 compat code
Kim Alvefur <zash@zash.se>
parents: 8725
diff changeset
    28
local get_room_from_jid = mod_muc.get_room_from_jid;
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    29
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    30
local is_stanza = st.is_stanza;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    31
local tostring = tostring;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    32
local time_now = os.time;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    33
local m_min = math.min;
11880
52a1b885044e mod_muc_mam: Use util.dataforms timestamp validation
Kim Alvefur <zash@zash.se>
parents: 11822
diff changeset
    34
local timestamp, datestamp = import("util.datetime", "datetime", "date");
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    35
local default_max_items, max_max_items = 20, module:get_option_number("max_archive_query_results", 50);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    36
10004
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
    37
local cleanup_after = module:get_option_string("muc_log_expires_after", "1w");
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
    38
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    39
local default_history_length = 20;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    40
local max_history_length = module:get_option_number("max_history_messages", math.huge);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    41
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    42
local function get_historylength(room)
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    43
	return math.min(room._data.history_length or default_history_length, max_history_length);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    44
end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    45
9884
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
    46
function schedule_cleanup()
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
    47
	-- replaced by non-noop later if cleanup is enabled
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
    48
end
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
    49
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    50
local log_all_rooms = module:get_option_boolean("muc_log_all_rooms", false);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    51
local log_by_default = module:get_option_boolean("muc_log_by_default", true);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    52
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    53
local archive_store = "muc_log";
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    54
local archive = module:open_store(archive_store, "archive");
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    55
10004
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
    56
local archive_item_limit = module:get_option_number("storage_archive_item_limit", archive.caps and archive.caps.quota or 1000);
10804
62794e065e33 MAM: Remove 1% of contents when reaching limits, fix #1545
Kim Alvefur <zash@zash.se>
parents: 10687
diff changeset
    57
local archive_truncate = math.floor(archive_item_limit * 0.99);
10004
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
    58
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    59
if archive.name == "null" or not archive.find then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    60
	if not archive.find then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    61
		module:log("error", "Attempt to open archive storage returned a driver without archive API support");
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    62
		module:log("error", "mod_%s does not support archiving",
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    63
			archive._provided_by or archive.name and "storage_"..archive.name.."(?)" or "<unknown>");
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    64
	else
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    65
		module:log("error", "Attempt to open archive storage returned null driver");
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    66
	end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    67
	module:log("info", "See https://prosody.im/doc/storage and https://prosody.im/doc/archiving for more information");
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    68
	return false;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    69
end
12863
cd738fb8c754 mod_muc_mam: Copy "include total" behavior from mod_mam
Kim Alvefur <zash@zash.se>
parents: 12862
diff changeset
    70
local use_total = module:get_option_boolean("muc_log_include_total", true);
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    71
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    72
local function archiving_enabled(room)
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    73
	if log_all_rooms then
10004
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
    74
		module:log("debug", "Archiving all rooms");
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    75
		return true;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    76
	end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    77
	local enabled = room._data.archiving;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    78
	if enabled == nil then
10004
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
    79
		module:log("debug", "Default is %s (for %s)", log_by_default, room.jid);
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    80
		return log_by_default;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    81
	end
10004
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
    82
	module:log("debug", "Logging in room %s is %s", room.jid, enabled);
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    83
	return enabled;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    84
end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    85
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    86
if not log_all_rooms then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    87
	module:hook("muc-config-form", function(event)
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    88
		local room, form = event.room, event.form;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    89
		table.insert(form,
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    90
		{
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    91
			name = muc_form_enable,
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    92
			type = "boolean",
13271
7ae000fc8c07 mod_muc_mam: Improve wording of enable setting
Kim Alvefur <zash@zash.se>
parents: 12863
diff changeset
    93
			label = "Archive chat on server",
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    94
			value = archiving_enabled(room),
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    95
		}
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    96
		);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    97
	end);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
    98
8726
f3bdb20214ab mod_muc_mam: Remove 0.10 compat code
Kim Alvefur <zash@zash.se>
parents: 8725
diff changeset
    99
	module:hook("muc-config-submitted/"..muc_form_enable, function(event)
f3bdb20214ab mod_muc_mam: Remove 0.10 compat code
Kim Alvefur <zash@zash.se>
parents: 8725
diff changeset
   100
		event.room._data.archiving = event.value;
8835
a9c3b15b9d37 mod_muc_mam: Set status code 170/171 on archiving configuration change
Kim Alvefur <zash@zash.se>
parents: 8789
diff changeset
   101
		event.status_codes[event.value and "170" or "171"] = true;
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   102
	end);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   103
end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   104
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   105
-- Note: We ignore the 'with' field as this is internally used for stanza types
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   106
local query_form = dataform {
11880
52a1b885044e mod_muc_mam: Use util.dataforms timestamp validation
Kim Alvefur <zash@zash.se>
parents: 11822
diff changeset
   107
	{ name = "FORM_TYPE"; type = "hidden"; value = xmlns_mam };
52a1b885044e mod_muc_mam: Use util.dataforms timestamp validation
Kim Alvefur <zash@zash.se>
parents: 11822
diff changeset
   108
	{ name = "with"; type = "jid-single" };
52a1b885044e mod_muc_mam: Use util.dataforms timestamp validation
Kim Alvefur <zash@zash.se>
parents: 11822
diff changeset
   109
	{ name = "start"; type = "text-single"; datatype = "xs:dateTime" };
52a1b885044e mod_muc_mam: Use util.dataforms timestamp validation
Kim Alvefur <zash@zash.se>
parents: 11822
diff changeset
   110
	{ name = "end"; type = "text-single"; datatype = "xs:dateTime" };
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   111
};
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   112
12862
71dc48a89e5a mod_muc_mam: Add mam#extended form fields #1796 (Thanks Rain)
Kim Alvefur <zash@zash.se>
parents: 12861
diff changeset
   113
if archive.caps and archive.caps.full_id_range then
71dc48a89e5a mod_muc_mam: Add mam#extended form fields #1796 (Thanks Rain)
Kim Alvefur <zash@zash.se>
parents: 12861
diff changeset
   114
	table.insert(query_form, { name = "before-id"; type = "text-single"; });
71dc48a89e5a mod_muc_mam: Add mam#extended form fields #1796 (Thanks Rain)
Kim Alvefur <zash@zash.se>
parents: 12861
diff changeset
   115
	table.insert(query_form, { name = "after-id"; type = "text-single"; });
71dc48a89e5a mod_muc_mam: Add mam#extended form fields #1796 (Thanks Rain)
Kim Alvefur <zash@zash.se>
parents: 12861
diff changeset
   116
end
71dc48a89e5a mod_muc_mam: Add mam#extended form fields #1796 (Thanks Rain)
Kim Alvefur <zash@zash.se>
parents: 12861
diff changeset
   117
71dc48a89e5a mod_muc_mam: Add mam#extended form fields #1796 (Thanks Rain)
Kim Alvefur <zash@zash.se>
parents: 12861
diff changeset
   118
if archive.caps and archive.caps.ids then
71dc48a89e5a mod_muc_mam: Add mam#extended form fields #1796 (Thanks Rain)
Kim Alvefur <zash@zash.se>
parents: 12861
diff changeset
   119
	table.insert(query_form, { name = "ids"; type = "list-multi"; });
71dc48a89e5a mod_muc_mam: Add mam#extended form fields #1796 (Thanks Rain)
Kim Alvefur <zash@zash.se>
parents: 12861
diff changeset
   120
end
71dc48a89e5a mod_muc_mam: Add mam#extended form fields #1796 (Thanks Rain)
Kim Alvefur <zash@zash.se>
parents: 12861
diff changeset
   121
71dc48a89e5a mod_muc_mam: Add mam#extended form fields #1796 (Thanks Rain)
Kim Alvefur <zash@zash.se>
parents: 12861
diff changeset
   122
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   123
-- Serve form
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   124
module:hook("iq-get/bare/"..xmlns_mam..":query", function(event)
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   125
	local origin, stanza = event.origin, event.stanza;
12861
cc86d77481fc mod_mam,mod_muc_mam: Minimize differences (reorder, copy some comments)
Kim Alvefur <zash@zash.se>
parents: 11993
diff changeset
   126
	origin.send(st.reply(stanza):query(xmlns_mam):add_child(query_form:form()));
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   127
	return true;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   128
end);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   129
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   130
-- Handle archive queries
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   131
module:hook("iq-set/bare/"..xmlns_mam..":query", function(event)
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   132
	local origin, stanza = event.origin, event.stanza;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   133
	local room_jid = stanza.attr.to;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   134
	local room_node = jid_split(room_jid);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   135
	local orig_from = stanza.attr.from;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   136
	local query = stanza.tags[1];
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   137
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   138
	local room = get_room_from_jid(room_jid);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   139
	if not room then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   140
		origin.send(st.error_reply(stanza, "cancel", "item-not-found"))
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   141
		return true;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   142
	end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   143
	local from = jid_bare(orig_from);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   144
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   145
	-- Banned or not a member of a members-only room?
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   146
	local from_affiliation = room:get_affiliation(from);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   147
	if from_affiliation == "outcast" -- banned
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   148
		or room:get_members_only() and not from_affiliation then -- members-only, not a member
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   149
		origin.send(st.error_reply(stanza, "auth", "forbidden"))
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   150
		return true;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   151
	end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   152
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   153
	local qid = query.attr.queryid;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   154
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   155
	-- Search query parameters
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   156
	local qstart, qend;
11286
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   157
	local qbefore, qafter;
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   158
	local qids;
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   159
	local form = query:get_child("x", "jabber:x:data");
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   160
	if form then
9848
3de80fc511ab mod_muc_mam: Validate that the FORM_TYPE of a query is as expected
Kim Alvefur <zash@zash.se>
parents: 9555
diff changeset
   161
		local form_type, err = get_form_type(form);
10562
40c2500208f4 mod_muc_mam: Handle form identification error (e.g. not a form at all)
Kim Alvefur <zash@zash.se>
parents: 10419
diff changeset
   162
		if not form_type then
40c2500208f4 mod_muc_mam: Handle form identification error (e.g. not a form at all)
Kim Alvefur <zash@zash.se>
parents: 10419
diff changeset
   163
			origin.send(st.error_reply(stanza, "modify", "bad-request", "Invalid dataform: "..err));
40c2500208f4 mod_muc_mam: Handle form identification error (e.g. not a form at all)
Kim Alvefur <zash@zash.se>
parents: 10419
diff changeset
   164
			return true;
40c2500208f4 mod_muc_mam: Handle form identification error (e.g. not a form at all)
Kim Alvefur <zash@zash.se>
parents: 10419
diff changeset
   165
		elseif form_type ~= xmlns_mam then
9848
3de80fc511ab mod_muc_mam: Validate that the FORM_TYPE of a query is as expected
Kim Alvefur <zash@zash.se>
parents: 9555
diff changeset
   166
			origin.send(st.error_reply(stanza, "modify", "bad-request", "Unexpected FORM_TYPE, expected '"..xmlns_mam.."'"));
3de80fc511ab mod_muc_mam: Validate that the FORM_TYPE of a query is as expected
Kim Alvefur <zash@zash.se>
parents: 9555
diff changeset
   167
			return true;
3de80fc511ab mod_muc_mam: Validate that the FORM_TYPE of a query is as expected
Kim Alvefur <zash@zash.se>
parents: 9555
diff changeset
   168
		end
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   169
		form, err = query_form:data(form);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   170
		if err then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   171
			origin.send(st.error_reply(stanza, "modify", "bad-request", select(2, next(err))));
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   172
			return true;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   173
		end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   174
		qstart, qend = form["start"], form["end"];
11286
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   175
		qbefore, qafter = form["before-id"], form["after-id"];
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   176
		qids = form["ids"];
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   177
	end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   178
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   179
	-- RSM stuff
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   180
	local qset = rsm.get(query);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   181
	local qmax = m_min(qset and qset.max or default_max_items, max_max_items);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   182
	local reverse = qset and qset.before or false;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   183
11286
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   184
	local before, after = qset and qset.before or qbefore, qset and qset.after or qafter;
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   185
	if type(before) ~= "string" then before = nil; end
12861
cc86d77481fc mod_mam,mod_muc_mam: Minimize differences (reorder, copy some comments)
Kim Alvefur <zash@zash.se>
parents: 11993
diff changeset
   186
11286
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   187
	-- A reverse query needs to be flipped
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   188
	local flip = reverse;
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   189
	-- A flip-page query needs to be the opposite of that.
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   190
	if query:get_child("flip-page") then flip = not flip end
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   191
11821
a67b4d4f8eef mod_muc_mam: Merge main and RSM-specific log message into a single one
Kim Alvefur <zash@zash.se>
parents: 11820
diff changeset
   192
	module:log("debug", "Archive query by %s id=%s when=%s...%s rsm=%q",
a67b4d4f8eef mod_muc_mam: Merge main and RSM-specific log message into a single one
Kim Alvefur <zash@zash.se>
parents: 11820
diff changeset
   193
		from,
a67b4d4f8eef mod_muc_mam: Merge main and RSM-specific log message into a single one
Kim Alvefur <zash@zash.se>
parents: 11820
diff changeset
   194
		qid or stanza.attr.id,
a67b4d4f8eef mod_muc_mam: Merge main and RSM-specific log message into a single one
Kim Alvefur <zash@zash.se>
parents: 11820
diff changeset
   195
		qstart and timestamp(qstart) or "",
a67b4d4f8eef mod_muc_mam: Merge main and RSM-specific log message into a single one
Kim Alvefur <zash@zash.se>
parents: 11820
diff changeset
   196
		qend and timestamp(qend) or "",
a67b4d4f8eef mod_muc_mam: Merge main and RSM-specific log message into a single one
Kim Alvefur <zash@zash.se>
parents: 11820
diff changeset
   197
		qset);
a67b4d4f8eef mod_muc_mam: Merge main and RSM-specific log message into a single one
Kim Alvefur <zash@zash.se>
parents: 11820
diff changeset
   198
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   199
	-- Load all the data!
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   200
	local data, err = archive:find(room_node, {
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   201
		start = qstart; ["end"] = qend; -- Time range
12861
cc86d77481fc mod_mam,mod_muc_mam: Minimize differences (reorder, copy some comments)
Kim Alvefur <zash@zash.se>
parents: 11993
diff changeset
   202
		with = "message<groupchat";
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   203
		limit = qmax + 1;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   204
		before = before; after = after;
11286
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   205
		ids = qids;
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   206
		reverse = reverse;
12863
cd738fb8c754 mod_muc_mam: Copy "include total" behavior from mod_mam
Kim Alvefur <zash@zash.se>
parents: 12862
diff changeset
   207
		total = use_total or qmax == 0;
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   208
	});
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   209
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   210
	if not data then
10419
360d574517b6 mod_muc_mam: Copy debug log improvements from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10123
diff changeset
   211
		module:log("debug", "Archive query id=%s failed: %s", qid or stanza.attr.id, err);
10026
b56654f89cd5 mod_muc_mam: Propagate item-not-found to client (fixes #1325)
Kim Alvefur <zash@zash.se>
parents: 10004
diff changeset
   212
		if err == "item-not-found" then
b56654f89cd5 mod_muc_mam: Propagate item-not-found to client (fixes #1325)
Kim Alvefur <zash@zash.se>
parents: 10004
diff changeset
   213
			origin.send(st.error_reply(stanza, "modify", "item-not-found"));
b56654f89cd5 mod_muc_mam: Propagate item-not-found to client (fixes #1325)
Kim Alvefur <zash@zash.se>
parents: 10004
diff changeset
   214
		else
b56654f89cd5 mod_muc_mam: Propagate item-not-found to client (fixes #1325)
Kim Alvefur <zash@zash.se>
parents: 10004
diff changeset
   215
			origin.send(st.error_reply(stanza, "cancel", "internal-server-error"));
b56654f89cd5 mod_muc_mam: Propagate item-not-found to client (fixes #1325)
Kim Alvefur <zash@zash.se>
parents: 10004
diff changeset
   216
		end
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   217
		return true;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   218
	end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   219
	local total = tonumber(err);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   220
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   221
	local msg_reply_attr = { to = stanza.attr.from, from = stanza.attr.to };
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   222
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   223
	local results = {};
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   224
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   225
	-- Wrap it in stuff and deliver
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   226
	local first, last;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   227
	local count = 0;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   228
	local complete = "true";
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   229
	for id, item, when in data do
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   230
		count = count + 1;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   231
		if count > qmax then
12861
cc86d77481fc mod_mam,mod_muc_mam: Minimize differences (reorder, copy some comments)
Kim Alvefur <zash@zash.se>
parents: 11993
diff changeset
   232
			-- We requested qmax+1 items. If that many items are retrieved then
cc86d77481fc mod_mam,mod_muc_mam: Minimize differences (reorder, copy some comments)
Kim Alvefur <zash@zash.se>
parents: 11993
diff changeset
   233
			-- there are more results to page through, so:
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   234
			complete = nil;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   235
			break;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   236
		end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   237
		local fwd_st = st.message(msg_reply_attr)
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   238
			:tag("result", { xmlns = xmlns_mam, queryid = qid, id = id })
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   239
				:tag("forwarded", { xmlns = xmlns_forward })
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   240
					:tag("delay", { xmlns = xmlns_delay, stamp = timestamp(when) }):up();
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   241
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   242
		-- Strip <x> tag, containing the original senders JID, unless the room makes this public
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   243
		if room:get_whois() ~= "anyone" then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   244
			item:maptags(function (tag)
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   245
				if tag.name == "x" and tag.attr.xmlns == xmlns_muc_user then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   246
					return nil;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   247
				end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   248
				return tag;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   249
			end);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   250
		end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   251
		if not is_stanza(item) then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   252
			item = st.deserialize(item);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   253
		end
9845
a44f562e01a5 mod_muc_mam: Strip the stanza 'to' attribute (fixes #1259)
Kim Alvefur <zash@zash.se>
parents: 9555
diff changeset
   254
		item.attr.to = nil;
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   255
		item.attr.xmlns = "jabber:client";
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   256
		fwd_st:add_child(item);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   257
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   258
		if not first then first = id; end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   259
		last = id;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   260
11286
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   261
		if flip then
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   262
			results[count] = fwd_st;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   263
		else
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   264
			origin.send(fwd_st);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   265
		end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   266
	end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   267
11286
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   268
	if flip then
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   269
		for i = #results, 1, -1 do
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   270
			origin.send(results[i]);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   271
		end
11286
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   272
	end
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   273
	if reverse then
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   274
		first, last = last, first;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   275
	end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   276
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   277
	origin.send(st.reply(stanza)
11748
5f99aa6bb76d mod_muc_mam: Omit queryid attribute from <fin/>
Holger Weiss <holger@zedat.fu-berlin.de>
parents: 11286
diff changeset
   278
		:tag("fin", { xmlns = xmlns_mam, complete = complete })
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   279
			:add_child(rsm.generate {
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   280
				first = first, last = last, count = total }));
10419
360d574517b6 mod_muc_mam: Copy debug log improvements from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10123
diff changeset
   281
360d574517b6 mod_muc_mam: Copy debug log improvements from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10123
diff changeset
   282
	-- That's all folks!
360d574517b6 mod_muc_mam: Copy debug log improvements from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10123
diff changeset
   283
	module:log("debug", "Archive query id=%s completed, %d items returned", qid or stanza.attr.id, complete and count or count - 1);
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   284
	return true;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   285
end);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   286
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   287
module:hook("muc-get-history", function (event)
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   288
	local room = event.room;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   289
	if not archiving_enabled(room) then return end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   290
	local room_jid = room.jid;
8786
79133eca0656 mod_muc_mam: Tweak calculation of max history to retrieve
Kim Alvefur <zash@zash.se>
parents: 8728
diff changeset
   291
	local maxstanzas = event.maxstanzas;
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   292
	local maxchars = event.maxchars;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   293
	local since = event.since;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   294
	local to = event.to;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   295
8787
64b78e3deb96 mod_muc_mam: Skip fetching history if no history was requested
Kim Alvefur <zash@zash.se>
parents: 8786
diff changeset
   296
	if maxstanzas == 0 or maxchars == 0 then
64b78e3deb96 mod_muc_mam: Skip fetching history if no history was requested
Kim Alvefur <zash@zash.se>
parents: 8786
diff changeset
   297
		return -- No history requested
64b78e3deb96 mod_muc_mam: Skip fetching history if no history was requested
Kim Alvefur <zash@zash.se>
parents: 8786
diff changeset
   298
	end
64b78e3deb96 mod_muc_mam: Skip fetching history if no history was requested
Kim Alvefur <zash@zash.se>
parents: 8786
diff changeset
   299
8786
79133eca0656 mod_muc_mam: Tweak calculation of max history to retrieve
Kim Alvefur <zash@zash.se>
parents: 8728
diff changeset
   300
	if not maxstanzas or maxstanzas > get_historylength(room) then
79133eca0656 mod_muc_mam: Tweak calculation of max history to retrieve
Kim Alvefur <zash@zash.se>
parents: 8728
diff changeset
   301
		maxstanzas = get_historylength(room);
79133eca0656 mod_muc_mam: Tweak calculation of max history to retrieve
Kim Alvefur <zash@zash.se>
parents: 8728
diff changeset
   302
	end
79133eca0656 mod_muc_mam: Tweak calculation of max history to retrieve
Kim Alvefur <zash@zash.se>
parents: 8728
diff changeset
   303
8788
82b889608503 mod_muc_mam: Skip fetching history if built-in recent history is enough
Kim Alvefur <zash@zash.se>
parents: 8787
diff changeset
   304
	if room._history and #room._history >= maxstanzas then
82b889608503 mod_muc_mam: Skip fetching history if built-in recent history is enough
Kim Alvefur <zash@zash.se>
parents: 8787
diff changeset
   305
		return -- It can deal with this itself
82b889608503 mod_muc_mam: Skip fetching history if built-in recent history is enough
Kim Alvefur <zash@zash.se>
parents: 8787
diff changeset
   306
	end
82b889608503 mod_muc_mam: Skip fetching history if built-in recent history is enough
Kim Alvefur <zash@zash.se>
parents: 8787
diff changeset
   307
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   308
	-- Load all the data!
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   309
	local query = {
8786
79133eca0656 mod_muc_mam: Tweak calculation of max history to retrieve
Kim Alvefur <zash@zash.se>
parents: 8728
diff changeset
   310
		limit = maxstanzas;
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   311
		start = since;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   312
		reverse = true;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   313
		with = "message<groupchat";
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   314
	}
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   315
	local data, err = archive:find(jid_split(room_jid), query);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   316
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   317
	if not data then
10115
0f335815244f plugins: Remove tostring call from logging
Kim Alvefur <zash@zash.se>
parents: 10034
diff changeset
   318
		module:log("error", "Could not fetch history: %s", err);
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   319
		return
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   320
	end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   321
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   322
	local history, i = {}, 1;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   323
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   324
	for id, item, when in data do
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   325
		item.attr.to = to;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   326
		item:tag("delay", { xmlns = "urn:xmpp:delay", from = room_jid, stamp = timestamp(when) }):up(); -- XEP-0203
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   327
		item:tag("stanza-id", { xmlns = xmlns_st_id, by = room_jid, id = id }):up();
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   328
		if room:get_whois() ~= "anyone" then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   329
			item:maptags(function (tag)
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   330
				if tag.name == "x" and tag.attr.xmlns == xmlns_muc_user then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   331
					return nil;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   332
				end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   333
				return tag;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   334
			end);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   335
		end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   336
		if maxchars then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   337
			local chars = #tostring(item);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   338
			if maxchars - chars < 0 then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   339
				break
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   340
			end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   341
			maxchars = maxchars - chars;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   342
		end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   343
		history[i], i = item, i+1;
10115
0f335815244f plugins: Remove tostring call from logging
Kim Alvefur <zash@zash.se>
parents: 10034
diff changeset
   344
		-- module:log("debug", item);
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   345
	end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   346
	function event.next_stanza()
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   347
		i = i - 1;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   348
		return history[i];
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   349
	end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   350
	return true;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   351
end, 1);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   352
10818
e042b0c8b310 mod_muc_mam: Fix stanza id filter event name, fixes #1546
Kim Alvefur <zash@zash.se>
parents: 10686
diff changeset
   353
module:hook("muc-broadcast-message", function (event)
8789
adffadd88ff0 mod_muc_mam: Have stanza-id filtering over all groupchat messages, not just ones considered for history
Kim Alvefur <zash@zash.se>
parents: 8788
diff changeset
   354
	local room, stanza = event.room, event.stanza;
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   355
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   356
	-- Filter out <stanza-id> that claim to be from us
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   357
	stanza:maptags(function (tag)
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   358
		if tag.name == "stanza-id" and tag.attr.xmlns == xmlns_st_id
8789
adffadd88ff0 mod_muc_mam: Have stanza-id filtering over all groupchat messages, not just ones considered for history
Kim Alvefur <zash@zash.se>
parents: 8788
diff changeset
   359
		and jid_prep(tag.attr.by) == room.jid then
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   360
			return nil;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   361
		end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   362
		return tag;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   363
	end);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   364
10838
c6e852984d48 mod_muc_mam: Remove spoofed archive IDs before archiving, fix #1552
Kim Alvefur <zash@zash.se>
parents: 10819
diff changeset
   365
end, 1);
8789
adffadd88ff0 mod_muc_mam: Have stanza-id filtering over all groupchat messages, not just ones considered for history
Kim Alvefur <zash@zash.se>
parents: 8788
diff changeset
   366
adffadd88ff0 mod_muc_mam: Have stanza-id filtering over all groupchat messages, not just ones considered for history
Kim Alvefur <zash@zash.se>
parents: 8788
diff changeset
   367
-- Handle messages
adffadd88ff0 mod_muc_mam: Have stanza-id filtering over all groupchat messages, not just ones considered for history
Kim Alvefur <zash@zash.se>
parents: 8788
diff changeset
   368
local function save_to_history(self, stanza)
10564
3adb6c46fbf4 mod_muc_mam: Remove unused variable [luacheck]
Kim Alvefur <zash@zash.se>
parents: 10562
diff changeset
   369
	local room_node = jid_split(self.jid);
8789
adffadd88ff0 mod_muc_mam: Have stanza-id filtering over all groupchat messages, not just ones considered for history
Kim Alvefur <zash@zash.se>
parents: 8788
diff changeset
   370
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   371
	local stored_stanza = stanza;
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   372
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   373
	if stanza.name == "message" and self:get_whois() == "anyone" then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   374
		stored_stanza = st.clone(stanza);
9845
a44f562e01a5 mod_muc_mam: Strip the stanza 'to' attribute (fixes #1259)
Kim Alvefur <zash@zash.se>
parents: 9555
diff changeset
   375
		stored_stanza.attr.to = nil;
10674
5376f882cf82 mod_muc_mam: Fix traceback saving message from non-occupant (fixes #1497)
Kim Alvefur <zash@zash.se>
parents: 10570
diff changeset
   376
		local occupant = self._occupants[stanza.attr.from];
5376f882cf82 mod_muc_mam: Fix traceback saving message from non-occupant (fixes #1497)
Kim Alvefur <zash@zash.se>
parents: 10570
diff changeset
   377
		if occupant then
5376f882cf82 mod_muc_mam: Fix traceback saving message from non-occupant (fixes #1497)
Kim Alvefur <zash@zash.se>
parents: 10570
diff changeset
   378
			local actor = jid_bare(occupant.jid);
5376f882cf82 mod_muc_mam: Fix traceback saving message from non-occupant (fixes #1497)
Kim Alvefur <zash@zash.se>
parents: 10570
diff changeset
   379
			local affiliation = self:get_affiliation(actor) or "none";
5376f882cf82 mod_muc_mam: Fix traceback saving message from non-occupant (fixes #1497)
Kim Alvefur <zash@zash.se>
parents: 10570
diff changeset
   380
			local role = self:get_role(actor) or self:get_default_role(affiliation);
5376f882cf82 mod_muc_mam: Fix traceback saving message from non-occupant (fixes #1497)
Kim Alvefur <zash@zash.se>
parents: 10570
diff changeset
   381
			stored_stanza:add_direct_child(st.stanza("x", { xmlns = xmlns_muc_user })
5376f882cf82 mod_muc_mam: Fix traceback saving message from non-occupant (fixes #1497)
Kim Alvefur <zash@zash.se>
parents: 10570
diff changeset
   382
				:tag("item", { affiliation = affiliation; role = role; jid = actor }));
5376f882cf82 mod_muc_mam: Fix traceback saving message from non-occupant (fixes #1497)
Kim Alvefur <zash@zash.se>
parents: 10570
diff changeset
   383
		end
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   384
	end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   385
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   386
	-- Policy check
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   387
	if not archiving_enabled(self) then return end -- Don't log
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   388
9847
17060708d0eb mod_muc_mam: Add comment about the tricks done with the 'with' field
Kim Alvefur <zash@zash.se>
parents: 9846
diff changeset
   389
	-- Save the type in the 'with' field, allows storing presence without conflicts
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   390
	local with = stanza.name
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   391
	if stanza.attr.type then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   392
		with = with .. "<" .. stanza.attr.type
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   393
	end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   394
9846
6f39be2e0be5 mod_muc_mam: Move a comment to the line it describes
Kim Alvefur <zash@zash.se>
parents: 9845
diff changeset
   395
	-- And stash it
10004
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   396
	local time = time_now();
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   397
	local id, err = archive:append(room_node, nil, stored_stanza, time, with);
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   398
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   399
	if not id and err == "quota-limit" then
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   400
		if type(cleanup_after) == "number" then
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   401
			module:log("debug", "Room '%s' over quota, cleaning archive", room_node);
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   402
			local cleaned = archive:delete(room_node, {
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   403
				["end"] = (os.time() - cleanup_after);
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   404
			});
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   405
			if cleaned then
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   406
				id, err = archive:append(room_node, nil, stored_stanza, time, with);
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   407
			end
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   408
		end
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   409
		if not id and (archive.caps and archive.caps.truncate) then
11822
c443abff04d8 mod_muc_mam: Fix reference to "user" in debug message copied from mod_mam
Kim Alvefur <zash@zash.se>
parents: 11821
diff changeset
   410
			module:log("debug", "Room '%s' over quota, truncating archive", room_node);
10004
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   411
			local truncated = archive:delete(room_node, {
10804
62794e065e33 MAM: Remove 1% of contents when reaching limits, fix #1545
Kim Alvefur <zash@zash.se>
parents: 10687
diff changeset
   412
				truncate = archive_truncate;
10004
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   413
			});
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   414
			if truncated then
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   415
				id, err = archive:append(room_node, nil, stored_stanza, time, with);
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   416
			end
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   417
		end
189b00a782bf mod_muc_mam: Handle archive quotas
Kim Alvefur <zash@zash.se>
parents: 9886
diff changeset
   418
	end
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   419
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   420
	if id then
9884
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   421
		schedule_cleanup(room_node);
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   422
		stanza:add_direct_child(st.stanza("stanza-id", { xmlns = xmlns_st_id, by = self.jid, id = id }));
10530
28c8e09fb3cd mod_muc_mam: Log error when unable to store stanza (fix #1480) [luacheck]
Kim Alvefur <zash@zash.se>
parents: 10033
diff changeset
   423
	else
28c8e09fb3cd mod_muc_mam: Log error when unable to store stanza (fix #1480) [luacheck]
Kim Alvefur <zash@zash.se>
parents: 10033
diff changeset
   424
		module:log("error", "Could not archive stanza: %s", err);
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   425
	end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   426
end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   427
8727
cfcc78c50905 mod_muc_mam: Let muc/history.lib decide which messages to store
Kim Alvefur <zash@zash.se>
parents: 8726
diff changeset
   428
module:hook("muc-add-history", function (event)
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   429
	local room, stanza = event.room, event.stanza;
8727
cfcc78c50905 mod_muc_mam: Let muc/history.lib decide which messages to store
Kim Alvefur <zash@zash.se>
parents: 8726
diff changeset
   430
	save_to_history(room, stanza);
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   431
end);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   432
9004
23070882f3d4 mod_muc_mam: Disable presence logging by default
Kim Alvefur <zash@zash.se>
parents: 8835
diff changeset
   433
if module:get_option_boolean("muc_log_presences", false) then
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   434
	module:hook("muc-occupant-joined", function (event)
8728
ced09d7d7c96 mod_muc_mam: Save the MUC <x> on recorded join stanzas
Kim Alvefur <zash@zash.se>
parents: 8727
diff changeset
   435
		save_to_history(event.room, st.stanza("presence", { from = event.nick }):tag("x", { xmlns = "http://jabber.org/protocol/muc" }));
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   436
	end);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   437
	module:hook("muc-occupant-left", function (event)
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   438
		save_to_history(event.room, st.stanza("presence", { type = "unavailable", from = event.nick }));
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   439
	end);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   440
end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   441
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   442
if not archive.delete then
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   443
	module:log("warn", "Storage driver %s does not support deletion", archive._provided_by);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   444
	module:log("warn", "Archived message will persist after a room has been destroyed");
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   445
else
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   446
	module:hook("muc-room-destroyed", function(event)
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   447
		local room_node = jid_split(event.room.jid);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   448
		archive:delete(room_node);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   449
	end);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   450
end
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   451
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   452
-- And role/affiliation changes?
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   453
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   454
module:add_feature(xmlns_mam);
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   455
11286
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   456
local advertise_extended = archive.caps and archive.caps.full_id_range and archive.caps.ids;
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   457
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   458
module:hook("muc-disco#info", function(event)
10123
29733134c76c mod_muc_mam: Conditionally advertise MAM feature on rooms (fixes #1407)
Kim Alvefur <zash@zash.se>
parents: 10115
diff changeset
   459
	if archiving_enabled(event.room) then
29733134c76c mod_muc_mam: Conditionally advertise MAM feature on rooms (fixes #1407)
Kim Alvefur <zash@zash.se>
parents: 10115
diff changeset
   460
		event.reply:tag("feature", {var=xmlns_mam}):up();
11286
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   461
		if advertise_extended then
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   462
			(event.reply or event.stanza):tag("feature", {var=xmlns_mam_ext}):up();
cabb022f31c0 mod_muc_mam: Copy extended MAM support from mod_mam
Kim Alvefur <zash@zash.se>
parents: 10948
diff changeset
   463
		end
10123
29733134c76c mod_muc_mam: Conditionally advertise MAM feature on rooms (fixes #1407)
Kim Alvefur <zash@zash.se>
parents: 10115
diff changeset
   464
	end
10819
c432b7172fa3 mod_muc_mam: Fix missing advertising of XEP-0359, fixes #1547
Kim Alvefur <zash@zash.se>
parents: 10818
diff changeset
   465
	event.reply:tag("feature", {var=xmlns_st_id}):up();
8725
7ee93b3fa160 mod_muc_mam: Import mod_mam_muc from prosody-modules ba6466fa6823
Kim Alvefur <zash@zash.se>
parents:
diff changeset
   466
end);
9884
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   467
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   468
-- Cleanup
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   469
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   470
if cleanup_after ~= "never" then
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   471
	local cleanup_storage = module:open_store("muc_log_cleanup");
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   472
	local cleanup_map = module:open_store("muc_log_cleanup", "map");
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   473
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   474
	local day = 86400;
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   475
	local multipliers = { d = day, w = day * 7, m = 31 * day, y = 365.2425 * day };
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   476
	local n, m = cleanup_after:lower():match("(%d+)%s*([dwmy]?)");
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   477
	if not n then
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   478
		module:log("error", "Could not parse muc_log_expires_after string %q", cleanup_after);
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   479
		return false;
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   480
	end
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   481
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   482
	cleanup_after = tonumber(n) * ( multipliers[m] or 1 );
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   483
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   484
	module:log("debug", "muc_log_expires_after = %d -- in seconds", cleanup_after);
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   485
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   486
	if not archive.delete then
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   487
		module:log("error", "muc_log_expires_after set but mod_%s does not support deleting", archive._provided_by);
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   488
		return false;
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   489
	end
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   490
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   491
	-- For each day, store a set of rooms that have new messages. To expire
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   492
	-- messages, we collect the union of sets of rooms from dates that fall
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   493
	-- outside the cleanup range.
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   494
10033
2c8f674b9243 mod_muc_mam: Cache last date that archive owner has messages to reduce writes (fixes #1368)
Kim Alvefur <zash@zash.se>
parents: 9884
diff changeset
   495
	local last_date = require "util.cache".new(module:get_option_number("muc_log_cleanup_date_cache_size", 1000));
11972
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   496
	if not ( archive.caps and archive.caps.wildcard_delete ) then
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   497
		function schedule_cleanup(roomname, date)
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   498
			date = date or datestamp();
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   499
			if last_date:get(roomname) == date then return end
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   500
			local ok = cleanup_map:set(date, roomname, true);
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   501
			if ok then
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   502
				last_date:set(roomname, date);
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   503
			end
10033
2c8f674b9243 mod_muc_mam: Cache last date that archive owner has messages to reduce writes (fixes #1368)
Kim Alvefur <zash@zash.se>
parents: 9884
diff changeset
   504
		end
9884
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   505
	end
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   506
10589
2d8535338099 mod_muc_mam: Measure how long a cleanup run takes (like mod_mam)
Kim Alvefur <zash@zash.se>
parents: 10572
diff changeset
   507
	local cleanup_time = module:measure("cleanup", "times");
2d8535338099 mod_muc_mam: Measure how long a cleanup run takes (like mod_mam)
Kim Alvefur <zash@zash.se>
parents: 10572
diff changeset
   508
10686
62ef68f95b6f mod_mam,mod_muc_mam: Allow other work to be performed during archive cleanup (fixes #1504)
Kim Alvefur <zash@zash.se>
parents: 10674
diff changeset
   509
	local async = require "util.async";
11993
871100cdbbad mod_muc_mam: Switch to mod_cron for message expiry
Kim Alvefur <zash@zash.se>
parents: 11972
diff changeset
   510
	module:daily("Remove expired messages", function ()
10589
2d8535338099 mod_muc_mam: Measure how long a cleanup run takes (like mod_mam)
Kim Alvefur <zash@zash.se>
parents: 10572
diff changeset
   511
		local cleanup_done = cleanup_time();
11972
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   512
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   513
		if archive.caps and archive.caps.wildcard_delete then
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   514
			local ok, err = archive:delete(true, { ["end"] = os.time() - cleanup_after })
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   515
			if ok then
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   516
				local sum = tonumber(ok);
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   517
				if sum then
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   518
					module:log("info", "Deleted %d expired messages", sum);
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   519
				else
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   520
					-- driver did not tell
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   521
					module:log("info", "Deleted all expired messages");
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   522
				end
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   523
			else
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   524
				module:log("error", "Could not delete messages: %s", err);
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   525
			end
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   526
			cleanup_done();
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   527
			return;
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   528
		end
6e1af07921d1 mod_mam,mod_muc_mam: Simplify deletion when multi-user-deletion is supported
Kim Alvefur <zash@zash.se>
parents: 11880
diff changeset
   529
9884
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   530
		local rooms = {};
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   531
		local cut_off = datestamp(os.time() - cleanup_after);
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   532
		for date in cleanup_storage:users() do
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   533
			if date <= cut_off then
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   534
				module:log("debug", "Messages from %q should be expired", date);
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   535
				local messages_this_day = cleanup_storage:get(date);
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   536
				if messages_this_day then
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   537
					for room in pairs(messages_this_day) do
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   538
						rooms[room] = true;
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   539
					end
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   540
					if date < cut_off then
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   541
						-- Messages from the same day as the cut-off might not have expired yet,
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   542
						-- but all earlier will have, so clear storage for those days.
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   543
						cleanup_storage:set(date, nil);
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   544
					end
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   545
				end
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   546
			end
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   547
		end
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   548
		local sum, num_rooms = 0, 0;
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   549
		for room in pairs(rooms) do
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   550
			local ok, err = archive:delete(room, { ["end"] = os.time() - cleanup_after; })
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   551
			if ok then
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   552
				num_rooms = num_rooms + 1;
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   553
				sum = sum + (tonumber(ok) or 0);
10565
29b3eb95c268 mod_muc_mam: Log error when unable to delete old messages (fix #1481) [luacheck]
Kim Alvefur <zash@zash.se>
parents: 10530
diff changeset
   554
			else
10566
670afc079f68 mod_muc_mam: Schedule cleanup again on failure
Kim Alvefur <zash@zash.se>
parents: 10565
diff changeset
   555
				cleanup_map:set(cut_off, room, true);
10565
29b3eb95c268 mod_muc_mam: Log error when unable to delete old messages (fix #1481) [luacheck]
Kim Alvefur <zash@zash.se>
parents: 10530
diff changeset
   556
				module:log("error", "Could not delete messages for room '%s': %s", room, err);
9884
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   557
			end
10686
62ef68f95b6f mod_mam,mod_muc_mam: Allow other work to be performed during archive cleanup (fixes #1504)
Kim Alvefur <zash@zash.se>
parents: 10674
diff changeset
   558
			local wait, done = async.waiter();
62ef68f95b6f mod_mam,mod_muc_mam: Allow other work to be performed during archive cleanup (fixes #1504)
Kim Alvefur <zash@zash.se>
parents: 10674
diff changeset
   559
			module:add_timer(0.01, done);
62ef68f95b6f mod_mam,mod_muc_mam: Allow other work to be performed during archive cleanup (fixes #1504)
Kim Alvefur <zash@zash.se>
parents: 10674
diff changeset
   560
			wait();
9884
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   561
		end
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   562
		module:log("info", "Deleted %d expired messages for %d rooms", sum, num_rooms);
10589
2d8535338099 mod_muc_mam: Measure how long a cleanup run takes (like mod_mam)
Kim Alvefur <zash@zash.se>
parents: 10572
diff changeset
   563
		cleanup_done();
9884
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   564
	end);
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   565
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   566
else
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   567
	module:log("debug", "Archive expiry disabled");
12863
cd738fb8c754 mod_muc_mam: Copy "include total" behavior from mod_mam
Kim Alvefur <zash@zash.se>
parents: 12862
diff changeset
   568
	-- Don't ask the backend to count the potentially unbounded number of items,
cd738fb8c754 mod_muc_mam: Copy "include total" behavior from mod_mam
Kim Alvefur <zash@zash.se>
parents: 12862
diff changeset
   569
	-- it'll get slow.
cd738fb8c754 mod_muc_mam: Copy "include total" behavior from mod_mam
Kim Alvefur <zash@zash.se>
parents: 12862
diff changeset
   570
	use_total = module:get_option_boolean("mam_include_total", false);
9884
78885b1bbb91 mod_muc_mam: Copy cleanup mechanism from mod_mam (fixes #672)
Kim Alvefur <zash@zash.se>
parents: 9847
diff changeset
   571
end