netcmd: Add --site option when restoring a domain
authorTim Beale <timbeale@catalyst.net.nz>
Mon, 17 Sep 2018 03:36:21 +0000 (15:36 +1200)
committerAndrew Bartlett <abartlet@samba.org>
Wed, 26 Sep 2018 05:49:17 +0000 (07:49 +0200)
Restoring a backup only worked if the Default-First-Site-Name site was
still present. When the new restored DC account is created, it was
trying to add the new server's DN under CN=Default-First-Site-Name.
However, if the original domain was setup using a different site, then
the restore would fail because the DN didn't exist.

When running the restore command, you should be able to specify the
site that you want the new/restored DC to be in (same as during a
DC 'join'). Passing the correct --site argument is one way to avoid
this problem. (A subsequent patch will further improve the tool so it
can work around non-default sites automatically).

Note we also need to pass the site through to where the new DNS entries
get registered (in the rename case).

BUG: https://bugzilla.samba.org/show_bug.cgi?id=13621

Signed-off-by: Tim Beale <timbeale@catalyst.net.nz>
Reviewed-by: Douglas Bagnall <douglas.bagnall@catalyst.net.nz>
Reviewed-by: Andrew Bartlett <abartlet@samba.org>
python/samba/netcmd/domain_backup.py

index e87debd8fe9a876b6ad4f029b2c3cd6680ff4e1e..89de40db7aaf215c001228b78c83126b27b74492 100644 (file)
@@ -36,7 +36,7 @@ from samba.netcmd import Option, CommandError
 from samba.dcerpc import misc, security
 from samba import Ldb
 from . fsmo import cmd_fsmo_seize
-from samba.provision import make_smbconf
+from samba.provision import make_smbconf, DEFAULTSITE
 from samba.upgradehelpers import update_krbtgt_account_password
 from samba.remove_dc import remove_dc
 from samba.provision import secretsdb_self_join
@@ -295,6 +295,7 @@ class cmd_domain_backup_restore(cmd_fsmo_seize):
                help="set IPv4 ipaddress"),
         Option("--host-ip6", type="string", metavar="IP6ADDRESS",
                help="set IPv6 ipaddress"),
+        Option("--site", help="Site to add the new server in", type=str),
     ]
 
     takes_optiongroups = {
@@ -303,7 +304,7 @@ class cmd_domain_backup_restore(cmd_fsmo_seize):
     }
 
     def register_dns_zone(self, logger, samdb, lp, ntdsguid, host_ip,
-                          host_ip6):
+                          host_ip6, site):
         '''
         Registers the new realm's DNS objects when a renamed domain backup
         is restored.
@@ -330,7 +331,7 @@ class cmd_domain_backup_restore(cmd_fsmo_seize):
 
         # Add the DNS objects for the new realm (note: the backup clone already
         # has the root server objects, so don't add them again)
-        fill_dns_data_partitions(samdb, domainsid, names.sitename, domaindn,
+        fill_dns_data_partitions(samdb, domainsid, site, domaindn,
                                  forestdn, dnsdomain, dnsforest, hostname,
                                  host_ip, host_ip6, domainguid, ntdsguid,
                                  dnsadmins_sid, add_root=False)
@@ -361,7 +362,8 @@ class cmd_domain_backup_restore(cmd_fsmo_seize):
         samdb.transaction_commit()
 
     def run(self, sambaopts=None, credopts=None, backup_file=None,
-            targetdir=None, newservername=None, host_ip=None, host_ip6=None):
+            targetdir=None, newservername=None, host_ip=None, host_ip6=None,
+            site=DEFAULTSITE):
         if not (backup_file and os.path.exists(backup_file)):
             raise CommandError('Backup file not found.')
         if targetdir is None:
@@ -413,7 +415,7 @@ class cmd_domain_backup_restore(cmd_fsmo_seize):
         ncs = [str(r) for r in res[0].get('namingContexts')]
 
         creds = credopts.get_credentials(lp)
-        ctx = DCJoinContext(logger, creds=creds, lp=lp,
+        ctx = DCJoinContext(logger, creds=creds, lp=lp, site=site,
                             forced_local_samdb=samdb,
                             netbios_name=newservername)
         ctx.nc_list = ncs
@@ -451,7 +453,7 @@ class cmd_domain_backup_restore(cmd_fsmo_seize):
         # know the new DC's IP address)
         if is_rename:
             self.register_dns_zone(logger, samdb, lp, ctx.ntds_guid,
-                                   host_ip, host_ip6)
+                                   host_ip, host_ip6, site)
 
         secrets_path = os.path.join(private_dir, 'secrets.ldb')
         secrets_ldb = Ldb(secrets_path, session_info=system_session(), lp=lp)