Hi,

Provides a pluggable framework for generating configuration
scriptlets and instructions for various machine setups.

Creates a new ipa-client-advise command, available to root user
on the IPA server.

Also provides an example configuration plugin.

https://fedorahosted.org/freeipa/ticket/3670

Tomas
From 6cb034b8facf98e45ccad54142ff3e0f9ffb08cb Mon Sep 17 00:00:00 2001
From: Tomas Babej <tba...@redhat.com>
Date: Mon, 10 Jun 2013 14:43:24 +0200
Subject: [PATCH] Provide ipa-client-advise tool

Provides a pluggable framework for generating configuration
scriptlets and instructions for various machine setups.

Creates a new ipa-client-advise command, available to root user
on the IPA server.

Also provides an example configuration plugin.

https://fedorahosted.org/freeipa/ticket/3670
---
 freeipa.spec.in                               |   4 +
 install/tools/Makefile.am                     |   1 +
 install/tools/ipa-client-advise               |  23 +++++
 install/tools/man/Makefile.am                 |   1 +
 install/tools/man/ipa-client-advise.1         |  72 ++++++++++++++
 ipalib/frontend.py                            |  19 ++++
 ipalib/plugable.py                            |   2 +
 ipaserver/advise/__init__.py                  |  22 +++++
 ipaserver/advise/base.py                      | 132 ++++++++++++++++++++++++++
 ipaserver/advise/plugins/__init__.py          |  22 +++++
 ipaserver/advise/plugins/fedora_authconfig.py |  39 ++++++++
 setup.py                                      |   2 +
 12 files changed, 339 insertions(+)
 create mode 100755 install/tools/ipa-client-advise
 create mode 100644 install/tools/man/ipa-client-advise.1
 create mode 100644 ipaserver/advise/__init__.py
 create mode 100644 ipaserver/advise/base.py
 create mode 100644 ipaserver/advise/plugins/__init__.py
 create mode 100644 ipaserver/advise/plugins/fedora_authconfig.py

diff --git a/freeipa.spec.in b/freeipa.spec.in
index 4a38e8785903faa5f38295534432a8f679671136..4e37f7f2c4a78cfe295c799efda80342efdc7ba4 100644
--- a/freeipa.spec.in
+++ b/freeipa.spec.in
@@ -636,6 +636,7 @@ fi
 %{_sbindir}/ipactl
 %{_sbindir}/ipa-upgradeconfig
 %{_sbindir}/ipa-compliance
+%{_sbindir}/ipa-client-advise
 %{_libexecdir}/certmonger/dogtag-ipa-retrieve-agent-submit
 %{_libexecdir}/ipa-otpd
 %{_sysconfdir}/cron.d/ipa-compliance
@@ -652,6 +653,8 @@ fi
 %dir %{python_sitelib}/ipaserver
 %dir %{python_sitelib}/ipaserver/install
 %dir %{python_sitelib}/ipaserver/install/plugins
