diff options
-rwxr-xr-x | install/tools/ipa-replica-manage | 89 | ||||
-rw-r--r-- | ipaserver/install/replication.py | 22 |
2 files changed, 109 insertions, 2 deletions
diff --git a/install/tools/ipa-replica-manage b/install/tools/ipa-replica-manage index 135b346bc..3c789d0ee 100755 --- a/install/tools/ipa-replica-manage +++ b/install/tools/ipa-replica-manage @@ -55,8 +55,8 @@ def parse_options(): options, args = parser.parse_args() - if not len(args) or not ("list" in args[0] or "add" in args[0] or "del" in args[0] or "init" in args[0] or "synch" in args[0]): - parser.error("must provide a command [list | add | del | init | synch]") + if not len(args) or not ("list" in args[0] or "add" in args[0] or "del" in args[0] or "init" in args[0] or "synch" in args[0] or "disconnect" in args[0]): + parser.error("must provide a command [list | add | del | init | synch | disconnect]") # set log level if options.verbose: @@ -105,6 +105,80 @@ def list_masters(replman, verbose): print " last update status: %s" % entry.nsds5replicalastupdatestatus print " last update ended: %s" % str(ipautil.parse_generalized_time(entry.nsds5replicalastupdateend)) +def del_link(replica1, replica2, dirman_passwd, force=False): + + repl2 = None + + try: + repl1 = replication.ReplicationManager(replica1, dirman_passwd) + repl1.suffix = get_suffix() + + type1 = repl1.get_agreement_type(replica2) + + repl_list = repl1.find_ipa_replication_agreements() + if not force and len(repl_list) <= 1 and type1 == replication.IPA_REPLICA: + print "Cannot remove the last replication link of '%s'" % replica1 + print "Please use the 'del' command to remove it from the domain" + return + + except ldap.NO_SUCH_OBJECT: + print "'%s' has no replication agreement for '%s'" % (replica1, replica2) + return + except errors.NotFound: + print "'%s' has no replication agreement for '%s'" % (replica1, replica2) + return + except Exception, e: + print "Failed to get data from '%s': %s" % (replica1, str(e)) + return + + if type1 == replication.IPA_REPLICA: + try: + repl2 = replication.ReplicationManager(replica2, dirman_passwd) + repl2.suffix = get_suffix() + + repl_list = repl1.find_ipa_replication_agreements() + if not force and len(repl_list) <= 1: + print "Cannot remove the last replication link of '%s'" % replica2 + print "Please use the 'del' command to remove it from the domain" + return + + except ldap.NO_SUCH_OBJECT: + print "'%s' has no replication agreement for '%s'" % (replica2, replica1) + if not force: + return + except errors.NotFound: + print "'%s' has no replication agreement for '%s'" % (replica2, replica1) + if not force: + return + except Exception, e: + print "Failed to get data from '%s': %s" % (replica2, str(e)) + if not force: + return + + if repl2 and type1 == replication.IPA_REPLICA: + failed = False + try: + repl2.delete_agreement(replica1) + except ldap.LDAPError, e: + desc = e.args[0]['desc'].strip() + info = e.args[0].get('info', '').strip() + print "Unable to remove agreement on %s: %s: %s" % (replica2, desc, info) + failed = True + except Exception, e: + print "Unable to remove agreement on %s: %s" % (replica2, str(e)) + failed = True + + if failed: + if force: + print "Forcing removal on '%s'" % replica1 + else: + return + + if not repl2 and force: + print "Forcing removal on '%s'" % replica1 + + repl1.delete_agreement(replica2) + def del_master(replman, hostname, force=False): has_repl_agreement = True try: @@ -253,6 +327,17 @@ def main(): print "must provide hostname of supplier to synchronize with" sys.exit(1) synch_master(r, args[1]) + elif args[0] == "disconnect": + if len(args) == 3: + replica1 = args[1] + replica2 = args[2] + elif len(args) == 2: + replica1 = host + replica2 = args[1] + else: + print "must provide the name of the server you want to disconnect" + sys.exit(1) + del_link(replica1, replica2, dirman_passwd) else: print "unknown command: %s" % args[0] sys.exit(1) diff --git a/ipaserver/install/replication.py b/ipaserver/install/replication.py index fbe4d2f76..000529f47 100644 --- a/ipaserver/install/replication.py +++ b/ipaserver/install/replication.py @@ -135,6 +135,28 @@ class ReplicationManager: return [] return [ent.dn for ent in ents] + def find_ipa_replication_agreements(self): + """ + The replication agreements are stored in + cn="$SUFFIX",cn=mapping tree,cn=config + + Return the list of hosts we have replication agreements. + """ + + res = [] + + filt = "(objectclass=nsds5ReplicationAgreement)" + try: + ents = self.conn.search_s("cn=mapping tree,cn=config", + ldap.SCOPE_SUBTREE, filt) + except ldap.NO_SUCH_OBJECT: + return res + + for ent in ents: + res.append(ent.nsds5replicahost) + + return res + def add_replication_manager(self, conn, passwd=None): """ Create a pseudo user to use for replication. If no password |