From 80cbddaa37241e5c762edb656e4c658e652c87ef Mon Sep 17 00:00:00 2001 From: Martin Babinsky Date: Jun 13 2016 15:50:54 +0000 Subject: Server Roles: public API for server roles This patch implements the `serverroles` API plugin which introduces the following commands: * server-role-show SERVER ROLE: show status of a single role on a server * server-role-find [--server SERVER [--role SERVROLE [--status=STATUS]]]: find role(s) SERVROLE and return their status on IPA masters. If --server option is given, the query is limited to this server. --status options filters the output by status [enabled vs. configurer vs. absent] https://fedorahosted.org/freeipa/ticket/5181 http://www.freeipa.org/page/V4/Server_Roles Reviewed-By: Jan Cholasta Reviewed-By: Martin Basti Reviewed-By: Pavel Vomacka --- diff --git a/API.txt b/API.txt index 4247dd7..f52f23f 100644 --- a/API.txt +++ b/API.txt @@ -4043,6 +4043,31 @@ option: Str('version?') output: Entry('result') output: Output('summary', type=[, ]) output: PrimaryKey('value') +command: server_role_find +args: 1,8,4 +arg: Str('criteria?') +option: Flag('all', autofill=True, cli_name='all', default=False) +option: Flag('raw', autofill=True, cli_name='raw', default=False) +option: Str('role_servrole?', autofill=False, cli_name='role') +option: Str('server_server?', autofill=False, cli_name='server') +option: Int('sizelimit?', autofill=False) +option: StrEnum('status?', autofill=False, cli_name='status', default=u'enabled', values=[u'enabled', u'configured', u'absent']) +option: Int('timelimit?', autofill=False) +option: Str('version?') +output: Output('count', type=[]) +output: ListOfEntries('result') +output: Output('summary', type=[, ]) +output: Output('truncated', type=[]) +command: server_role_show +args: 2,3,3 +arg: Str('server_server', cli_name='server') +arg: Str('role_servrole', cli_name='role') +option: Flag('all', autofill=True, cli_name='all', default=False) +option: Flag('raw', autofill=True, cli_name='raw', default=False) +option: Str('version?') +output: Entry('result') +output: Output('summary', type=[, ]) +output: PrimaryKey('value') command: server_show args: 1,5,3 arg: Str('cn', cli_name='name') diff --git a/VERSION b/VERSION index 8945ae5..50cf35e 100644 --- a/VERSION +++ b/VERSION @@ -90,5 +90,5 @@ IPA_DATA_VERSION=20100614120000 # # ######################################################## IPA_API_VERSION_MAJOR=2 -IPA_API_VERSION_MINOR=177 -# Last change: abbra - adtrust: remove nttrustpartner parameter +IPA_API_VERSION_MINOR=178 +# Last change: mbabinsk - Server Roles: public API for server roles diff --git a/ipaserver/plugins/serverrole.py b/ipaserver/plugins/serverrole.py new file mode 100644 index 0000000..91f7e7a --- /dev/null +++ b/ipaserver/plugins/serverrole.py @@ -0,0 +1,178 @@ +# +# Copyright (C) 2016 FreeIPA Contributors see COPYING for license +# + +from ipalib.crud import Retrieve, Search +from ipalib.errors import NotFound +from ipalib.frontend import Object +from ipalib.parameters import Int, Str, StrEnum +from ipalib.plugable import Registry +from ipalib import _, ngettext + + +__doc__ = _(""" +IPA server roles +""") + _(""" +Get status of roles (DNS server, CA, etc. )provided by IPA masters. +""") + _(""" +EXAMPLES: +""") + _(""" + Show status of 'DNS server' role on a server: + ipa server-role-show ipa.example.com "DNS server" +""") + _(""" + Show status of all roles containing 'AD' on a server: + ipa server-role-find --server ipa.example.com --role='AD' +""") + _(""" + Show status of all configured roles on a server: + ipa server-role-find ipa.example.com +""") + + +register = Registry() + + +@register() +class server_role(Object): + """ + association between certain role (e.g. DNS server) and its status with + an IPA master + """ + backend_name = 'serverroles' + object_name = _('server role') + object_name_plural = _('server roles') + default_attributes = [ + 'role', 'status' + ] + label = _('IPA Server Roles') + label_singular = _('IPA Server Role') + + takes_params = ( + Str( + 'server_server', + cli_name='server', + label=_('Server name'), + doc=_('IPA server hostname'), + ), + Str( + 'role_servrole', + cli_name='role', + label=_("Role name"), + doc=_("IPA server role name"), + flags={u'virtual_attribute'} + ), + StrEnum( + 'status?', + cli_name='status', + label=_('Role status'), + doc=_('Status of the role'), + values=(u'enabled', u'configured', u'absent'), + default=u'enabled', + flags={'virtual_attribute', 'no_create', 'no_update'} + ) + ) + + def ensure_master_exists(self, fqdn): + server_obj = self.api.Object.server + try: + server_obj.get_dn_if_exists(fqdn) + except NotFound: + server_obj.handle_not_found(fqdn) + + +@register() +class server_role_show(Retrieve): + __doc__ = _('Show role status on a server') + + obj_name = 'server_role' + attr_name = 'show' + + def get_args(self): + for arg in super(server_role_show, self).get_args(): + yield arg + + for param in self.obj.params(): + if param.name != u'status': + yield param.clone() + + def execute(self, *keys, **options): + self.obj.ensure_master_exists(keys[0]) + + role_status = self.obj.backend.server_role_retrieve( + server_server=keys[0], role_servrole=keys[1]) + + return dict(result=role_status[0], value=None) + + +@register() +class server_role_find(Search): + __doc__ = _('Find a server role on a server(s)') + + obj_name = 'server_role' + attr_name = 'find' + + msg_summary = ngettext('%(count)s server role matched', + '%(count)s server roles matched', 0) + takes_options = Search.takes_options + ( + Int( + 'timelimit?', + label=_('Time Limit'), + doc=_('Time limit of search in seconds (0 is unlimited)'), + flags=['no_display'], + minvalue=0, + autofill=False, + ), + Int( + 'sizelimit?', + label=_('Size Limit'), + doc=_('Maximum number of entries returned (0 is unlimited)'), + flags=['no_display'], + minvalue=0, + autofill=False, + ), + ) + + def execute(self, *keys, **options): + if keys: + return dict( + result=[], + count=0, + truncated=False + ) + + server = options.get('server_server', None) + role_name = options.get('role_servrole', None) + status = options.get('status', None) + + if server is not None: + self.obj.ensure_master_exists(server) + + role_status = self.obj.backend.server_role_search( + server_server=server, + role_servrole=role_name, + status=status) + + result = [ + r for r in role_status if r[u'role_servrole'] != "IPA master"] + return dict( + result=result, + count=len(result), + truncated=False, + ) + + +@register() +class servrole(Object): + """ + Server role object + """ + object_name = _('role') + object_name_plural = _('roles') + takes_params = ( + Str( + 'name', + primary_key=True, + label=_("Role name"), + doc=_("IPA role name"), + flags=(u'virtual_attribute',) + ) + )