public async Task <bool> CreateDefaultTemplate(StorePickUpConstants.MailTemplateType templateType)
        {
            bool   templateExists = false;
            string templateName   = string.Empty;
            string subjectText    = string.Empty;

            switch (templateType)
            {
            case StorePickUpConstants.MailTemplateType.AtLocation:
                templateName = StorePickUpConstants.MailTemplates.AtLocation;
                subjectText  = StorePickUpConstants.TemplateSubject.AtLocation;
                break;

            case StorePickUpConstants.MailTemplateType.PackageReady:
                templateName = StorePickUpConstants.MailTemplates.PackageReady;
                subjectText  = StorePickUpConstants.TemplateSubject.PackageReady;
                break;

            case StorePickUpConstants.MailTemplateType.ReadyForPacking:
                templateName = StorePickUpConstants.MailTemplates.ReadyForPacking;
                subjectText  = StorePickUpConstants.TemplateSubject.ReadyForPacking;
                break;

            case StorePickUpConstants.MailTemplateType.PickedUp:
                templateName = StorePickUpConstants.MailTemplates.PickedUp;
                subjectText  = StorePickUpConstants.TemplateSubject.PickedUp;
                break;
            }

            templateExists = await this.TemplateExists(templateName);

            if (!templateExists)
            {
                string templateBody = await this.GetDefaultTemplate(templateName);

                if (string.IsNullOrWhiteSpace(templateBody))
                {
                    Console.WriteLine($"Failed to Load Template {templateName}");
                    _context.Vtex.Logger.Info("SendEmail", "Create Template", $"Failed to Load Template {templateName}");
                }
                else
                {
                    EmailTemplate emailTemplate = JsonConvert.DeserializeObject <EmailTemplate>(templateBody);

                    emailTemplate.Templates.Email.Message = emailTemplate.Templates.Email.Message.Replace(@"\n", "\n");

                    templateExists = await this.CreateOrUpdateTemplate(emailTemplate);
                }
            }

            return(templateExists);
        }
        public async Task <bool> SendEmail(StorePickUpConstants.MailTemplateType templateType, VtexOrder order)
        {
            bool             success          = false;
            MerchantSettings merchantSettings = await _storePickupRepository.GetMerchantSettings();

            if (string.IsNullOrEmpty(merchantSettings.AppKey) || string.IsNullOrEmpty(merchantSettings.AppToken))
            {
                Console.WriteLine("App Settings missing.");
            }

            string responseText = string.Empty;
            string templateName = string.Empty;
            string subjectText  = string.Empty;
            string toEmail      = string.Empty;
            string nextAction   = string.Empty;
            string shopperEmail = order.ClientProfileData.Email;
            List <LogisticsInfo> pickUpItems = order.ShippingData.LogisticsInfo.Where(i => i.Slas.Any(s => s.PickupStoreInfo.IsPickupStore)).ToList();
            string storeEmail = string.Empty;

            // TODO: Divide notifications by store location.  Send separate email to each.
            foreach (LogisticsInfo logisticsInfo in pickUpItems)
            {
                string selectedSla = logisticsInfo.SelectedSla;
                Sla    sla         = logisticsInfo.Slas.Where(s => s.Id.Equals(selectedSla)).FirstOrDefault();
                storeEmail = sla.PickupStoreInfo.Address.Complement;
                if (!string.IsNullOrEmpty(storeEmail))
                {
                    break;
                }
            }

            Console.WriteLine($"Store Email = {storeEmail}");
            switch (templateType)
            {
            case StorePickUpConstants.MailTemplateType.AtLocation:
                templateName = StorePickUpConstants.MailTemplates.AtLocation;
                subjectText  = StorePickUpConstants.TemplateSubject.AtLocation;
                toEmail      = storeEmail;
                nextAction   = StorePickUpConstants.MailTemplates.PickedUp;
                break;

            case StorePickUpConstants.MailTemplateType.PackageReady:
                templateName = StorePickUpConstants.MailTemplates.PackageReady;
                subjectText  = StorePickUpConstants.TemplateSubject.PackageReady;
                toEmail      = shopperEmail;
                nextAction   = StorePickUpConstants.MailTemplates.AtLocation;
                break;

            case StorePickUpConstants.MailTemplateType.ReadyForPacking:
                templateName = StorePickUpConstants.MailTemplates.ReadyForPacking;
                subjectText  = StorePickUpConstants.TemplateSubject.ReadyForPacking;
                toEmail      = storeEmail;
                nextAction   = StorePickUpConstants.MailTemplates.PackageReady;
                break;

            case StorePickUpConstants.MailTemplateType.PickedUp:
                templateName = StorePickUpConstants.MailTemplates.PickedUp;
                subjectText  = StorePickUpConstants.TemplateSubject.PickedUp;
                toEmail      = shopperEmail;
                break;
            }

            //templateName = "test1";

            string encryptedOrderId     = _cryptoService.EncryptString(order.ClientProfileData.Email, order.OrderId, _context.Vtex.Account);
            string queryText            = $"{order.ClientProfileData.Email}|{encryptedOrderId}";
            string queryArgs            = Uri.EscapeDataString(_cryptoService.EncryptString(nextAction, queryText, _context.Vtex.Account));
            string cancelOrderQueryArgs = Uri.EscapeDataString(_cryptoService.EncryptString(StorePickUpConstants.MailTemplates.CancelOrder, queryText, _context.Vtex.Account));
            // https://sandboxusdev.myvtex.com/_v/pickup/notification/package-ready/{{queryArgs}}
            string actionLink = $"https://{_context.Vtex.Host}/_v/curbside-pickup/notification/{nextAction}/{queryArgs}";
            string cancelLink = $"https://{_context.Vtex.Host}/_v/curbside-pickup/notification/{StorePickUpConstants.MailTemplates.CancelOrder}/{cancelOrderQueryArgs}";

            EmailMessage emailMessage = new EmailMessage
            {
                templateName = templateName,
                providerName = StorePickUpConstants.Acquirer,
                jsonData     = new JsonData
                {
                    order          = order,
                    curbsidePickup = new CurbsidePickup
                    {
                        actionLink       = actionLink,
                        cancelLink       = cancelLink,
                        encryptedOrderId = encryptedOrderId,
                        toEmail          = toEmail,
                        queryArgs        = queryArgs
                    }
                }
            };

            string accountName = _httpContextAccessor.HttpContext.Request.Headers[StorePickUpConstants.VTEX_ACCOUNT_HEADER_NAME].ToString();
            string message     = JsonConvert.SerializeObject(emailMessage);

            var request = new HttpRequestMessage
            {
                Method     = HttpMethod.Post,
                RequestUri = new Uri($"{StorePickUpConstants.MailService}?an={accountName}"),
                Content    = new StringContent(message, Encoding.UTF8, StorePickUpConstants.APPLICATION_JSON)
            };

            request.Headers.Add(StorePickUpConstants.USE_HTTPS_HEADER_NAME, "true");
            string authToken = this._httpContextAccessor.HttpContext.Request.Headers[StorePickUpConstants.HEADER_VTEX_CREDENTIAL];

            if (authToken != null)
            {
                request.Headers.Add(StorePickUpConstants.AUTHORIZATION_HEADER_NAME, authToken);
                request.Headers.Add(StorePickUpConstants.PROXY_AUTHORIZATION_HEADER_NAME, authToken);
            }

            request.Headers.Add(StorePickUpConstants.AppKey, merchantSettings.AppKey);
            request.Headers.Add(StorePickUpConstants.AppToken, merchantSettings.AppToken);

            HttpClient client = _clientFactory.CreateClient();

            try
            {
                HttpResponseMessage responseMessage = await client.SendAsync(request);

                string responseContent = await responseMessage.Content.ReadAsStringAsync();

                responseText = $"[-] SendEmail [{responseMessage.StatusCode}] {responseContent}";
                _context.Vtex.Logger.Info("SendEmail", null, $"{toEmail} [{responseMessage.StatusCode}] {responseContent}");
                success = responseMessage.IsSuccessStatusCode;
                if (responseMessage.StatusCode.Equals(HttpStatusCode.NotFound))
                {
                    _context.Vtex.Logger.Error("SendEmail", null, $"Template {templateName} not found.");
                }
            }
            catch (Exception ex)
            {
                responseText = $"[-] SendEmail Failure [{ex.Message}]";
                _context.Vtex.Logger.Error("SendEmail", null, "Failure", ex);
                success = false;  //jic
            }

            Console.WriteLine(responseText);
            return(success);
        }
        public async Task <bool> SendEmail(StorePickUpConstants.MailTemplateType templateType, VtexOrder order)
        {
            bool             success          = false;
            MerchantSettings merchantSettings = await _storePickupRepository.GetMerchantSettings();

            if (string.IsNullOrEmpty(merchantSettings.AppKey) || string.IsNullOrEmpty(merchantSettings.AppToken))
            {
                _context.Vtex.Logger.Error("SendEmail", null, "App Settings Missing.");
                return(success);
            }

            string templateName = string.Empty;
            string subjectText  = string.Empty;
            string toEmail      = string.Empty;
            string nextAction   = string.Empty;
            string shopperEmail = order.ClientProfileData.Email;
            List <LogisticsInfo> pickUpItems = order.ShippingData.LogisticsInfo.Where(i => i.Slas.Any(s => s.PickupStoreInfo.IsPickupStore)).ToList();
            string storeEmail = string.Empty;

            if (pickUpItems != null && pickUpItems.Count > 0)
            {
                try
                {
                    // TODO: Divide notifications by store location.  Send separate email to each.
                    foreach (LogisticsInfo logisticsInfo in pickUpItems)
                    {
                        string selectedSla = logisticsInfo.SelectedSla;
                        Sla    sla         = logisticsInfo.Slas.FirstOrDefault(s => s.Id.Equals(selectedSla));
                        if (sla.PickupStoreInfo.Address != null && !string.IsNullOrEmpty(sla.PickupStoreInfo.Address.Complement))
                        {
                            storeEmail = sla.PickupStoreInfo.Address.Complement;
                        }
                    }
                }
                catch (Exception ex)
                {
                    _context.Vtex.Logger.Error("SendEmail", null, $"Pickup Store Info Missing.  Order Id {order.OrderId}", ex);
                    return(success);
                }
            }
            else
            {
                _context.Vtex.Logger.Error("SendEmail", null, $"Pickup Store Info Missing.  Order Id {order.OrderId}");
                return(success);
            }

            // Store email fallback
            if (string.IsNullOrWhiteSpace(storeEmail))
            {
                try
                {
                    foreach (LogisticsInfo logisticsInfo in pickUpItems)
                    {
                        string selectedSla = logisticsInfo.SelectedSla;
                        Sla    sla         = logisticsInfo.Slas.FirstOrDefault(s => s.Id.Equals(selectedSla));
                        if (sla.PickupStoreInfo.Address != null && !string.IsNullOrEmpty(sla.PickupStoreInfo.AdditionalInfo))
                        {
                            string emailToVerify = sla.PickupStoreInfo.AdditionalInfo.Trim();
                            if (this.IsValidEmail(emailToVerify))
                            {
                                storeEmail = emailToVerify;
                                _context.Vtex.Logger.Info("SendEmail", null, "Using email from AdditionalInfo.");
                            }
                        }
                    }
                }
                catch (Exception ex)
                {
                    _context.Vtex.Logger.Warn("SendEmail", null, $"Pickup Store Info Missing.  Order Id {order.OrderId}");
                    return(success);
                }
            }

            switch (templateType)
            {
            case StorePickUpConstants.MailTemplateType.AtLocation:
                templateName = StorePickUpConstants.MailTemplates.AtLocation;
                subjectText  = StorePickUpConstants.TemplateSubject.AtLocation;
                toEmail      = storeEmail;
                nextAction   = StorePickUpConstants.MailTemplates.PickedUp;
                break;

            case StorePickUpConstants.MailTemplateType.PackageReady:
                templateName = StorePickUpConstants.MailTemplates.PackageReady;
                subjectText  = StorePickUpConstants.TemplateSubject.PackageReady;
                toEmail      = shopperEmail;
                nextAction   = StorePickUpConstants.MailTemplates.AtLocation;
                break;

            case StorePickUpConstants.MailTemplateType.ReadyForPacking:
                templateName = StorePickUpConstants.MailTemplates.ReadyForPacking;
                subjectText  = StorePickUpConstants.TemplateSubject.ReadyForPacking;
                toEmail      = storeEmail;
                nextAction   = StorePickUpConstants.MailTemplates.PackageReady;
                break;

            case StorePickUpConstants.MailTemplateType.PickedUp:
                templateName = StorePickUpConstants.MailTemplates.PickedUp;
                subjectText  = StorePickUpConstants.TemplateSubject.PickedUp;
                toEmail      = shopperEmail;
                break;
            }

            if (string.IsNullOrWhiteSpace(toEmail))
            {
                // log the missing email address, but allow the mail to send in the event that the to address is in the template
                _context.Vtex.Logger.Error("SendEmail", null, "'To' email address missing.", null, new[] { ("templateType", templateType.ToString()), ("order", JsonConvert.SerializeObject(order)) });