plugins/mod_authz_internal.lua
author Matthew Wild <mwild1@gmail.com>
Wed, 27 Mar 2024 15:39:03 +0000
changeset 13470 5d9ec2e55d74
parent 13236 e0ab20519ce5
permissions -rw-r--r--
Merge 0.12->trunk
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
12981
74b9e05af71e plugins: Prefix module imports with prosody namespace
Kim Alvefur <zash@zash.se>
parents: 12929
diff changeset
     1
local array = require "prosody.util.array";
74b9e05af71e plugins: Prefix module imports with prosody namespace
Kim Alvefur <zash@zash.se>
parents: 12929
diff changeset
     2
local it = require "prosody.util.iterators";
74b9e05af71e plugins: Prefix module imports with prosody namespace
Kim Alvefur <zash@zash.se>
parents: 12929
diff changeset
     3
local set = require "prosody.util.set";
74b9e05af71e plugins: Prefix module imports with prosody namespace
Kim Alvefur <zash@zash.se>
parents: 12929
diff changeset
     4
local jid_split, jid_bare, jid_host = import("prosody.util.jid", "split", "bare", "host");
74b9e05af71e plugins: Prefix module imports with prosody namespace
Kim Alvefur <zash@zash.se>
parents: 12929
diff changeset
     5
local normalize = require "prosody.util.jid".prep;
74b9e05af71e plugins: Prefix module imports with prosody namespace
Kim Alvefur <zash@zash.se>
parents: 12929
diff changeset
     6
local roles = require "prosody.util.roles";
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
     7
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
     8
local config_global_admin_jids = module:context("*"):get_option_set("admins", {}) / normalize;
11749
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
     9
local config_admin_jids = module:get_option_inherited_set("admins", {}) / normalize;
10663
8f95308c3c45 usermanager, mod_authz_*: Merge mod_authz_config and mod_authz_internal into the latter
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
    10
local host = module.host;
12734
427dd01f0864 mod_authz_internal: Allow configuring role of local-server/parent-host users
Matthew Wild <mwild1@gmail.com>
parents: 12667
diff changeset
    11
local host_suffix = host:gsub("^[^%.]+%.", "");
427dd01f0864 mod_authz_internal: Allow configuring role of local-server/parent-host users
Matthew Wild <mwild1@gmail.com>
parents: 12667
diff changeset
    12
427dd01f0864 mod_authz_internal: Allow configuring role of local-server/parent-host users
Matthew Wild <mwild1@gmail.com>
parents: 12667
diff changeset
    13
local hosts = prosody.hosts;
13174
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    14
local is_anon_host = module:get_option_string("authentication") == "anonymous";
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    15
local default_user_role = module:get_option_string("default_user_role", is_anon_host and "prosody:guest" or "prosody:registered");
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    16
12734
427dd01f0864 mod_authz_internal: Allow configuring role of local-server/parent-host users
Matthew Wild <mwild1@gmail.com>
parents: 12667
diff changeset
    17
local is_component = hosts[host].type == "component";
12744
f58c6ae5edc1 mod_authz_internal: Fix warning due to global use
Kim Alvefur <zash@zash.se>
parents: 12737
diff changeset
    18
local host_user_role, server_user_role, public_user_role;
12734
427dd01f0864 mod_authz_internal: Allow configuring role of local-server/parent-host users
Matthew Wild <mwild1@gmail.com>
parents: 12667
diff changeset
    19
if is_component then
13174
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    20
	host_user_role = module:get_option_string("host_user_role", "prosody:registered");
12734
427dd01f0864 mod_authz_internal: Allow configuring role of local-server/parent-host users
Matthew Wild <mwild1@gmail.com>
parents: 12667
diff changeset
    21
	server_user_role = module:get_option_string("server_user_role");
12737
2167e1639aab mod_authz_internal: Allow specifying default role for public (remote) users
Matthew Wild <mwild1@gmail.com>
parents: 12734
diff changeset
    22
	public_user_role = module:get_option_string("public_user_role");
