# HG changeset patch # User Matthew Wild # Date 1488544275 0 # Node ID 1e1c929c1aa5235d8ae162e6e9777d9f75a58b1f # Parent b61b0ff1c0f9e08a4fd68b1d9f6b3182b4116e8c mod_firewall: Add and document CROSSING GROUPS condition diff -r b61b0ff1c0f9 -r 1e1c929c1aa5 mod_firewall/README.markdown --- a/mod_firewall/README.markdown Wed Mar 01 20:34:17 2017 +0100 +++ b/mod_firewall/README.markdown Fri Mar 03 12:31:15 2017 +0000 @@ -317,10 +317,33 @@ Using Prosody's mod\_groups it is possible to define groups of users on the server. You can match based on these groups in firewall rules. - Condition Matches - ------------- ---------------------------- - `FROM GROUP` When the stanza is being sent from a member of the named group - `TO GROUP` When the stanza is being sent to a member of the named group + Condition Matches + ----------------- ---------------------------- + `FROM GROUP` When the stanza is being sent from a member of the named group + `TO GROUP` When the stanza is being sent to a member of the named group + `CROSSING GROUPS` When the stanza is being sent between users of different named groups + +#### CROSSING GROUPS + +The `CROSSING GROUPS` condition takes a comma-separated list of groups to check. If the +sender and recipient are not in the same group (only the listed groups are checked), then the +this condition matches and the stanza is deemed to be crossing between groups. + +For example, if you had three groups: Engineering, Marketing and Employees. All users are +members of the 'Employees' group, and the others are for employees of the named department only. + +To prevent employees in the marketing department from communicating with engineers, you could use +the following rule: + +``` +CROSSING GROUPS: Marketing, Engineering +BOUNCE=policy-violation (no communication between these groups is allowed!) +``` + +This works, even though both the users are in the 'Employees' group, because that group is not listed +in the condition. + +In the above example, a user who is member of both groups is not restricted. #### SENT DIRECTED PRESENCE TO SENDER diff -r b61b0ff1c0f9 -r 1e1c929c1aa5 mod_firewall/conditions.lib.lua --- a/mod_firewall/conditions.lib.lua Wed Mar 01 20:34:17 2017 +0100 +++ b/mod_firewall/conditions.lib.lua Fri Mar 03 12:31:15 2017 +0000 @@ -157,6 +157,16 @@ return ("group_contains(%q, bare_to)"):format(group_name), { "group_contains", "bare_to" }; end +function condition_handlers.CROSSING_GROUPS(group_names) + local code = {}; + for group_name in group_names:gmatch("([^, ][^,]+)") do + group_name = group_name:match("^%s*(.-)%s*$"); -- Trim leading/trailing whitespace + -- Just check that's it is crossing from outside group to inside group + table.insert(code, ("(group_contains(%q, bare_to) and group_contains(%q, bare_from))"):format(group_name, group_name)) + end + return "not "..table.concat(code, " or "), { "group_contains", "bare_to", "bare_from" }; +end + 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