Mercurial > prosody-modules
changeset 5002:84997bc3f92e
mod_firewall: Update for role-auth (backwards compatible)
Probably worth investigating mod_compat_roles in the future.
author | Matthew Wild <mwild1@gmail.com> |
---|---|
date | Thu, 11 Aug 2022 17:04:53 +0100 (2022-08-11) |
parents | cb19cb1c03d6 |
children | e840aadebb61 |
files | mod_firewall/README.markdown mod_firewall/conditions.lib.lua mod_firewall/mod_firewall.lua |
diffstat | 3 files changed, 54 insertions(+), 1 deletions(-) [+] |
line wrap: on
line diff
--- a/mod_firewall/README.markdown Wed Jul 13 11:27:44 2022 +0100 +++ b/mod_firewall/README.markdown Thu Aug 11 17:04:53 2022 +0100 @@ -435,8 +435,40 @@ NOT SENT DIRECTED PRESENCE TO SENDER? BOUNCE=service-unavailable +### Permissions + +Rules can consult Prosody's internal role and permissions system to check whether a certain action may +be performed. The acting entity, their role, and appropriate context is automatically inferred. All you +need to do is provide the identifier of the permission that should be checked. + + Condition Description + ----------------------- -------------------------------------------------------------------- + `MAY=permission` Checks whether 'permission' is allowed in the current context. + +As with all other conditions, `MAY` can be combined with `NOT` to negate the result of the check. + +Example, blocking outgoing stanzas from users with roles that do not allow the 'xmpp:federate' permission: + +``` +::deliver_remote +MAY NOT: xmpp:federate +BOUNCE=policy-violation (You are not allowed access to the federation) +``` + +### Roles + + Condition Matches + ---------------- ------------------------------------------------------------------------------------- + `TO ROLE` When the recipient JID of the stanza has the named role + `FROM ROLE` When the sender JID of the stanza has the named role + +**Note:** In most cases, you should avoid checking for specific roles, and instead check for +permissions granted by those roles (using the 'MAY' condition). + ### Admins +**Deprecated:** These conditions should no longer be used. Prefer 'MAY', 'TO ROLE' or 'FROM ROLE'. + Prosody allows certain JIDs to be declared as administrators of a host, component or the whole server. Condition Matches
--- a/mod_firewall/conditions.lib.lua Wed Jul 13 11:27:44 2022 +0100 +++ b/mod_firewall/conditions.lib.lua Thu Aug 11 17:04:53 2022 +0100 @@ -175,22 +175,39 @@ return "not "..table.concat(code, " or "), { "group_contains", "bare_to", "bare_from" }; end +-- COMPAT w/0.12: Deprecated function condition_handlers.FROM_ADMIN_OF(host) return ("is_admin(bare_from, %s)"):format(host ~= "*" and metaq(host) or nil), { "is_admin", "bare_from" }; end +-- COMPAT w/0.12: Deprecated function condition_handlers.TO_ADMIN_OF(host) return ("is_admin(bare_to, %s)"):format(host ~= "*" and metaq(host) or nil), { "is_admin", "bare_to" }; end +-- COMPAT w/0.12: Deprecated function condition_handlers.FROM_ADMIN() return ("is_admin(bare_from, current_host)"), { "is_admin", "bare_from", "current_host" }; end +-- COMPAT w/0.12: Deprecated function condition_handlers.TO_ADMIN() return ("is_admin(bare_to, current_host)"), { "is_admin", "bare_to", "current_host" }; end +-- MAY: permission_to_check +function condition_handlers.MAY(permission_to_check) + return ("module:may(%q, event)"):format(permission_to_check); +end + +function condition_handlers.TO_ROLE(role_name) + return ("get_jid_role(bare_to, current_host) == %q"):format(role_name), { "get_jid_role", "current_host", "bare_to" }; +end + +function condition_handlers.FROM_ROLE(role_name) + return ("get_jid_role(bare_from, current_host) == %q"):format(role_name), { "get_jid_role", "current_host", "bare_from" }; +end + local day_numbers = { sun = 0, mon = 2, tue = 3, wed = 4, thu = 5, fri = 6, sat = 7 }; local function current_time_check(op, hour, minute)
--- a/mod_firewall/mod_firewall.lua Wed Jul 13 11:27:44 2022 +0100 +++ b/mod_firewall/mod_firewall.lua Thu Aug 11 17:04:53 2022 +0100 @@ -6,6 +6,9 @@ local it = require "util.iterators"; local set = require "util.set"; +local have_features, features = pcall(require, "core.features"); +features = have_features and features.available or set.new(); + -- [definition_type] = definition_factory(param) local definitions = module:shared("definitions"); @@ -181,7 +184,8 @@ group_contains = { global_code = [[local group_contains = module:depends("groups").group_contains]]; }; - is_admin = { global_code = [[local is_admin = require "core.usermanager".is_admin;]]}; + is_admin = features:contains("permissions") and { global_code = [[local is_admin = require "core.usermanager".is_admin;]]} or nil; + get_jid_role = require "core.usermanager".get_jid_role and { global_code = [[local get_jid_role = require "core.usermanager".get_jid_role;]] } or nil; core_post_stanza = { global_code = [[local core_post_stanza = prosody.core_post_stanza;]] }; zone = { global_code = function (zone) local var = zone;