12734
427dd01f0864 mod_authz_internal: Allow configuring role of local-server/parent-host users
Matthew Wild <mwild1@gmail.com>
parents: 12667
diff changeset
    23
end
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
    24
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
    25
local role_store = module:open_store("account_roles");
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
    26
local role_map_store = module:open_store("account_roles", "map");
10663
8f95308c3c45 usermanager, mod_authz_*: Merge mod_authz_config and mod_authz_internal into the latter
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
    27
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    28
local role_registry = {};
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
    29
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    30
function register_role(role)
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    31
	if role_registry[role.name] ~= nil then
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    32
		return error("A role '"..role.name.."' is already registered");
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    33
	end
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    34
	if not roles.is_role(role) then
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    35
		-- Convert table syntax to real role object
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    36
		for i, inherited_role in ipairs(role.inherits or {}) do
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    37
			if type(inherited_role) == "string" then
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    38
				role.inherits[i] = assert(role_registry[inherited_role], "The named role '"..inherited_role.."' is not registered");
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    39
			end
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    40
		end
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    41
		if not role.permissions then role.permissions = {}; end
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    42
		for _, allow_permission in ipairs(role.allow or {}) do
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    43
			role.permissions[allow_permission] = true;
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    44
		end
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    45
		for _, deny_permission in ipairs(role.deny or {}) do
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    46
			role.permissions[deny_permission] = false;
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    47
		end
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    48
		role = roles.new(role);
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    49
	end
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    50
	role_registry[role.name] = role;
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    51
end
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    52
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    53
-- Default roles
13174
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    54
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    55
-- For untrusted guest/anonymous users
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    56
register_role {
13174
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    57
	name = "prosody:guest";
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    58
	priority = 15;
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    59
};
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    60
13174
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    61
-- For e.g. self-registered accounts
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    62
register_role {
13174
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    63
	name = "prosody:registered";
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    64
	priority = 25;
13174
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    65
	inherits = { "prosody:guest" };
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
    66
};
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
    67
13174
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    68
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    69
-- For trusted/provisioned accounts
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    70
register_role {
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    71
	name = "prosody:member";
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    72
	priority = 35;
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    73
	inherits = { "prosody:registered" };
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    74
};
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    75
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    76
-- For administrators, e.g. of a host
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    77
register_role {
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    78
	name = "prosody:admin";
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    79
	priority = 50;
13174
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    80
	inherits = { "prosody:member" };
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    81
};
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    82
13174
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
    83
-- For server operators (full access)
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    84
register_role {
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    85
	name = "prosody:operator";
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    86
	priority = 75;
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    87
	inherits = { "prosody:admin" };
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    88
};
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    89
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    90
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    91
-- Process custom roles from config
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    92
13236
e0ab20519ce5 plugins: Use get_option_array for some list shaped options
Kim Alvefur <zash@zash.se>
parents: 13174
diff changeset
    93
local custom_roles = module:get_option_array("custom_roles", {});
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    94
for n, role_config in ipairs(custom_roles) do
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    95
	local ok, err = pcall(register_role, role_config);
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    96
	if not ok then
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
    97
		module:log("error", "Error registering custom role %s: %s", role_config.name or tostring(n), err);
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
    98
	end
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
    99
end
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   100
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   101
-- Process custom permissions from config
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   102
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   103
local config_add_perms = module:get_option("add_permissions", {});
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   104
local config_remove_perms = module:get_option("remove_permissions", {});
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   105
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   106
for role_name, added_permissions in pairs(config_add_perms) do
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   107
	if not role_registry[role_name] then
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   108
		module:log("error", "Cannot add permissions to unknown role '%s'", role_name);
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   109
	else
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   110
		for _, permission in ipairs(added_permissions) do
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   111
			role_registry[role_name]:set_permission(permission, true, true);
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   112
		end
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   113
	end
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   114
end
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   115
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   116
for role_name, removed_permissions in pairs(config_remove_perms) do
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   117
	if not role_registry[role_name] then
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   118
		module:log("error", "Cannot remove permissions from unknown role '%s'", role_name);
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   119
	else
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   120
		for _, permission in ipairs(removed_permissions) do
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   121
			role_registry[role_name]:set_permission(permission, false, true);
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   122
		end
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   123
	end
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   124
end
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   125
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   126
-- Public API
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   127
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   128
-- Get the primary role of a user
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   129
function get_user_role(user)
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   130
	local bare_jid = user.."@"..host;
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   131
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   132
	-- Check config first
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   133
	if config_global_admin_jids:contains(bare_jid) then
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   134
		return role_registry["prosody:operator"];
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   135
	elseif config_admin_jids:contains(bare_jid) then
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   136
		return role_registry["prosody:admin"];
