deleriumbg

Scheduled Task

Jul 29th, 2019
382
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C# 18.73 KB | None | 0 0
  1. using System;
  2. using System.Configuration;
  3. using System.Collections.Generic;
  4. using System.Linq;
  5. using System.Text;
  6. using Automating_Approval_of_Registration.Models;
  7. using log4net;
  8. using Microsoft.Crm.Sdk.Messages;
  9. using Microsoft.Xrm.Sdk;
  10. using UOP.Portal.Gateway.Services.DAL;
  11.  
  12. namespace Automating_Approval_of_Registration.Helpers
  13. {
  14.     public class TaskHelper
  15.     {
  16.         private const string TableStyle =
  17.             "<table style='width:100%; border-top: 1px solid black;border-left:1px solid black; border-collapse: collapse;'>";
  18.         private const string TableRowStyle =
  19.             "<th style='border-right: 1px solid black;border-bottom:1px solid black;text-align: left; padding: 5px;'>";
  20.         private const string Subject = "Automating Approval of Registration - Summary";
  21.         private readonly string _crmAccountUrl = ConfigurationManager.AppSettings["CRM_ACCOUNT_BASE_URL"];
  22.         private readonly ILog _logger;
  23.         private readonly bool _forceMode;
  24.         private readonly CrmConnection _connection;
  25.         private readonly DGuidsHelper _guidsHelper;
  26.         private readonly CrmHelper _helper;
  27.         private List<RegistrationData> _registrations;
  28.         private List<RegistrationData> _successes;
  29.         private List<RegistrationData> _failures;
  30.         private readonly StringBuilder _totalIds = new StringBuilder();
  31.         private readonly StringBuilder _successIds = new StringBuilder();
  32.         private readonly StringBuilder _failedIds = new StringBuilder();
  33.        
  34.  
  35.         public DateTime ServerDate = DateTime.Now;
  36.         public New_timeperiod NextTerm;
  37.  
  38.         public TaskHelper(ILog logger, bool forceMode)
  39.         {
  40.             this._forceMode = forceMode;
  41.             this._logger = logger;
  42.             this._connection = new CrmConnection(logger);
  43.             this._guidsHelper = new DGuidsHelper(_connection, logger);
  44.             this._helper = new CrmHelper(_connection, logger);
  45.             this._registrations = new List<RegistrationData>();
  46.             this._successes = new List<RegistrationData>();
  47.             this._failures = new List<RegistrationData>();
  48.         }
  49.  
  50.         public void Execute()
  51.         {
  52.             //1. Task triggers:
  53.             bool trigger = CheckTaskTriggers();
  54.             if (trigger)
  55.             {
  56.                 try
  57.                 {
  58.                     //3.1. Reporting compliance:
  59.                     //3.2. Create UoPeople process record with the following attributes:
  60.                     Guid uopProcessId = _helper.CreateUopProcess();
  61.  
  62.                     // Getting required lookup values section
  63.                     if (!_helper.InitializingRequiredGuids())
  64.                     {
  65.                         UpdateUopProcess(uopProcessId, (int)PortalEnums.UopeopleProcessRequeststatus.Faild, _totalIds.ToString(),
  66.                             "Issue in getting required guids", _successIds.ToString());
  67.                         _logger.Error($"Error in retrieving the required guids. Aborting task {nameof(Automating_Approval_of_Registration)}");
  68.                         _guidsHelper.SendEmailToSupport($"Error in task {nameof(Automating_Approval_of_Registration)}", "Error in retrieving the required guids.");
  69.                         return;
  70.                     }
  71.  
  72.                     //3.4. Search for registrations that:
  73.                     //3.4.1. Term = next term.
  74.                     //3.4.2. Registration status = “open”.
  75.                     //3.4.3. Registration sub - status = “processing request”.
  76.                     //3.4.4. In associated student: program funding = “on my own” OR “scholarships”.
  77.                     _registrations = _helper.RetrieveNextTermRegistrations(NextTerm);
  78.                     if (_registrations.Count == 0)
  79.                     {
  80.                         _logger.Error($"No registrations meeting the criteria found for term {NextTerm.New_name}. " +
  81.                                       $"Aborting {nameof(Automating_Approval_of_Registration)} execution.");
  82.                         return;
  83.                     }
  84.  
  85.                     //// QA Test
  86.                     //var testRegistrationIds = new []
  87.                     //{
  88.                     //    "Reg1042585",
  89.                     //    "Reg1042614",
  90.                     //    "Reg1042618",
  91.                     //    "Reg1042611",
  92.                     //    "Reg1042613",
  93.                     //    "Reg1042620",
  94.                     //    "Reg1042326",
  95.                     //    "Reg1042612",
  96.                     //    "Reg1042619"
  97.                     //};
  98.  
  99.                     //_registrations = _registrations.Where(r => testRegistrationIds.Contains(r.RegistrationName)).ToList();
  100.                     //// End of QA Test
  101.  
  102.                     foreach (var currentRegistration in _registrations)
  103.                     {
  104.                         try
  105.                         {
  106.                             //3.5. For each record found:
  107.                             //3.5.1. Set “registration sub-status” = “registered”.
  108.                             //3.5.2. Set “registration sub status reason” = “your request has been approved”.
  109.                             //3.5.3. Set “payment creation status” = “requires payment creation”.
  110.                             //3.5.4. Save relevant registration.
  111.                             _logger.Info($"Updating registration {currentRegistration.RegistrationName} with id {currentRegistration.RegistrationId}...");
  112.                             New_enrollment registrationToUpdate = new New_enrollment
  113.                             {
  114.                                 Id = currentRegistration.RegistrationId,
  115.                                 New_RegistrationSubStatusId = new EntityReference(
  116.                                     New_registrationsubstatus.EntityLogicalName,
  117.                                     _helper.RegistrationSubStatusRegistered),
  118.                                 New_RegistrationSubStatusReasonId = new EntityReference(
  119.                                     New_registrationsubstatusreason.EntityLogicalName,
  120.                                     _helper.RegistrationSubStatusReasonApproved),
  121.                                 new_PaymentCreationStatus =
  122.                                     new OptionSetValue((int)PortalEnums.PaymentCreationStatus.RequiresPayemntCreation)
  123.                             };
  124.  
  125.                             _connection.Service.Update(registrationToUpdate);
  126.                             _logger.Info($"Successfully updated registration {currentRegistration.RegistrationName} with id {currentRegistration.RegistrationId}");
  127.                             _successes.Add(currentRegistration);
  128.                             _successIds.AppendLine(currentRegistration.RegistrationId.ToString());
  129.                         }
  130.                         catch (Exception e)
  131.                         {
  132.                             _logger.Error($"Exception while updating registration with id {currentRegistration.RegistrationId}. Details: {e}");
  133.                             currentRegistration.IssueDescription = e.Message;
  134.                             _failures.Add(currentRegistration);
  135.                             _failedIds.AppendLine(currentRegistration.RegistrationId.ToString());
  136.                         }
  137.                         finally
  138.                         {
  139.                             _totalIds.AppendLine(currentRegistration.RegistrationId.ToString());
  140.                         }
  141.                     }
  142.  
  143.                     //3.6. Send email to task owners stored in (university rule: student services – approving registrations – task owners)
  144.                     List<string> taskOwners = _helper.RetrieveTaskOwners();
  145.                     bool emailsSent = SendEmailToTaskOwners(taskOwners, uopProcessId);
  146.                     if (emailsSent)
  147.                     {
  148.                         _logger.Info($"Email to task owners sent successfully.");
  149.                     }
  150.                     else
  151.                     {
  152.                         _logger.Error("Unable to send email to task owners.");
  153.                         _guidsHelper.SendEmailToSupport($"Error in task {nameof(Automating_Approval_of_Registration)}",
  154.                             $"Unable to send email to task owners: {string.Join(",", taskOwners)}.");
  155.                     }
  156.  
  157.                     //3.7. Reporting compliance:
  158.                     //3.8. If any system failure occurred during the execution:
  159.                     //3.8.1. Update UoPeople process record
  160.                     if (_failures.Count > 0)
  161.                     {
  162.                         UpdateUopProcess(uopProcessId, (int)PortalEnums.UopeopleProcessRequeststatus.Faild, _totalIds.ToString(),
  163.                             _failedIds.ToString(), _successIds.ToString());
  164.                     }
  165.                     else
  166.                     {
  167.                         UpdateUopProcess(uopProcessId, (int)PortalEnums.UopeopleProcessRequeststatus.Completed, _totalIds.ToString(),
  168.                             _failedIds.ToString(), _successIds.ToString());
  169.                     }
  170.                 }
  171.                 catch (Exception ex)
  172.                 {
  173.                     _logger.Error($"An error occurred while executing {nameof(Automating_Approval_of_Registration)}. Details: {ex}");
  174.                     _guidsHelper.SendEmailToSupport($"Error in task {nameof(Automating_Approval_of_Registration)}", "Error details: " + ex);
  175.                 }
  176.             }
  177.         }
  178.  
  179.  
  180.         #region Private Methods
  181.  
  182.         private bool CheckTaskTriggers()
  183.         {
  184.             //1.1.1. The task shall execute the logic if:
  185.             //1.1.1.1. Current date = “date to approve registrations” for next term.
  186.             NextTerm = _helper.GetNextTerm(ServerDate);
  187.  
  188.             if (NextTerm != null)
  189.             {
  190.                 _logger.Info($"{nameof(CheckTaskTriggers)} returned term {NextTerm.New_name} with date to approve registrations {NextTerm.new_datetoapproveregistrations}");
  191.                 if (NextTerm.new_datetoapproveregistrations != null && ServerDate.Date == NextTerm.new_datetoapproveregistrations.Value.Date)
  192.                 {
  193.                     _logger.Info($"Date to approve registration in {NextTerm.New_name} matches the current date {ServerDate.Date}. The scheduled task begins execution...");
  194.                     return true;
  195.                 }
  196.                 else
  197.                 {
  198.                     _logger.Info($"Date to approve registration in {NextTerm.New_name} is different that current date {ServerDate.Date}. Aborting scheduled task execution.");
  199.                     return false;
  200.                 }
  201.             }
  202.             return false;
  203.         }
  204.  
  205.         private void UpdateUopProcess(Guid uopProcessId, int uopProcessStatus, string totalRecordIds, string failIds, string successIds)
  206.         {
  207.             if (uopProcessId != Guid.Empty)
  208.             {
  209.                 _logger.Info("Updating UOP Process....");
  210.                 try
  211.                 {
  212.                     new_crmisvrequest uopProcessToUpdate = new new_crmisvrequest
  213.                     {
  214.                         Id = uopProcessId,
  215.                         new_successes = _successes.Count,
  216.                         new_failures = _failures.Count,
  217.                         new_total = _registrations.Count,
  218.                         new_requeststatus = new OptionSetValue(uopProcessStatus),
  219.                         new_failedrecordsids = failIds,
  220.                         new_totalrecordids = totalRecordIds,
  221.                         new_succeededrecordsids = successIds,
  222.                         new_Datecompleted = DateTime.Now,
  223.                         new_Datefailed = _failures.Count != 0 ? DateTime.Now : (DateTime?)null
  224.                     };
  225.  
  226.                     _connection.Service.Update(uopProcessToUpdate);
  227.                     _logger.Info($"UOP Process with id {uopProcessId} updated successfully");
  228.  
  229.                 }
  230.                 catch (Exception ex)
  231.                 {
  232.                     _logger.Error($"Error in {nameof(UpdateUopProcess)}. Details: {ex}");
  233.                 }
  234.             }
  235.             else
  236.             {
  237.                 _logger.Info("Can't update UOP Process, record id is null");
  238.             }
  239.         }
  240.  
  241.         private bool SendEmailToTaskOwners(List<string> taskOwners, Guid uopProcessId)
  242.         {
  243.             string description = BuildEmailDescription();
  244.             _logger.Debug($"Executing {nameof(SendEmailToTaskOwners)}, subject: {Subject}, description: {description}");
  245.  
  246.             try
  247.             {
  248.                 var service = _connection.Service;
  249.  
  250.                 // Create the 'From:' activity party for the email
  251.                 ActivityParty fromParty = new ActivityParty
  252.                 {
  253.                     PartyId = new EntityReference(Queue.EntityLogicalName, _helper.StudentServicesQueueId)
  254.                 };
  255.  
  256.                 // Create the 'To:' activity party for the email
  257.                 List<ActivityParty> toParties = new List<ActivityParty>();
  258.  
  259.                 foreach (string emailAddress in taskOwners)
  260.                 {
  261.                     ActivityParty toParty = new ActivityParty
  262.                     {
  263.                         AddressUsed = emailAddress
  264.                     };
  265.  
  266.                     toParties.Add(toParty);
  267.                 }
  268.  
  269.                 // Create an email message entity
  270.                 Email email = new Email
  271.                 {
  272.                     To = toParties,
  273.                     From = new[] { fromParty },
  274.                     Subject = Subject,
  275.                     Description = description,
  276.                     DirectionCode = true,
  277.                     RegardingObjectId = new EntityReference(new_crmisvrequest.EntityLogicalName, uopProcessId)
  278.                 };
  279.  
  280.                 Guid emailId = service.Create(email);
  281.                 if (emailId == Guid.Empty)
  282.                 {
  283.                     _logger.Error("Email to task owners not created successfully");
  284.                     return false;
  285.                 }
  286.                 _logger.Info($"Created email message with id {emailId} with the following information: " +
  287.                           $"Subject: {email.Subject}, Description: {email.Description}");
  288.  
  289.                 SendEmailRequest sendEmailRequest = new SendEmailRequest
  290.                 {
  291.                     EmailId = emailId,
  292.                     TrackingToken = string.Empty,
  293.                     IssueSend = true
  294.                 };
  295.  
  296.                 SendEmailResponse sendEmailResponse = (SendEmailResponse)service.Execute(sendEmailRequest);
  297.                 return sendEmailResponse != null;
  298.             }
  299.             catch (Exception ex)
  300.             {
  301.                 _logger.FatalFormat($"Error in {nameof(SendEmailToTaskOwners)}. Details: {ex}");
  302.                 return false;
  303.             }
  304.         }
  305.  
  306.         private string BuildEmailDescription()
  307.         {
  308.             string description = @"Automating approval of registration started at: " + ServerDate + "<br>";
  309.             description += @"Automating approval of registration finished at: " + DateTime.Now + "<br>";
  310.             description += @"Total number of registrations found: " + _registrations.Count + "<br>";
  311.             description += @"Number of registrations successfully processed: " + _successes.Count + "<br>";
  312.             description += @"Number of registrations failed to be processed: " + _failures.Count + "<br> <br>";
  313.             description += "List of registrations processed successfully (related data was updated):";
  314.             description += TableStyle +
  315.                            TableRowStyle + "#</th>" +
  316.                            TableRowStyle + "Registration ID</th>" +
  317.                            TableRowStyle + "Student ID</th>";
  318.  
  319.             //3.6.3. List of registrations processed.
  320.             for (int i = 0; i < _successes.Count; i++)
  321.             {
  322.                 string studentId = _successes[i].Student.StudentId.ToString();
  323.                 string accountUrl = _crmAccountUrl.Replace("ENTITY_NAME", Account.EntityLogicalName)
  324.                     .Replace("ENTITY_ID", studentId);
  325.  
  326.                 string registrationId = _successes[i].RegistrationId.ToString();
  327.                 string registrationUrl = _crmAccountUrl.Replace("ENTITY_NAME", New_enrollment.EntityLogicalName)
  328.                     .Replace("ENTITY_ID", registrationId);
  329.  
  330.                 description += @"<tr>" +
  331.                                     TableRowStyle + (i + 1) + " </td>" +
  332.                                     TableRowStyle + "<a href='" + registrationUrl + "'>" + _successes[i].RegistrationName + "</a></td>" +
  333.                                     TableRowStyle + "<a href='" + accountUrl + "'>" + _successes[i].Student.StudentNumber + "</a></td>" +
  334.                                "</tr>";
  335.             }
  336.  
  337.             description += "</table> <br>";
  338.  
  339.             if (_failures.Count > 0)
  340.             {
  341.                 //3.6.4. List of registrations failed to be processed.
  342.                 description += "List of students with issues (data was not updated):";
  343.                 description += TableStyle +
  344.                                TableRowStyle + "#</th>" +
  345.                                TableRowStyle + "Registration ID</th>" +
  346.                                TableRowStyle + "Student ID</th>" +
  347.                                TableRowStyle + "Issue Description</th>";
  348.  
  349.                 for (int i = 0; i < _failures.Count; i++)
  350.                 {
  351.                     string studentId = _failures[i].Student.StudentId.ToString();
  352.                     string accountUrl = _crmAccountUrl.Replace("ENTITY_NAME", Account.EntityLogicalName)
  353.                         .Replace("ENTITY_ID", studentId);
  354.  
  355.                     string registrationId = _failures[i].RegistrationId.ToString();
  356.                     string registrationUrl = _crmAccountUrl.Replace("ENTITY_NAME", New_enrollment.EntityLogicalName)
  357.                         .Replace("ENTITY_ID", registrationId);
  358.  
  359.                     description += @"<tr>" +
  360.                                         TableRowStyle + (i + 1) + " </td>" +
  361.                                         TableRowStyle + "<a href='" + registrationUrl + "'>" + _failures[i].RegistrationName + "</a></td>" +
  362.                                         TableRowStyle + "<a href='" + accountUrl + "'>" + _failures[i].Student.StudentNumber + "</a></td>" +
  363.                                         TableRowStyle + _failures[i].IssueDescription + "</a></td>" +
  364.                                    "</tr>";
  365.                 }
  366.  
  367.                 description += "</table> <br>";
  368.             }
  369.  
  370.             description +=
  371.                 "<div style ='font-size: 10px; float: left;'>Related version: v15.9 Automating Approval of Registration</div>";
  372.             return description;
  373.         }
  374.  
  375.         #endregion
  376.     }
  377. }
Advertisement
Add Comment
Please, Sign In to add comment