Lib_CommonGPMCFunctions.js (13739B)
1 ///////////////////////////////////////////////////////////////// 2 // Copyright (c) Microsoft Corporation. All rights reserved 3 // 4 // Title: Lib_CommonGPMCFunctions.js 5 // Author: mtreit@microsoft.com 6 // Created: 7/16/2002 7 // Purpose: Provides a library of common helper functions 8 // for use when scripting the GPMC interfaces. 9 // 10 // This library must be included with the sample 11 // WSH scripts that ship with the GPMC 12 ///////////////////////////////////////////////////////////////// 13 14 /////////////////////////////////////// 15 // Initialization 16 /////////////////////////////////////// 17 18 // Create global objects for use by all of the functions 19 var GPM = new ActiveXObject("GPMgmt.GPM"); 20 var Constants = GPM.GetConstants(); 21 22 /////////////////////////////////////// 23 // Common Function Library 24 /////////////////////////////////////// 25 26 // 27 // Note: The functions in this section are shared by 28 // many of the GPMC sample scripts. This section may be 29 // pasted directly in each individual script to ensure they 30 // will work stand-alone, or may be collected in a library 31 // file and accessed using the 'include' functionality 32 // provided by the WSF script format. 33 // 34 35 // Takes a GPO name or GUID and returns the GPO 36 function GetGPO(szGPOName, GPMDomain) 37 { 38 var GPO; 39 40 // Get the GPO object for the specified GPO 41 try 42 { 43 GPO = GPMDomain.GetGPO(szGPOName); 44 } 45 catch (err) 46 { 47 // The attempt to get the GPO failed. The user may have 48 // passed in the name instead of GUID, so fetch by name. 49 try 50 { 51 GPO = GetGPOByName(szGPOName, GPMDomain); 52 } 53 catch (err) 54 { 55 WScript.Echo("Could not find GPO " + szGPOName); 56 return false; 57 } 58 } 59 60 return GPO; 61 62 } 63 64 65 // Given a GPO name or ID (GUID), returns that GPO from the directory. 66 // If no GPO is found, returns null 67 // If multiple GPOs exist by that name, returns the resulting collection 68 // 69 function GetGPOByName(szGPOName, GPMDomain) 70 { 71 // Create a search criteria object for the name 72 var GPMSearchCriteria = GPM.CreateSearchCriteria(); 73 GPMSearchCriteria.Add(Constants.SearchPropertyGPODisplayName, Constants.SearchOpEquals, szGPOName); 74 75 // Search for the specified GPO 76 var GPOList = GPMDomain.SearchGPOs(GPMSearchCriteria); 77 78 if (GPOList.Count == 0) 79 { 80 return false; // No GPO found 81 } 82 83 // The following could return a collection of multiple GPOs if more than one GPO 84 // with the same name exists in the domain 85 // 86 if (GPOList.Count == 1) 87 { 88 return GPOList.Item(1); 89 } 90 else 91 { 92 return GPOList; 93 } 94 95 } 96 97 // Retrieves the WMI filter with the specified name 98 function GetWMIFilter(szWMIFilterName, GPMDomain) 99 { 100 var GPMSearchCriteria = GPM.CreateSearchCriteria(); 101 var FilterList = GPMDomain.SearchWMIFilters(); 102 var e = new Enumerator(FilterList); 103 var WMIFilter; 104 105 for (; !e.atEnd(); e.moveNext()) 106 { 107 WMIFilter = e.item(); 108 if (WMIFilter.Name.toLowerCase() == szWMIFilterName.toLowerCase()) 109 { 110 return WMIFilter; 111 } 112 } 113 114 return false; 115 } 116 117 // Attempts to retrieve a SOM by name or path from the directory. Will return a single GPMSOM object, or 118 // an array of such objects if more than one with the given name is found. 119 // 120 function GetSOM(szSOMName, GPMDomain) 121 { 122 123 // Check if this is the domain level - if so, get the SOM for the domain and return it 124 if (szSOMName.toLowerCase() == GPMDomain.Domain.toLowerCase()) 125 { 126 return GPMDomain.GetSOM(""); // Returns the SOM representing the domain 127 } 128 129 // First try to get the SOM, in case a valid LDAP-style path was passed in 130 try 131 { 132 var GPMSOM = GPMDomain.GetSOM(szSOMName); 133 } 134 catch (err) 135 { 136 try 137 { 138 // Might be a site instead of a domain or oU 139 GPMSOM = GPMSitesContainer.GetSite(szSOMName); 140 } 141 catch (err) 142 { 143 GPMSOM = false; 144 } 145 } 146 147 if (GPMSOM) 148 { 149 return GPMSOM; 150 } 151 152 // Search for the SOM by name, using ADSI 153 154 // Create an array to hold the results, as we may find more than one SOM with the specified name 155 var aResult = new Array(); 156 157 // Define ADS related values - see IADS.h 158 var ADS_SCOPE_BASE = 0; 159 var ADS_SCOPE_ONELEVEL = 1; 160 var ADS_SCOPE_SUBTREE = 2; 161 var ADSIPROP_CHASE_REFERRALS = 0x9; 162 var ADS_CHASE_REFERRALS_NEVER = 0; 163 var ADS_CHASE_REFERRALS_SUBORDINATE = 0x20; 164 var ADS_CHASE_REFERRALS_EXTERNAL = 0x40; 165 var ADS_CHASE_REFERRALS_ALWAYS = ADS_CHASE_REFERRALS_SUBORDINATE | ADS_CHASE_REFERRALS_EXTERNAL; 166 167 var szLDAPSuffix = GPMDomain.GetSOM("").Path; 168 169 // Create the ADO objects and open the connection 170 var ADOConnection = new ActiveXObject("ADODB.Connection"); 171 var ADOCommand = new ActiveXObject("ADODB.Command"); 172 ADOConnection.Provider = "ADsDSOObject"; 173 ADOConnection.Open("Active Directory Provider"); 174 ADOCommand.ActiveConnection = ADOConnection; 175 176 // First look for OUs 177 var szDomainLDAPPath = "LDAP://" + szLDAPSuffix; 178 var szSQL = "select AdsPath from '" + EscapeString(szDomainLDAPPath) + "'"; 179 szSQL += " where Name='" + szSOMName + "'"; 180 181 // Execute the search 182 ADOCommand.CommandText = szSQL; 183 ADOCommand.Properties("Page Size") = 1000; 184 ADOCommand.Properties("Timeout") = 500; 185 ADOCommand.Properties("SearchScope") = ADS_SCOPE_SUBTREE; 186 ADOCommand.Properties("Cache Results") = false; 187 ADOCommand.Properties("Chase Referrals") = ADS_CHASE_REFERRALS_EXTERNAL; // Needed when querying a different domain 188 189 try 190 { 191 var rs = ADOCommand.Execute(); 192 } 193 catch (err) 194 { 195 WScript.Echo("There was an error executing the DS query " + szSQL); 196 WScript.Echo("The error was:"); 197 WScript.Echo(ErrCode(err.number) + " - " + err.description); 198 return false; 199 } 200 201 var SOM; 202 while ( ! rs.eof ) 203 { 204 SOM = GetObject(rs.Fields(0)); 205 206 // Ignore objects that are not OUs or the domain level 207 if (SOM.Class == 'organizationalUnit' || SOM.Class == 'fTDfs') 208 { 209 GPMSOM = GPMDomain.GetSOM(SOM.ADsPath) 210 aResult = aResult.concat(GPMSOM); 211 } 212 213 rs.MoveNext(); 214 } 215 216 // Get the LDAP suffix from the forest name 217 ForestDomain = GPM.GetDomain(szForestName, "", Constants.UseAnyDC); 218 szLDAPSuffix = ForestDomain.GetSOM("").Path; 219 220 var szSitesLDAPPath = "LDAP://CN=Sites,CN=Configuration," + szLDAPSuffix; 221 var szSQL = "select AdsPath from '" + EscapeString(szSitesLDAPPath) + "'"; 222 szSQL += " where Name='" + szSOMName + "'"; 223 224 // Execute the search 225 ADOCommand.CommandText = szSQL; 226 227 try 228 { 229 var rs = ADOCommand.Execute(); 230 } 231 catch (err) 232 { 233 WScript.Echo("There was an error executing the DS query " + szSQL); 234 WScript.Echo("The error was:"); 235 WScript.Echo(ErrCode(err.number) + " - " + err.description); 236 return false; 237 } 238 239 while ( ! rs.eof ) 240 { 241 SOM = GetObject(rs.Fields(0)); 242 if (SOM.Class == 'site') 243 { 244 GPMSOM = GPMSitesContainer.GetSite(SOM.Name) 245 aResult = aResult.concat(GPMSOM); 246 } 247 248 rs.MoveNext(); 249 } 250 251 // Cleanup 252 ADOConnection.Close(); 253 254 // Return the result 255 if (aResult.length == 1) 256 { 257 return aResult[0]; 258 } 259 260 if (aResult.length == 0) 261 { 262 return false; 263 } 264 265 return aResult; 266 } 267 268 // Retrieves a specific backup from the specified location 269 function GetBackup(szBackupLocation, szBackupID) 270 { 271 var GPMBackup; 272 var GPMBackupDir; 273 274 // Get the backup directory specified 275 try 276 { 277 GPMBackupDir = GPM.GetBackupDir(szBackupLocation); 278 } 279 catch (err) 280 { 281 WScript.Echo("The specified backup folder '" + szBackupLocation + "' could not be accessed."); 282 return false; 283 } 284 285 // See if we were passed a valid backup ID 286 try 287 { 288 GPMBackup = GPMBackupDir.GetBackup(szBackupID); 289 } 290 catch (err) 291 { 292 GPMBackup = false; 293 } 294 295 if (!GPMBackup) 296 { 297 // Not a valid backup ID, so fetch backup by GPO name 298 var GPMSearchCriteria = GPM.CreateSearchCriteria(); 299 GPMSearchCriteria.Add(Constants.SearchPropertyBackupMostRecent, Constants.SearchOpEquals, true); 300 GPMSearchCriteria.Add(Constants.SearchPropertyGPODisplayName, Constants.SearchOpEquals, szBackupID); 301 var BackupList = GPMBackupDir.SearchBackups(GPMSearchCriteria); 302 303 if (BackupList.Count == 0) 304 { 305 WScript.Echo("The specified backup '" + szBackupID + "' was not found in folder '" + szBackupLocation); 306 return false; 307 } 308 else 309 { 310 GPMBackup = BackupList.Item(1); 311 } 312 } 313 314 return GPMBackup; 315 } 316 317 // Prints any status messages for a GPO operation, such as backup or import 318 function PrintStatusMessages(GPMResult) 319 { 320 var GPMStatus = GPMResult.Status; 321 322 if (GPMStatus.Count == 0) 323 { 324 // No messages, so just return 325 return; 326 } 327 328 WScript.Echo(""); 329 var e = new Enumerator(GPMStatus); 330 for (; !e.atEnd(); e.moveNext()) 331 { 332 WScript.Echo(e.item().Message); 333 } 334 } 335 336 // Returns the DNS domain name for the current user, using ADSI 337 function GetDNSDomainForCurrentUser() 338 { 339 340 var ADS_NAME_INITTYPE_DOMAIN = 1; 341 var ADS_NAME_INITTYPE_SERVER = 2; 342 var ADS_NAME_INITTYPE_GC = 3; 343 344 var ADS_NAME_TYPE_1779 = 1; // "CN=Jane Doe,CN=users, DC=Microsoft, DC=com" 345 var ADS_NAME_TYPE_CANONICAL = 2; // "Microsoft.com/Users/Jane Doe". 346 var ADS_NAME_TYPE_NT4 = 3; // "Microsoft\JaneDoe" 347 var ADS_NAME_TYPE_DISPLAY = 4; // "Jane Doe" 348 var ADS_NAME_TYPE_DOMAIN_SIMPLE = 5; // "JaneDoe@Microsoft.com" 349 var ADS_NAME_TYPE_ENTERPRISE_SIMPLE = 6; // "JaneDoe@Microsoft.com" 350 var ADS_NAME_TYPE_GUID = 7; // {95ee9fff-3436-11d1-b2b0-d15ae3ac8436} 351 var ADS_NAME_TYPE_UNKNOWN = 8; // The system will try to make the best guess 352 var ADS_NAME_TYPE_USER_PRINCIPAL_NAME = 9; // "JaneDoe@Fabrikam.com" 353 var ADS_NAME_TYPE_CANONICAL_EX = 10; // "Microsoft.com/Users Jane Doe" 354 var ADS_NAME_TYPE_SERVICE_PRINCIPAL_NAME = 11; // "www/www.microsoft.com@microsoft.com" 355 var ADS_NAME_TYPE_SID_OR_SID_HISTORY_NAME = 12; // "O:AOG:DAD:(A;;RPWPCCDCLCSWRCWDWOGA;;;S-1-0-0)" 356 357 358 var objWshNetwork = new ActiveXObject("Wscript.Network"); 359 var objectNameTranslate = new ActiveXObject("NameTranslate"); 360 var arrNamePart; 361 var strNTPath = ""; 362 var strTranslatedName = ""; 363 var strResult = ""; 364 365 strUser = objWshNetwork.UserName; 366 strDomain = objWshNetwork.UserDomain; 367 strNTPath = strDomain + "\\" + strUser; 368 369 objectNameTranslate.Init(ADS_NAME_INITTYPE_DOMAIN, strDomain); 370 objectNameTranslate.Set(ADS_NAME_TYPE_NT4, strNTPath); 371 strTranslatedName = objectNameTranslate.Get(ADS_NAME_TYPE_CANONICAL); 372 373 arrNamePart = strTranslatedName.split("/"); 374 strResult = arrNamePart[0]; 375 376 return strResult; 377 } 378 379 // Use ADSI to get the LDAP-style forest name of a given domain 380 function GetForestLDAPPath(szDomainName) 381 { 382 // Get the RootDSE naming context for the specified domain 383 var RootDSE = GetObject("LDAP://" + szDomainName + "/RootDSE"); 384 385 // Initialize the property cache 386 RootDSE.GetInfo(); 387 388 // Now get the forest name 389 var szForestName = RootDSE.rootDomainNamingContext; 390 391 return szForestName; 392 } 393 394 // Use ADSI to get the forest name of a given domain 395 function GetForestDNSName(szDomainName) 396 { 397 var ADS_NAME_INITTYPE_DOMAIN = 1; 398 var ADS_NAME_INITTYPE_SERVER = 2; 399 var ADS_NAME_INITTYPE_GC = 3; 400 401 var ADS_NAME_TYPE_1779 = 1; // "CN=Jane Doe,CN=users, DC=Microsoft, DC=com" 402 var ADS_NAME_TYPE_CANONICAL = 2; // "Microsoft.com/Users/Jane Doe". 403 var ADS_NAME_TYPE_NT4 = 3; // "Microsoft\JaneDoe" 404 var ADS_NAME_TYPE_DISPLAY = 4; // "Jane Doe" 405 var ADS_NAME_TYPE_DOMAIN_SIMPLE = 5; // "JaneDoe@Microsoft.com" 406 var ADS_NAME_TYPE_ENTERPRISE_SIMPLE = 6; // "JaneDoe@Microsoft.com" 407 var ADS_NAME_TYPE_GUID = 7; // {95ee9fff-3436-11d1-b2b0-d15ae3ac8436} 408 var ADS_NAME_TYPE_UNKNOWN = 8; // The system will try to make the best guess 409 var ADS_NAME_TYPE_USER_PRINCIPAL_NAME = 9; // "JaneDoe@Fabrikam.com" 410 var ADS_NAME_TYPE_CANONICAL_EX = 10; // "Microsoft.com/Users Jane Doe" 411 var ADS_NAME_TYPE_SERVICE_PRINCIPAL_NAME = 11; // "www/www.microsoft.com@microsoft.com" 412 var ADS_NAME_TYPE_SID_OR_SID_HISTORY_NAME = 12; // "O:AOG:DAD:(A;;RPWPCCDCLCSWRCWDWOGA;;;S-1-0-0)" 413 414 415 // Get the RootDSE naming context for the specified domain 416 var RootDSE = GetObject("LDAP://" + szDomainName + "/RootDSE"); 417 418 // Initialize the property cache 419 RootDSE.GetInfo(); 420 421 // Now get the forest name 422 var szForestName = RootDSE.rootDomainNamingContext; 423 424 // Translate it to DNS style 425 var objectNameTranslate = new ActiveXObject("NameTranslate"); 426 objectNameTranslate.Init(ADS_NAME_INITTYPE_DOMAIN, szDomainName); 427 objectNameTranslate.Set(ADS_NAME_TYPE_1779, szForestName); 428 429 var szTranslatedName = objectNameTranslate.Get(ADS_NAME_TYPE_CANONICAL); 430 431 return szTranslatedName.slice(0,-1); 432 } 433 434 // Escapes certain characters in a string so they will work with SQL statements 435 function EscapeString(str) 436 { 437 var result; 438 439 // Handle single quotes 440 var re = new RegExp(/'/g); 441 result = str.replace(re, "''"); 442 return result; 443 } 444 445 // Replaces invalid characters in a file name 446 function GetValidFileName(str) 447 { 448 var result = str; 449 result = result.replace(/\*/g, ""); 450 result = result.replace(/\\/g, ""); 451 result = result.replace(/\//g, ""); 452 result = result.replace(/\|/g, ""); 453 result = result.replace(/>/g, ""); 454 result = result.replace(/</g, ""); 455 result = result.replace(/:/g, ""); 456 result = result.replace(/\"/g, ""); 457 result = result.replace(/\?/g, ""); 458 459 return result; 460 } 461 462 // Checks if the specified file system path is valid. 463 // Returns true if the path is found, false otherwise. 464 // 465 function ValidatePath(szPath) 466 { 467 var fso = new ActiveXObject("Scripting.FileSystemObject"); 468 try 469 { 470 var Path = fso.GetFolder(szPath); 471 } 472 catch (err) 473 { 474 return false; 475 } 476 477 return true; 478 } 479 480 // Returns the hexadecimal string for a number, converting negative decimal 481 // values to the appropriate winerror style hex values 482 // 483 function ErrCode(i) 484 { 485 var result; 486 487 if (i < 0) 488 { 489 // Get the winerror-style representation of the hex value 490 result = 0xFFFFFFFF + i + 1; 491 } 492 else 493 { 494 result = i; 495 } 496 497 return "0x" + result.toString(16); // base 16 498 }