10663
8f95308c3c45 usermanager, mod_authz_*: Merge mod_authz_config and mod_authz_internal into the latter
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
   137
	end
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   138
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   139
	-- Check storage
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   140
	local stored_roles, err = role_store:get(user);
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   141
	if not stored_roles then
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   142
		if err then
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   143
			-- Unable to fetch role, fail
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   144
			return nil, err;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   145
		end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   146
		-- No role set, use default role
13174
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
   147
		return role_registry[default_user_role];
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   148
	end
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   149
	if stored_roles._default == nil then
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   150
		-- No primary role explicitly set, return default
13174
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
   151
		return role_registry[default_user_role];
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   152
	end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   153
	local primary_stored_role = role_registry[stored_roles._default];
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   154
	if not primary_stored_role then
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   155
		return nil, "unknown-role";
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   156
	end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   157
	return primary_stored_role;
10663
8f95308c3c45 usermanager, mod_authz_*: Merge mod_authz_config and mod_authz_internal into the latter
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
   158
end
8f95308c3c45 usermanager, mod_authz_*: Merge mod_authz_config and mod_authz_internal into the latter
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
   159
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   160
-- Set the primary role of a user
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   161
function set_user_role(user, role_name)
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   162
	local role = role_registry[role_name];
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   163
	if not role then
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   164
		return error("Cannot assign default user an unknown role: "..tostring(role_name));
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   165
	end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   166
	local keys_update = {
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   167
		_default = role_name;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   168
		-- Primary role cannot be secondary role
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   169
		[role_name] = role_map_store.remove;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   170
	};
13174
082c7d856e61 core, plugins: Split prosody:user role into prosody:{guest,registered,member}
Matthew Wild <mwild1@gmail.com>
parents: 12981
diff changeset
   171
	if role_name == default_user_role then
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   172
		-- Don't store default
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   173
		keys_update._default = role_map_store.remove;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   174
	end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   175
	local ok, err = role_map_store:set_keys(user, keys_update);
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   176
	if not ok then
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   177
		return nil, err;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   178
	end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   179
	return role;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   180
end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   181
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   182
function add_user_secondary_role(user, role_name)
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   183
	if not role_registry[role_name] then
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   184
		return error("Cannot assign default user an unknown role: "..tostring(role_name));
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   185
	end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   186
	role_map_store:set(user, role_name, true);
11476
c32753ceb0f0 mod_authz_internal: add support for setting roles of a local user
Jonas Schäfer <jonas@wielicki.name>
parents: 10663
diff changeset
   187
end
c32753ceb0f0 mod_authz_internal: add support for setting roles of a local user
Jonas Schäfer <jonas@wielicki.name>
parents: 10663
diff changeset
   188
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   189
function remove_user_secondary_role(user, role_name)
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   190
	role_map_store:set(user, role_name, nil);
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   191
end
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   192
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   193
function get_user_secondary_roles(user)
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   194
	local stored_roles, err = role_store:get(user);
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   195
	if not stored_roles then
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   196
		if err then
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   197
			-- Unable to fetch role, fail
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   198
			return nil, err;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   199
		end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   200
		-- No role set
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   201
		return {};
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   202
	end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   203
	stored_roles._default = nil;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   204
	for role_name in pairs(stored_roles) do
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   205
		stored_roles[role_name] = role_registry[role_name];
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   206
	end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   207
	return stored_roles;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   208
