private int RunAutomation(GuidCollection bulletins) { Console.Write("\n\n"); string now = DateTime.Now.ToString("yyyyMMddHHmmss"); operation_log = "journal_" + now.ToString() + ".log"; int i = 0; try { SecurityContextManager.SetContextData(); PatchAPI wrap = new PatchAPI(); string name = ""; if (config.Dry_Run) { Console.WriteLine("\n######## THIS IS A DRY RUN ########"); } foreach (Guid bulletin in bulletins) { name = Item.GetItem(bulletin).Name; Console.WriteLine(""); Console.WriteLine("Processing bulletin {0} ({1}) now.", name, bulletin); if (wrap.IsStaged(bulletin.ToString())) { Console.WriteLine("\tThis bulletin is already staged."); } else { if (config.RecreateMissingPolicies || config.Retarget) { // Skip this bulletin as it is not yet downloaded continue; } Console.WriteLine("\t... bulletin will be staged now."); if (!config.Dry_Run) { try { wrap.EnsureStaged(bulletin.ToString(), true); LogOp(String.Format("{0}: Staged bulletin {1} (guid={2}).", DateTime.Now.ToString(), name, bulletin.ToString())); } catch { // Do not retry staging error. Any download error is retried at the task level. Other errors won't be solved by retry... if (config.ExcludeOnFail) { DatabaseAPI.ExecuteNonQuery("insert patchautomation_excluded (bulletin) values ('" + name + "')"); Console.WriteLine("Failed to stage bulletin {0} - the bulletin is now excluded.", name); } else { Console.WriteLine("Failed to stage bulletin {0} - skipping the bulletin now.", name); } continue; // Go to the next bulletin } } Console.WriteLine("\tBulletin is now staged."); } Console.WriteLine("\tChecking if we need to create a new policy now."); string policies_str = wrap.ResolveToPolicies(bulletin.ToString()); string[] policies_arr = policies_str.Split(','); if (!config.Retarget && (policies_str == "" || policies_str.Length == 0 || config.Create_Duplicates)) { Console.WriteLine("\t... create a policy for the bulletin now."); if (!config.Dry_Run) { int j = 0; // Used for retry count retry_create_policy: try { if (config.Target_Guids.Count == 0) { wrap.CreateUpdatePolicy(name, bulletin.ToString(), true); LogOp(String.Format("{0}: Created policy for bulletin {1} (guid={2})", DateTime.Now.ToString(), name, bulletin.ToString())); } else { wrap.CreateUpdatePolicy(name, bulletin.ToString(), config.Target_Guids, true); LogOp(String.Format("{0}: Created policy for bulletin {1} (guid={2}, target={3})", DateTime.Now.ToString(), name, bulletin.ToString(), config.Get_TargetGuids())); } // Added the bulletin to the exclusion list here if (config.Create_Duplicates) { DatabaseAPI.ExecuteNonQuery("insert patchautomation_excluded (bulletin) values ('" + name + "')"); } i++; } catch (Exception e) { if (j++ < 3) { Console.WriteLine(e.Message); Console.WriteLine(e.StackTrace); Console.WriteLine("\tFailed to create policy for bulletin {0} {1} time(s)...", name, j.ToString()); goto retry_create_policy; // Retry ceiling not reach - let's do it again. } else // Retried 3 times - we quit and document the problem { if (config.ExcludeOnFail) { DatabaseAPI.ExecuteNonQuery("insert patchautomation_excluded (bulletin) values ('" + name + "')"); Console.WriteLine("\tFailed to create policy for bulletin {0} 3 times - the bulletin is now excluded.", name); } else { Console.WriteLine("\tFailed to create policy for bulletin {0} 3 times - skipping the bulletin now.", name); } continue; // Go to the next bulletin } } } Console.WriteLine("\tSoftware update policy created!"); } else if (config.Retarget) { if (policies_arr.Length > 0) { /* ENHANCEMENT: 2018-01-24; There is no need to update each policy - one of them will update the "parent" policy which is enough :D. * This avoid doing the same task 153 times when an Office policy as 153 updates! * * */ // foreach (string p in policies_arr) { string p = policies_arr[0]; if (p.Length != 36) { continue; } Console.WriteLine("\tA policy already exists for this bulletin..."); Guid policyGuid = new Guid(p); SoftwareUpdateAdvertismentSetPolicy policyItem = Item.GetItem <SoftwareUpdateAdvertismentSetPolicy>(policyGuid, ItemLoadFlags.Writeable); Console.WriteLine("\tPolicy {0} will be retargetted now.", policyItem.Name); policyItem.ResourceTargets.Clear(); foreach (string target in config.Target_Guids) { policyItem.ResourceTargets.Add(new Guid(target)); } if (!config.Dry_Run) { int retry = 0; save_item: try { policyItem.Save(); LogOp(String.Format("{0}: Retargetted policy for bulletin {1} (guid={2}, new target={3})", DateTime.Now.ToString(), name, bulletin.ToString(), config.Get_TargetGuids())); i++; } catch { Console.WriteLine("\tCaught an exception. Retry " + retry.ToString() + "will start now."); if (retry < 10) { goto save_item; } Console.WriteLine("\tSaving the policy failed 10 times. Moving on to the next item."); } } // } // Commented out for each node removed to fix } } else { Console.WriteLine("\tA policy already exists for this bulletin."); } if (i > 9 && config.Test_Run) { break; } } } catch (Exception e) { Console.WriteLine("Error message={0}\nInner Exception={1}\nStacktrace={2}", e.Message, e.InnerException, e.StackTrace); return(-1); } return(i); }
private int RunAutomation() { int i = 0; int rc = 0; try { GuidCollection bulletins = new GuidCollection(); bulletins = GetSoftwareBulletins(); SecurityContextManager.SetContextData(); PatchAPI wrap = new PatchAPI(); if (config.Dry_Run) { Console.WriteLine("\n######## THIS IS A DRY RUN ########"); } foreach (Guid bulletin in bulletins) { string bulletin_name = Item.GetItem(bulletin).Name; Console.WriteLine("\n### BEGIN {0}, {1}", bulletin_name, bulletin); if (wrap.IsStaged(bulletin.ToString())) { Console.WriteLine("PHASE 1: This bulletin is already staged."); } else { Console.WriteLine("PHASE 1: This bulletin will be staged now."); if (!config.Dry_Run) { try { EventLog.ReportInfo(String.Format("Bulletin {0} will be staged now.", bulletin_name)); wrap.EnsureStaged(bulletin.ToString(), true); } catch { // Do not retry staging error. Any download error is retried at the task level. Other errors won't be solved by retry... if (config.ExcludeOnFail) { DatabaseAPI.ExecuteNonQuery("insert patchautomation_excluded (bulletin) values ('" + bulletin_name + "')"); EventLog.ReportError(String.Format("Failed to stage bulletin {0} 3 times - the bulletin is now excluded.", bulletin_name)); } else { EventLog.ReportError(String.Format("Failed to stage bulletin {0} 3 times - skipping the bulletin now.", bulletin_name)); } continue; } } } string policyGuids = ""; policyGuids = wrap.ResolveToPolicies(bulletin.ToString()); if (policyGuids == "" || policyGuids.Length == 0 || config.Create_Duplicates) { string date = DateTime.Today.ToString("yyyy-MM-dd"); string policy_name = bulletin_name + ", " + config.POLICY_TEST + ", " + date; Console.WriteLine("PHASE 2: Creating policy {0} now.", policy_name); if (!config.Dry_Run) { int k = 0; //retry counter retry_policy_creation: try { wrap.CreateUpdatePolicy(policy_name, bulletin.ToString(), config.Target_Guid_Test, true); EventLog.ReportInfo(String.Format("SoftwareUpdateAdvertisement policy {0} (targetguid={1}) was created.", policy_name, config.Target_Guid_Test)); } catch { if (k++ < 3) // Policy creation is retried 3 times - as the most likely fail case i deadlock. { EventLog.ReportWarning(String.Format("Failed to create policy for bulletin {0} {1} times...", bulletin_name, k.ToString())); goto retry_policy_creation; } else // Failed three times - skip or exclude based on CLI config { if (config.ExcludeOnFail) { DatabaseAPI.ExecuteNonQuery("insert patchautomation_excluded (bulletin) values ('" + bulletin_name + "')"); EventLog.ReportError(String.Format("Failed to create policy for bulletin {0} 3 times - the bulletin is now excluded.", bulletin_name)); } else { EventLog.ReportError(String.Format("Failed to create policy for bulletin {0} 3 times - skipping the bulletin now.", bulletin_name)); } continue; } } if (config.Create_Duplicates) { DatabaseAPI.ExecuteNonQuery("insert patchautomation_excluded (bulletin) values ('" + bulletin_name + "')"); } i++; } Console.WriteLine("\tSoftware update policy created!"); } else { Console.WriteLine("PHASE 2: Policy already exists."); string[] _policyGuids = policyGuids.Split(','); foreach (string policy in _policyGuids) { Guid policyGuid = new Guid(policy); string policyName = Item.GetItem(policyGuid).Name; if (policyName.Contains(config.POLICY_TEST)) { string timestamp = policyName.Substring(policyName.Length - 10); DateTime policyDate = DateTime.Parse(timestamp); TimeSpan ts = DateTime.Today - policyDate; if (ts.Days >= config.Span_Test_To_Validation) { Console.WriteLine("PHASE 3: Policy needs retargetting (test -> validation)"); this.UpdatePolicy("TEST_TO_VALIDATION", policyGuid, timestamp); } else { Console.WriteLine("PHASE 3: Policy '{0}' doesn't need re-targetting.", policyName); } } else if (policyName.Contains(config.POLICY_VALIDATED)) { string timestamp = policyName.Substring(policyName.Length - 10); DateTime policyDate = DateTime.Parse(timestamp); TimeSpan ts = DateTime.Today - policyDate; if (ts.Days >= config.Span_Validation_To_Production) { Console.WriteLine("PHASE 4: Policy needs retargetting (validation -> production)"); this.UpdatePolicy("VALIDATION_TO_PRODUCTION", policyGuid, timestamp); } else { Console.WriteLine("PHASE 4: Policy '{0}' doesn't need re-targetting.", policyName); } } } } if (i == 10 && config.Test_Run) { break; // Limit the staging to 10 bulletin whilst testing } Console.WriteLine("### END"); rc = 0; } } catch (Exception e) { LoggingAPI.ReportException(e); rc = -2; } Console.WriteLine("\n{0} software update policy creation tasks were started.", i.ToString()); return(rc); }