+%dir %{python_sitelib}/ipaserver/advise
+%dir %{python_sitelib}/ipaserver/advise/plugins
 %dir %{python_sitelib}/ipaserver/plugins
 %dir %{_libdir}/ipa/certmonger
 %attr(755,root,root) %{_libdir}/ipa/certmonger/*
@@ -770,6 +773,7 @@ fi
 %{_mandir}/man1/ipa-compliance.1.gz
 %{_mandir}/man1/ipa-backup.1.gz
 %{_mandir}/man1/ipa-restore.1.gz
+%{_mandir}/man1/ipa-client-advise.1.gz
 
 %files server-selinux
 %defattr(-,root,root,-)
diff --git a/install/tools/Makefile.am b/install/tools/Makefile.am
index 7c553116cdfdce69e594f9d9a36e6bebcab5f692..90d5a5382c23893d55b0297a73e5f01ad312f8d4 100644
--- a/install/tools/Makefile.am
+++ b/install/tools/Makefile.am
@@ -24,6 +24,7 @@ sbin_SCRIPTS =			\
 	ipa-compliance		\
 	ipa-backup		\
 	ipa-restore		\
+	ipa-client-advise	\
 	$(NULL)
 
 EXTRA_DIST =			\
diff --git a/install/tools/ipa-client-advise b/install/tools/ipa-client-advise
new file mode 100755
index 0000000000000000000000000000000000000000..6440503243bd124584eca55cf286b101ec861c16
--- /dev/null
+++ b/install/tools/ipa-client-advise
@@ -0,0 +1,23 @@
+#! /usr/bin/python -E
+# Authors: Tomas Babej <tba...@redhat.com>
+#
+# Copyright (C) 2013  Red Hat
+# see file 'COPYING' for use and warranty information
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program.  If not, see <http://www.gnu.org/licenses/>.
+#
+
+from ipaserver.advise.base import ClientAdvise
+
+ClientAdvise.run_cli()
diff --git a/install/tools/man/Makefile.am b/install/tools/man/Makefile.am
index a1bf076bf7917d309b67cf714f069f41c3496f0e..834197e6c3dcfd1474107e50de25caab31a75ac0 100644
--- a/install/tools/man/Makefile.am
+++ b/install/tools/man/Makefile.am
@@ -22,6 +22,7 @@ man1_MANS = 				\
 	ipa-compliance.1		\
 	ipa-backup.1			\
 	ipa-restore.1			\
+	ipa-client-advise.1		\
         $(NULL)
 
 man8_MANS =				\
diff --git a/install/tools/man/ipa-client-advise.1 b/install/tools/man/ipa-client-advise.1
new file mode 100644
index 0000000000000000000000000000000000000000..e6f6346af4f7c286f1fec5798be66143d7b5d175
--- /dev/null
+++ b/install/tools/man/ipa-client-advise.1
@@ -0,0 +1,72 @@
+.\" A man page for ipa-client-advise
+.\" Copyright (C) 2013 Red Hat, Inc.
+.\"
+.\" This program is free software; you can redistribute it and/or modify
+.\" it under the terms of the GNU General Public License as published by
+.\" the Free Software Foundation, either version 3 of the License, or
+.\" (at your option) any later version.
+.\"
+.\" This program is distributed in the hope that it will be useful, but
+.\" WITHOUT ANY WARRANTY; without even the implied warranty of
+.\" MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+.\" General Public License for more details.
+.\"
+.\" You should have received a copy of the GNU General Public License
+.\" along with this program.  If not, see <http://www.gnu.org/licenses/>.
+.\"
+.\" Author: Tomas Babej <tba...@redhat.com>
+.\"
+.TH "ipa-client-advise" "1" "Jun 10 2013" "FreeIPA" "FreeIPA Manual Pages"
+.SH "NAME"
+ipa\-client\-advise \- Provide trust setup instructions for configuration of legacy systems.
+.SH "SYNOPSIS"
+ipa\-client\-advise [\fIOPTION\fR]...
+.SH "DESCRIPTION"
+Two kinds of backups: full and data\-only.
+.TP
+The back up is optionally encrypted using either the default root GPG key or a named key. No passphrase is supported.
+.TP
+Backups are stored in a subdirectory in /var/lib/ipa/backup.
+.TP
+The naming convention for full backups is ipa\-full\-YEAR\-MM\-DD\-HH\-MM\-SS in the GMT time zone.
+.TP
+The naming convention for data backups is ipa\-data\-YEAR\-MM\-DD\-HH\-MM\-SS In the GMT time zone.
+.TP
+Within the subdirectory is file, header, that describes the back up including the type, system, date of backup, the version of IPA, the version of the backup and the services on the master.
+.TP
+A backup can not be restored on another host.
+.TP
+A backup can not be restored in a different version of IPA.
+.SH "OPTIONS"
+.TP
+\fB\-\-data\fR
+Back up data only. The default is to back up all IPA files plus data.
+.TP
+\fB\-\-v\fR, \fB\-\-verbose\fR
+Print debugging information
+.TP
+\fB\-d\fR, \fB\-\-debug\fR
+Alias for \-\-verbose
+.TP
+\fB\-q\fR, \fB\-\-quiet\fR
+Output only errors
+.TP
+\fB\-\-log\-file\fR=\fIFILE\fR
+Log to the given file
+.SH "EXIT STATUS"
+0 if the command was successful
+
+1 if an error occurred
+.SH "FILES"
+.PP
+\fI/var/lib/ipa/backup\fR
+.RS 4
+The default directory for storing backup files.
+.RE
+.PP
+\fl/var/log/ipabackup.log\fR
+.RS 4
+The log file for backups
+.PP
+.SH "SEE ALSO"
+ipa\-restore(1).
diff --git a/ipalib/frontend.py b/ipalib/frontend.py
index 427f682357579b1abcef5dcc684ef644112df124..f7eb932e964d6d8c1cf9c259f61f36ce66505980 100644
--- a/ipalib/frontend.py
+++ b/ipalib/frontend.py
@@ -1445,3 +1445,22 @@ class Updater(Method):
         )
 
         return self.execute(**options)
+
+
+class Configuration(Method):
+    """
+    Base class for supported client configurations.
+    """
+
+    description = None
+
+    def __init__(self):
+        super(Configuration, self).__init__()
+
+    def get_info(self):
+        """
+        This method should be overriden by child Configurations.
+
+        Returns a string with instructions.
+        """
+        raise NotImplementedError
\ No newline at end of file
diff --git a/ipalib/plugable.py b/ipalib/plugable.py
index aaa0dea480f092e32815c525751359f056936e3c..25698d8f5bf4a578e4c95cf56ef4ec3e573fa615 100644
--- a/ipalib/plugable.py
+++ b/ipalib/plugable.py
@@ -615,6 +615,8 @@ class API(DictProxy):
             self.import_plugins('ipaserver')
         if self.env.context in ('installer', 'updates'):
             self.import_plugins('ipaserver/install/plugins')
+        if self.env.context in ('advise'):
+            self.import_plugins('ipaserver/advise/plugins')
 
     # FIXME: This method has no unit test
     def import_plugins(self, package):
diff --git a/ipaserver/advise/__init__.py b/ipaserver/advise/__init__.py
new file mode 100644
index 0000000000000000000000000000000000000000..6a601dbbf9bca9a3c19b61706844966bec341533
--- /dev/null
+++ b/ipaserver/advise/__init__.py
@@ -0,0 +1,22 @@
+# Authors: Tomas Babej <tba...@redhat.com>
+#
+# Copyright (C) 2013  Red Hat
+# see file 'COPYING' for use and warranty information
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program.  If not, see <http://www.gnu.org/licenses/>.
+#
+
+"""
+Base subpackage for ipa-client-advise related code.
+"""
\ No newline at end of file
diff --git a/ipaserver/advise/base.py b/ipaserver/advise/base.py
new file mode 100644
index 0000000000000000000000000000000000000000..0d2280a4e78980d712907a5c37e934c3bd8a5125
--- /dev/null
+++ b/ipaserver/advise/base.py
@@ -0,0 +1,132 @@
+#!/usr/bin/python
+# Authors: Tomas Babej <tba...@redhat.com>
+#
+# Copyright (C) 2013  Red Hat
+# see file 'COPYING' for use and warranty information
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program.  If not, see <http://www.gnu.org/licenses/>.
+#
+
+from ipalib import api
+from ipalib.frontend import Object
+from ipalib.errors import ValidationError
+from ipapython import admintool
+from ipaserver.install import installutils
+import traceback
+
+"""
+To add instructions for a new configuration, define a new class that inherits
+from Configuration class.
+
+>>> class SampleConfiguration(Configuration):
+>>>     keyword = 'sssd10'
+>>>     description = 'Instructions for machine with SSSD 1.0 setup.'
+
+>>>.....def get_info():
+>>>         return 'Install new software.'
+"""
+
+
+class advise(Object):
+    """
+    Generic object used to register all advice plugins into a single namespace.
+    """
+    backend_name = 'ldap2'
+
+api.register(advise)
+
+
+class ClientAdvise(admintool.AdminTool):
+    """
+    Admin tool that given systems's configuration provides instructions how to
+    configure the system for the trusts.
+    """
+
+    command_name = 'ipa-client-advise'
+    log_file_name = '/var/log/ipa-client-advise.log'
+    usage = "%prog [options]"
+    description = "Provides trust configuration advice for legacy clients."
+
+    def __init__(self, options, args):
+        super(ClientAdvise, self).__init__(options, args)
+
+    @classmethod
+    def add_options(cls, parser):
+        super(ClientAdvise, cls).add_options(parser)
+
+        parser.add_option("--list", dest="list", action="store_true",
+            default=False, help="Lists the supported configuration types.")
+        parser.add_option("--setup", dest="setup",
+            help="Provide configuration instructions for given setup.")
+
+    def validate_options(self):
+        super(ClientAdvise, self).validate_options(needs_root=True)
+        installutils.check_server_configuration()
+
+        if self.options.list and self.options.setup:
+            self.option_parser.error("You cannot use both --list "
+                                     "and --setup")
+
+        if not any((self.options.list, self.options.setup)):
+            self.option_parser.error("You need to specify at least one of "
+                                     "--list or --setup.")
+
+    def log_success(self):
+        pass
+
+    def print_config_list(self):
+        advices = api.Object.advise.methods
+        for advice in advices:
+            print "    {conf} : {desc}".format(conf=advice,
+                                               desc=advices[advice].description)
+
+    def get_conf(self, keyword):
+        advices = api.Object.advise.methods
+        return getattr(advices, keyword, None)
+
+    def print_setup_info(self, keyword):
+        configuration = self.get_conf(keyword)
+
+        # Ensure that Configuration class for given --setup option value exists
+        if configuration is None:
+            raise ValidationError(
+                name="setup",
+                error="No instructions are available for '{con}'. "
+                      "See the list of available configuration "
+                      "advices using the --list option."
+                      .format(con=self.options.setup))
+
+        header_size = len(configuration.description)
+
+        # Print out nicely formatted header
+        print '-' * header_size
+        print configuration.description
+        print '-' * header_size
+
+        # Print out the actual advice
+        print configuration.get_info()
+
+    def run(self):
+        super(ClientAdvise, self).run()
+
+        api.bootstrap(in_server=False, context='advise')
+        api.finalize()
+
+        # With --list option, print the list out and exit
+        if self.options.list:
+            self.print_config_list()
+            return
+
+        if self.options.setup:
+            self.print_setup_info(self.options.setup)
diff --git a/ipaserver/advise/plugins/__init__.py b/ipaserver/advise/plugins/__init__.py
new file mode 100644
index 0000000000000000000000000000000000000000..84823cec328bbb491c013c6f511f61614974c147
--- /dev/null
+++ b/ipaserver/advise/plugins/__init__.py
@@ -0,0 +1,22 @@
+# Authors: Tomas Babej <tba...@redhat.com>
+#
+# Copyright (C) 2013  Red Hat
+# see file 'COPYING' for use and warranty information
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program.  If not, see <http://www.gnu.org/licenses/>.
+#
+
+"""
+Provides a separate api for ipa-client-advise plugins.
+"""
\ No newline at end of file
diff --git a/ipaserver/advise/plugins/fedora_authconfig.py b/ipaserver/advise/plugins/fedora_authconfig.py
new file mode 100644
index 0000000000000000000000000000000000000000..9d6fc5d60802ba1475ebe6b47430ec2b16a0ac22
--- /dev/null
+++ b/ipaserver/advise/plugins/fedora_authconfig.py
@@ -0,0 +1,39 @@
+# Authors: Tomas Babej <tba...@redhat.com>
+#
+# Copyright (C) 2013  Red Hat
+# see file 'COPYING' for use and warranty information
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program.  If not, see <http://www.gnu.org/licenses/>.
+#
+
+from ipalib import api
+from ipalib.frontend import Configuration
+
+
+class advise_fedora_authconfig(Configuration):
+    """
+    Provides client configuration instructions using authconfig.
+    """
+
+    description = 'Authconfig instructions for Fedora 18/19'
+
+    def get_info(self):
+        template = "/sbin/authconfig --enableldap --ldapserver={server} "\
+                   "--enablerfc2307bis --enablekrb5"
+        advice = template.format(server=api.env.host)
+
+        return advice
+
+
+api.register(advise_fedora_authconfig)
diff --git a/setup.py b/setup.py
index 04b20e05bb01660e3f3c77a528e7752c690e1fc7..08a14d3a10a46a6087596abf70ecadecd6b68634 100755
--- a/setup.py
+++ b/setup.py
@@ -79,6 +79,8 @@ setup(
         'ipalib',
         'ipalib.plugins',
         'ipaserver',
+        'ipaserver.advise',
+        'ipaserver.advise.plugins',
         'ipaserver.plugins',
         'ipaserver.install',
         'ipaserver.install.plugins',
-- 
1.8.1.4

_______________________________________________
Freeipa-devel mailing list
Freeipa-devel@redhat.com
https://www.redhat.com/mailman/listinfo/freeipa-devel

Reply via email to