end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   209
12667
cf88f6b03942 mod_authz_internal: Expose convenience method to test if user can assume role
Matthew Wild <mwild1@gmail.com>
parents: 12666
diff changeset
   210
function user_can_assume_role(user, role_name)
cf88f6b03942 mod_authz_internal: Expose convenience method to test if user can assume role
Matthew Wild <mwild1@gmail.com>
parents: 12666
diff changeset
   211
	local primary_role = get_user_role(user);
12929
6cb339423928 mod_authz_internal: Fix wrong role name field in user_can_assume_role()
Kim Alvefur <zash@zash.se>
parents: 12924
diff changeset
   212
	if primary_role and primary_role.name == role_name then
12667
cf88f6b03942 mod_authz_internal: Expose convenience method to test if user can assume role
Matthew Wild <mwild1@gmail.com>
parents: 12666
diff changeset
   213
		return true;
cf88f6b03942 mod_authz_internal: Expose convenience method to test if user can assume role
Matthew Wild <mwild1@gmail.com>
parents: 12666
diff changeset
   214
	end
cf88f6b03942 mod_authz_internal: Expose convenience method to test if user can assume role
Matthew Wild <mwild1@gmail.com>
parents: 12666
diff changeset
   215
	local secondary_roles = get_user_secondary_roles(user);
cf88f6b03942 mod_authz_internal: Expose convenience method to test if user can assume role
Matthew Wild <mwild1@gmail.com>
parents: 12666
diff changeset
   216
	if secondary_roles and secondary_roles[role_name] then
cf88f6b03942 mod_authz_internal: Expose convenience method to test if user can assume role
Matthew Wild <mwild1@gmail.com>
parents: 12666
diff changeset
   217
		return true;
cf88f6b03942 mod_authz_internal: Expose convenience method to test if user can assume role
Matthew Wild <mwild1@gmail.com>
parents: 12666
diff changeset
   218
	end
cf88f6b03942 mod_authz_internal: Expose convenience method to test if user can assume role
Matthew Wild <mwild1@gmail.com>
parents: 12666
diff changeset
   219
	return false;
cf88f6b03942 mod_authz_internal: Expose convenience method to test if user can assume role
Matthew Wild <mwild1@gmail.com>
parents: 12666
diff changeset
   220
end
cf88f6b03942 mod_authz_internal: Expose convenience method to test if user can assume role
Matthew Wild <mwild1@gmail.com>
parents: 12666
diff changeset
   221
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   222
-- This function is *expensive*
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   223
function get_users_with_role(role_name)
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   224
	local function role_filter(username, default_role) --luacheck: ignore 212/username
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   225
		return default_role == role_name;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   226
	end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   227
	local primary_role_users = set.new(it.to_array(it.filter(role_filter, pairs(role_map_store:get_all("_default") or {}))));
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   228
	local secondary_role_users = set.new(it.to_array(it.keys(role_map_store:get_all(role_name) or {})));
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   229
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   230
	local config_set;
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   231
	if role_name == "prosody:admin" then
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   232
		config_set = config_admin_jids;
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   233
	elseif role_name == "prosody:operator" then
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   234
		config_set = config_global_admin_jids;
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   235
	end
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   236
	if config_set then
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   237
		local config_admin_users = config_set / function (admin_jid)
11749
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   238
			local j_node, j_host = jid_split(admin_jid);
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   239
			if j_host == host then
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   240
				return j_node;
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   241
			end
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   242
		end;
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   243
		return it.to_array(config_admin_users + primary_role_users + secondary_role_users);
11749
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   244
	end
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   245
	return it.to_array(primary_role_users + secondary_role_users);
11749
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   246
end
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   247
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   248
function get_jid_role(jid)
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   249
	local bare_jid = jid_bare(jid);
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   250
	if config_global_admin_jids:contains(bare_jid) then
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   251
		return role_registry["prosody:operator"];
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   252
	elseif config_admin_jids:contains(bare_jid) then
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   253
		return role_registry["prosody:admin"];
