/// <summary>
        /// Handles incoming messages of AccountDeleteMessage type
        /// </summary>
        /// <param name="command"></param>
        /// <returns>True if processed successfully, false if we failed for some reason.</returns>
        /// <remarks>If accountManager.DeleteAccount throws, the entire method will throw and the message will go back into the queue.</remarks>
        public async Task <bool> HandleAsync(AccountDeleteMessage command)
        {
            var messageProcessed = true;
            var source           = command.Source;

            try
            {
                _logger.LogInformation("Processing Request from Source {Source}", source);
                _accountDeleteConfigurationAccessor.Value.VerifySource(source);

                var username = command.Username;
                var user     = _userService.FindByUsername(username);
                if (user == null)
                {
                    throw new UserNotFoundException();
                }

                if (_accountDeleteConfigurationAccessor.Value.RespectEmailContactSetting && !user.EmailAllowed)
                {
                    throw new EmailContactNotAllowedException();
                }

                var recipientEmail = user.EmailAddress;
                var deleteSuccess  = await _accountManager.DeleteAccount(user);

                _telemetryService.TrackDeleteResult(source, deleteSuccess);

                var baseEmailBuilder = _emailBuilderFactory.GetEmailBuilder(source, deleteSuccess);
                if (baseEmailBuilder != null)
                {
                    var toEmail = new List <MailAddress>();

                    var configuration = _accountDeleteConfigurationAccessor.Value;
                    var senderAddress = configuration.EmailConfiguration.GalleryOwner;
                    var ccEmail       = new List <MailAddress>();
                    // toEmail.Add(new MailAddress(recipientEmail)); // Temporarily disable sending to end user while we are in phase 1.
                    toEmail.Add(new MailAddress(senderAddress)); // Remove this when we switch to phase 2.
                    ccEmail.Add(new MailAddress(senderAddress));

                    var recipients   = new EmailRecipients(toEmail, ccEmail);
                    var emailBuilder = new DisposableEmailBuilder(baseEmailBuilder, recipients, username);
                    await _messenger.SendMessageAsync(emailBuilder);

                    _telemetryService.TrackEmailSent(source, user.EmailAllowed);
                    messageProcessed = true;
                }
            }
            catch (UnknownSourceException)
            {
                // Should definitely log if source isn't expected. Should we even send mail? or log and alert?
                // Log unknown source and fail.
                _logger.LogError("Unknown message source detected: {Source}.", command.Source);
                _telemetryService.TrackUnknownSource(source);
                messageProcessed = false;
            }
            catch (EmailContactNotAllowedException)
            {
                // Should we not send? or should we ignore the setting.
                _logger.LogWarning("User did not allow Email Contact.");
                _telemetryService.TrackEmailBlocked(source);
            }
            catch (UserNotFoundException)
            {
                _logger.LogWarning("User was not found. They may have already been deleted.");
                _telemetryService.TrackUserNotFound(source);
                messageProcessed = true;
            }
            catch (Exception e)
            {
                _logger.LogError(0, e, "An unknown exception occured: {ExceptionMessage}");
                throw e;
            }

            return(messageProcessed);
        }
Пример #2
0
        /// <summary>
        /// Handles incoming messages of AccountDeleteMessage type
        /// </summary>
        /// <param name="command"></param>
        /// <returns>True if processed successfully, false if we failed for some reason.</returns>
        /// <remarks>If accountManager.DeleteAccount throws, the entire method will throw and the message will go back into the queue.</remarks>
        public async Task <bool> HandleAsync(AccountDeleteMessage command)
        {
            var messageProcessed = true;
            var source           = command.Source;

            try
            {
                _logger.LogInformation("Processing Request from Source {Source}", source);
                _accountDeleteConfigurationAccessor.Value.GetSourceConfiguration(source);

                var username = command.Username;
                var user     = _userService.FindByUsername(username);
                if (user == null)
                {
                    throw new UserNotFoundException();
                }

                var recipientEmail = user.EmailAddress;
                var emailAllowed   = user.EmailAllowed;
                var deleteSuccess  = await _accountManager.DeleteAccount(user, source);

                _telemetryService.TrackDeleteResult(source, deleteSuccess);

                if (recipientEmail == null)
                {
                    _logger.LogWarning("User has no confirmed email address. The user has been deleted but no email was sent.");
                    _telemetryService.TrackUnconfirmedUser(source);
                    messageProcessed = true;
                }
                else if (_accountDeleteConfigurationAccessor.Value.RespectEmailContactSetting && !emailAllowed)
                {
                    _logger.LogWarning("User did not allow Email Contact. The user has been deleted but no email was sent.");
                    _telemetryService.TrackEmailBlocked(source);
                    messageProcessed = true;
                }
                else
                {
                    var baseEmailBuilder = _emailBuilderFactory.GetEmailBuilder(source, deleteSuccess);
                    if (baseEmailBuilder != null)
                    {
                        var toEmail = new List <MailAddress>();

                        var configuration = _accountDeleteConfigurationAccessor.Value;
                        var senderAddress = configuration.EmailConfiguration.GalleryOwner;
                        var ccEmail       = new List <MailAddress>();
                        toEmail.Add(new MailAddress(recipientEmail));
                        ccEmail.Add(new MailAddress(senderAddress));

                        var recipients   = new EmailRecipients(toEmail, ccEmail);
                        var emailBuilder = new DisposableEmailBuilder(baseEmailBuilder, recipients, username);
                        await _messenger.SendMessageAsync(emailBuilder);

                        _telemetryService.TrackEmailSent(source, emailAllowed);
                        messageProcessed = true;
                    }
                }
            }
            catch (UnknownSourceException)
            {
                // Should definitely log if source isn't expected. Should we even send mail? or log and alert?
                // Log unknown source and fail.
                _logger.LogError("Unknown message source detected: {Source}.", command.Source);
                _telemetryService.TrackUnknownSource(source);
                messageProcessed = false;
            }
            catch (UserNotFoundException)
            {
                _logger.LogWarning("User was not found. They may have already been deleted.");
                _telemetryService.TrackUserNotFound(source);
                messageProcessed = true;
            }
            catch (Exception e)
            {
                _logger.LogError(e, "An unknown exception occurred.");
                throw;
            }

            return(messageProcessed);
        }