s4 dns: Check more of the returned values for the A query
[Samba/gebeck_regimport.git] / source4 / scripting / python / samba / netcmd / fsmo.py
blob4449a306a9a46805fafa3f2f02cf44688556ab6d
1 #!/usr/bin/env python
3 # Changes a FSMO role owner
5 # Copyright Nadezhda Ivanova 2009
6 # Copyright Jelmer Vernooij 2009
7 # Copyright Giampaolo Lauria 2011 <lauria2@yahoo.com>
9 # This program is free software; you can redistribute it and/or modify
10 # it under the terms of the GNU General Public License as published by
11 # the Free Software Foundation; either version 3 of the License, or
12 # (at your option) any later version.
14 # This program is distributed in the hope that it will be useful,
15 # but WITHOUT ANY WARRANTY; without even the implied warranty of
16 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 # GNU General Public License for more details.
19 # You should have received a copy of the GNU General Public License
20 # along with this program. If not, see <http://www.gnu.org/licenses/>.
23 import samba.getopt as options
24 import ldb
25 from ldb import LdbError
27 from samba.auth import system_session
28 from samba.netcmd import (
29 Command,
30 CommandError,
31 SuperCommand,
32 Option,
34 from samba.samdb import SamDB
37 class cmd_fsmo_seize(Command):
38 """Seize the role"""
40 synopsis = "%prog [options]"
42 takes_options = [
43 Option("-H", "--URL", help="LDB URL for database or target server", type=str,
44 metavar="URL", dest="H"),
45 Option("--force", help="Force seizing of the role without attempting to transfer first.", action="store_true"),
46 Option("--role", type="choice", choices=["rid", "pdc", "infrastructure","schema","naming","all"],
47 help="""The FSMO role to seize or transfer.\n
48 rid=RidAllocationMasterRole\n
49 schema=SchemaMasterRole\n
50 pdc=PdcEmulationMasterRole\n
51 naming=DomainNamingMasterRole\n
52 infrastructure=InfrastructureMasterRole\n
53 all=all of the above"""),
56 takes_args = []
58 def seize_role(self, role, samdb, force):
59 res = samdb.search("",
60 scope=ldb.SCOPE_BASE, attrs=["dsServiceName"])
61 assert len(res) == 1
62 serviceName = res[0]["dsServiceName"][0]
63 domain_dn = samdb.domain_dn()
64 m = ldb.Message()
65 if role == "rid":
66 m.dn = ldb.Dn(samdb, self.rid_dn)
67 elif role == "pdc":
68 m.dn = ldb.Dn(samdb, domain_dn)
69 elif role == "naming":
70 m.dn = ldb.Dn(samdb, self.naming_dn)
71 elif role == "infrastructure":
72 m.dn = ldb.Dn(samdb, self.infrastructure_dn)
73 elif role == "schema":
74 m.dn = ldb.Dn(samdb, self.schema_dn)
75 else:
76 raise CommandError("Invalid FSMO role.")
77 #first try to transfer to avoid problem if the owner is still active
78 if force is None:
79 self.message("Attempting transfer...")
80 try:
81 self.transfer_role(role, samdb)
82 except LdbError, (num, _):
83 #transfer failed, use the big axe...
84 self.message("Transfer unsuccessful, seizing...")
85 m["fSMORoleOwner"]= ldb.MessageElement(
86 serviceName, ldb.FLAG_MOD_REPLACE,
87 "fSMORoleOwner")
88 else:
89 self.message("Will not attempt transfer, seizing...")
90 m["fSMORoleOwner"]= ldb.MessageElement(
91 serviceName, ldb.FLAG_MOD_REPLACE,
92 "fSMORoleOwner")
93 try:
94 samdb.modify(m)
95 except LdbError, (num, msg):
96 raise CommandError("Failed to initiate role seize of '%s' role: %s" % (role, msg))
97 self.outf.write("FSMO transfer of '%s' role successful\n" % role)
99 def run(self, force=None, H=None, role=None,
100 credopts=None, sambaopts=None, versionopts=None):
102 lp = sambaopts.get_loadparm()
103 creds = credopts.get_credentials(lp, fallback_machine=True)
105 samdb = SamDB(url=H, session_info=system_session(),
106 credentials=creds, lp=lp)
108 if role == "all":
109 self.seize_role("rid", samdb, force)
110 self.seize_role("pdc", samdb, force)
111 self.seize_role("naming", samdb, force)
112 self.seize_role("infrastructure", samdb, force)
113 self.seize_role("schema", samdb, force)
114 else:
115 self.seize_role(role, samdb, force)
118 class cmd_fsmo_show(Command):
119 """Show the roles"""
121 synopsis = "%prog [options]"
123 takes_options = [
124 Option("-H", "--URL", help="LDB URL for database or target server", type=str,
125 metavar="URL", dest="H"),
128 takes_args = []
130 def run(self, H=None, credopts=None, sambaopts=None, versionopts=None):
131 lp = sambaopts.get_loadparm()
132 creds = credopts.get_credentials(lp, fallback_machine=True)
134 samdb = SamDB(url=H, session_info=system_session(),
135 credentials=creds, lp=lp)
137 domain_dn = samdb.domain_dn()
138 self.infrastructure_dn = "CN=Infrastructure," + domain_dn
139 self.naming_dn = "CN=Partitions,%s" % samdb.get_config_basedn()
140 self.schema_dn = samdb.get_schema_basedn()
141 self.rid_dn = "CN=RID Manager$,CN=System," + domain_dn
143 res = samdb.search(self.infrastructure_dn,
144 scope=ldb.SCOPE_BASE, attrs=["fSMORoleOwner"])
145 assert len(res) == 1
146 self.infrastructureMaster = res[0]["fSMORoleOwner"][0]
148 res = samdb.search(domain_dn,
149 scope=ldb.SCOPE_BASE, attrs=["fSMORoleOwner"])
150 assert len(res) == 1
151 self.pdcEmulator = res[0]["fSMORoleOwner"][0]
153 res = samdb.search(self.naming_dn,
154 scope=ldb.SCOPE_BASE, attrs=["fSMORoleOwner"])
155 assert len(res) == 1
156 self.namingMaster = res[0]["fSMORoleOwner"][0]
158 res = samdb.search(self.schema_dn,
159 scope=ldb.SCOPE_BASE, attrs=["fSMORoleOwner"])
160 assert len(res) == 1
161 self.schemaMaster = res[0]["fSMORoleOwner"][0]
163 res = samdb.search(self.rid_dn,
164 scope=ldb.SCOPE_BASE, attrs=["fSMORoleOwner"])
165 assert len(res) == 1
166 self.ridMaster = res[0]["fSMORoleOwner"][0]
168 self.message("InfrastructureMasterRole owner: " + self.infrastructureMaster)
169 self.message("RidAllocationMasterRole owner: " + self.ridMaster)
170 self.message("PdcEmulationMasterRole owner: " + self.pdcEmulator)
171 self.message("DomainNamingMasterRole owner: " + self.namingMaster)
172 self.message("SchemaMasterRole owner: " + self.schemaMaster)
175 class cmd_fsmo_transfer(Command):
176 """Transfer the role"""
178 synopsis = "%prog [options]"
180 takes_options = [
181 Option("-H", "--URL", help="LDB URL for database or target server", type=str,
182 metavar="URL", dest="H"),
183 Option("--role", type="choice", choices=["rid", "pdc", "infrastructure","schema","naming","all"],
184 help="""The FSMO role to seize or transfer.\n
185 rid=RidAllocationMasterRole\n
186 schema=SchemaMasterRole\n
187 pdc=PdcEmulationMasterRole\n
188 naming=DomainNamingMasterRole\n
189 infrastructure=InfrastructureMasterRole\n
190 all=all of the above"""),
193 takes_args = []
195 def transfer_role(self, role, samdb):
196 m = ldb.Message()
197 m.dn = ldb.Dn(samdb, "")
198 if role == "rid":
199 m["becomeRidMaster"]= ldb.MessageElement(
200 "1", ldb.FLAG_MOD_REPLACE,
201 "becomeRidMaster")
202 elif role == "pdc":
203 domain_dn = samdb.domain_dn()
204 res = samdb.search(domain_dn,
205 scope=ldb.SCOPE_BASE, attrs=["objectSid"])
206 assert len(res) == 1
207 sid = res[0]["objectSid"][0]
208 m["becomePdc"]= ldb.MessageElement(
209 sid, ldb.FLAG_MOD_REPLACE,
210 "becomePdc")
211 elif role == "naming":
212 m["becomeDomainMaster"]= ldb.MessageElement(
213 "1", ldb.FLAG_MOD_REPLACE,
214 "becomeDomainMaster")
215 samdb.modify(m)
216 elif role == "infrastructure":
217 m["becomeInfrastructureMaster"]= ldb.MessageElement(
218 "1", ldb.FLAG_MOD_REPLACE,
219 "becomeInfrastructureMaster")
220 elif role == "schema":
221 m["becomeSchemaMaster"]= ldb.MessageElement(
222 "1", ldb.FLAG_MOD_REPLACE,
223 "becomeSchemaMaster")
224 else:
225 raise CommandError("Invalid FSMO role.")
226 try:
227 samdb.modify(m)
228 except LdbError, (num, msg):
229 raise CommandError("Failed to initiate transfer of '%s' role: %s" % (role, msg))
230 self.outf.write("FSMO transfer of '%s' role successful\n" % role)
232 def run(self, force=None, H=None, role=None,
233 credopts=None, sambaopts=None, versionopts=None):
235 lp = sambaopts.get_loadparm()
236 creds = credopts.get_credentials(lp, fallback_machine=True)
238 samdb = SamDB(url=H, session_info=system_session(),
239 credentials=creds, lp=lp)
241 if role == "all":
242 self.transfer_role("rid", samdb)
243 self.transfer_role("pdc", samdb)
244 self.transfer_role("naming", samdb)
245 self.transfer_role("infrastructure", samdb)
246 self.transfer_role("schema", samdb)
247 else:
248 self.transfer_role(role, samdb)
251 class cmd_fsmo(SuperCommand):
252 """Flexible Single Master Operations (FSMO) roles management"""
254 subcommands = {}
255 subcommands["seize"] = cmd_fsmo_seize()
256 subcommands["show"] = cmd_fsmo_show()
257 subcommands["transfer"] = cmd_fsmo_transfer()