12734
427dd01f0864 mod_authz_internal: Allow configuring role of local-server/parent-host users
Matthew Wild <mwild1@gmail.com>
parents: 12667
diff changeset
   254
	elseif is_component then
427dd01f0864 mod_authz_internal: Allow configuring role of local-server/parent-host users
Matthew Wild <mwild1@gmail.com>
parents: 12667
diff changeset
   255
		local user_host = jid_host(bare_jid);
427dd01f0864 mod_authz_internal: Allow configuring role of local-server/parent-host users
Matthew Wild <mwild1@gmail.com>
parents: 12667
diff changeset
   256
		if host_user_role and user_host == host_suffix then
427dd01f0864 mod_authz_internal: Allow configuring role of local-server/parent-host users
Matthew Wild <mwild1@gmail.com>
parents: 12667
diff changeset
   257
			return role_registry[host_user_role];
427dd01f0864 mod_authz_internal: Allow configuring role of local-server/parent-host users
Matthew Wild <mwild1@gmail.com>
parents: 12667
diff changeset
   258
		elseif server_user_role and hosts[user_host] then
427dd01f0864 mod_authz_internal: Allow configuring role of local-server/parent-host users
Matthew Wild <mwild1@gmail.com>
parents: 12667
diff changeset
   259
			return role_registry[server_user_role];
12737
2167e1639aab mod_authz_internal: Allow specifying default role for public (remote) users
Matthew Wild <mwild1@gmail.com>
parents: 12734
diff changeset
   260
		elseif public_user_role then
2167e1639aab mod_authz_internal: Allow specifying default role for public (remote) users
Matthew Wild <mwild1@gmail.com>
parents: 12734
diff changeset
   261
			return role_registry[public_user_role];
12734
427dd01f0864 mod_authz_internal: Allow configuring role of local-server/parent-host users
Matthew Wild <mwild1@gmail.com>
parents: 12667
diff changeset
   262
		end
10663
8f95308c3c45 usermanager, mod_authz_*: Merge mod_authz_config and mod_authz_internal into the latter
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
   263
	end
8f95308c3c45 usermanager, mod_authz_*: Merge mod_authz_config and mod_authz_internal into the latter
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
   264
	return nil;
8f95308c3c45 usermanager, mod_authz_*: Merge mod_authz_config and mod_authz_internal into the latter
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
   265
end
8f95308c3c45 usermanager, mod_authz_*: Merge mod_authz_config and mod_authz_internal into the latter
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
   266
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   267
function set_jid_role(jid, role_name) -- luacheck: ignore 212
11476
c32753ceb0f0 mod_authz_internal: add support for setting roles of a local user
Jonas Schäfer <jonas@wielicki.name>
parents: 10663
diff changeset
   268
	return false;
c32753ceb0f0 mod_authz_internal: add support for setting roles of a local user
Jonas Schäfer <jonas@wielicki.name>
parents: 10663
diff changeset
   269
end
11749
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   270
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   271
function get_jids_with_role(role_name)
11749
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   272
	-- Fetch role users from storage
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   273
	local storage_role_jids = array.map(get_users_with_role(role_name), function (username)
11749
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   274
		return username.."@"..host;
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   275
	end);
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   276
	if role_name == "prosody:admin" then
11749
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   277
		return it.to_array(config_admin_jids + set.new(storage_role_jids));
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   278
	elseif role_name == "prosody:operator" then
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   279
		return it.to_array(config_global_admin_jids + set.new(storage_role_jids));
11749
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   280
	end
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   281
	return storage_role_jids;
3a2d58a39872 usermanager, mod_authz_internal: Add methods to fetch users/JIDs of given role
Matthew Wild <mwild1@gmail.com>
parents: 11478
diff changeset
   282
end
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   283
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   284
function add_default_permission(role_name, action, policy)
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   285
	local role = role_registry[role_name];
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   286
	if not role then
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   287
		module:log("warn", "Attempt to add default permission for unknown role: %s", role_name);
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   288
		return nil, "no-such-role";
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   289
	end
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   290
	if policy == nil then policy = true; end
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   291
	module:log("debug", "Adding policy %s for permission %s on role %s", policy, action, role_name);
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   292
	return role:set_permission(action, policy);
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   293
end
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   294
12652
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   295
function get_role_by_name(role_name)
f299e570a0fe mod_authz_internal: Use util.roles, some API changes and config support
Matthew Wild <mwild1@gmail.com>
parents: 12646
diff changeset
   296
	return assert(role_registry[role_name], role_name);
12646
9061f9621330 Switch to a new role-based authorization framework, removing is_admin()
Matthew Wild <mwild1@gmail.com>
parents: 11749
diff changeset
   297
end
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   298
12924
cdb996637b08 authz: Add method for retrieving all roles
Kim Alvefur <zash@zash.se>
parents: 12744
diff changeset
   299
function get_all_roles()
cdb996637b08 authz: Add method for retrieving all roles
Kim Alvefur <zash@zash.se>
parents: 12744
diff changeset
   300
	return role_registry;
cdb996637b08 authz: Add method for retrieving all roles
Kim Alvefur <zash@zash.se>
parents: 12744
diff changeset
   301
end
cdb996637b08 authz: Add method for retrieving all roles
Kim Alvefur <zash@zash.se>
parents: 12744
diff changeset
   302
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   303
-- COMPAT: Migrate from 0.12 role storage
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   304
local function do_migration(migrate_host)
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   305
	local old_role_store = assert(module:context(migrate_host):open_store("roles"));
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   306
	local new_role_store = assert(module:context(migrate_host):open_store("account_roles"));
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   307
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   308
	local migrated, failed, skipped = 0, 0, 0;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   309
	-- Iterate all users
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   310
	for username in assert(old_role_store:users()) do
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   311
		local old_roles = it.to_array(it.filter(function (k) return k:sub(1,1) ~= "_"; end, it.keys(old_role_store:get(username))));
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   312
		if #old_roles == 1 then
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   313
			local ok, err = new_role_store:set(username, {
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   314
				_default = old_roles[1];
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   315
			});
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   316
			if ok then
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   317
				migrated = migrated + 1;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   318
			else
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   319
				failed = failed + 1;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   320
				print("EE: Failed to store new role info for '"..username.."': "..err);
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   321
			end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   322
		else
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   323
			print("WW: User '"..username.."' has multiple roles and cannot be automatically migrated");
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   324
			skipped = skipped + 1;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   325
		end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   326
	end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   327
	return migrated, failed, skipped;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   328
end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   329
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   330
function module.command(arg)
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   331
	if arg[1] == "migrate" then
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   332
		table.remove(arg, 1);
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   333
		local migrate_host = arg[1];
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   334
		if not migrate_host or not prosody.hosts[migrate_host] then
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   335
			print("EE: Please supply a valid host to migrate to the new role storage");
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   336
			return 1;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   337
		end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   338
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   339
		-- Initialize storage layer
12981
74b9e05af71e plugins: Prefix module imports with prosody namespace
Kim Alvefur <zash@zash.se>
parents: 12929
diff changeset
   340
		require "prosody.core.storagemanager".initialize_host(migrate_host);
12666
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   341
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   342
		print("II: Migrating roles...");
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   343
		local migrated, failed, skipped = do_migration(migrate_host);
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   344
		print(("II: %d migrated, %d failed, %d skipped"):format(migrated, failed, skipped));
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   345
		return (failed + skipped == 0) and 0 or 1;
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   346
	else
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   347
		print("EE: Unknown command: "..(arg[1] or "<none given>"));
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   348
		print("    Hint: try 'migrate'?");
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   349
	end
07424992d7fc mod_authz_internal, and more: New iteration of role API
Matthew Wild <mwild1@gmail.com>
parents: 12652
diff changeset
   350
end