using gehGassi.Core.Interfaces; using gehGassi.Core.Services; using gehGassi.Domain.Users; using gehGassi.Web.Helper; using gehGassi.Web.Models; using gehGassi.Web.Services; using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Identity; using Microsoft.AspNetCore.Mvc; using Microsoft.Extensions.Localization; using Microsoft.Extensions.Logging; using Microsoft.Extensions.Options; using System; using System.Threading.Tasks; using gehGassi.Web.Hubs; namespace gehGassi.Web.Controllers { /// /// Controller für Funktionen die via App nicht verfügbar sind, aber für App-Benutzer wichtig sind /// [Authorize] public class AppController : BaseController { private readonly ILogger _logger; private readonly IStringLocalizer _localizer; private readonly IEmailSender _emailSender; private readonly IUserService _userService; private readonly IOptions _emailSenderOptions; private readonly UserManager _userManager; private readonly DataProtectorTokenProvider _tokenProvider; private readonly IRefreshTokenService _refreshTokenService; private readonly IPushNotificationService _pushNotificationService; private readonly IAppUserService _appUserService; private readonly IAppHubSender _appHubSender; /// /// Erstellt eine Instanz /// /// Instanz eines ILogger /// Instanz eines IStringLocalizer /// Instanz eines IEmailSender /// Instanz eines IUserService /// Instanz von EmailSenderOptions /// Instanz eines UserManager /// Instanz eines DataProtectorTokenProvider /// Instanz eines IRefreshTokenService /// Instanz eines IPushNotificationService /// Instanz eines IAppUserService /// Instanz eines IAppHubSender public AppController(ILogger logger, IStringLocalizer localizer, IEmailSender emailSender, IUserService userService, IOptions emailSenderOptions, UserManager userManager, DataProtectorTokenProvider tokenProvider, IRefreshTokenService refreshTokenService, IPushNotificationService pushNotificationService, IAppUserService appUserService, IAppHubSender appHubSender) { _logger = logger; _localizer = localizer; _emailSender = emailSender; _userService = userService; _emailSenderOptions = emailSenderOptions; _userManager = userManager; _tokenProvider = tokenProvider; _refreshTokenService = refreshTokenService; _pushNotificationService = pushNotificationService; _appUserService = appUserService; _appHubSender = appHubSender; } /// /// Zeigt eine View für das Löschen eines Accounts an /// /// View [HttpGet] [AllowAnonymous] public IActionResult DeleteAccount() { return View(); } /// /// Handling für Account löschen /// /// Benutzereingaben /// Redirect oder View [HttpPost] [AllowAnonymous] [ValidateAntiForgeryToken] public async Task DeleteAccount(DeleteAccountVm model) { if (ModelState.IsValid) { try { var user = await _userManager.FindByNameAsync(model.Email); if (user != null && !user.LockoutEnd.HasValue) { var token = await _tokenProvider.GenerateAsync("deleteAccount", _userManager, user); var callbackUrl = Url.DeleteAccountCallbackLinkApp(user.Id, token, Request.Scheme); await _emailSender.SendDeleteAccountAsync(model.Email, callbackUrl, _localizer); } } catch { } return RedirectToAction(nameof(DeleteAccountConfirmation)); } // If we got this far, something failed, redisplay form return View(model); } /// /// Zeigt eine Bestätungun an, dass eine Email zum Löschen des Accounts versendet wurde /// Wird in jedem Fall angezeigt, auch wenn die Email nicht versendet werden konnte /// /// View [HttpGet] [AllowAnonymous] public IActionResult DeleteAccountConfirmation() { return View(); } /// /// Handler wenn ein Account Löschen Link angeklickt wurde /// /// Id des Benutzers /// Token-Code /// View [HttpGet] [AllowAnonymous] public async Task DoDeleteAccount(string userId, string code) { if (!string.IsNullOrWhiteSpace(userId)) { if (!string.IsNullOrWhiteSpace(code)) { var user = await _userManager.FindByIdAsync(userId); if (user != null) { var isCodeValid = await _tokenProvider.ValidateAsync("deleteAccount", code, _userManager, user); if (isCodeValid) { //Sperren des Benutzers user.LockoutEnd = DateTimeOffset.UtcNow.AddYears(5); await _userManager.UpdateAsync(user); //Löschen aller Refresh-tokens des Benutzers da eine Abmeldung erfolgt ist await _refreshTokenService.RemoveAllAsync(user.Id, user.UserName); await _refreshTokenService.CommitAsync(user.UserName); var appUser = await _appUserService.GetAsync(user.AppUserId); if (appUser != null) { appUser.Locked = true; appUser.LockedReason = "Delete account requested"; await _appUserService.CommitAsync(user.UserName); } //Nun Email an gehgassi senden, dass der Benutzer gelöscht werden soll await _emailSender.SendDeleteAccountEmailAsync(user.Email, user.FirstName, user.LastName, _localizer, _emailSenderOptions); //Senden einer Nachricht an die App dass ein Logout durchgeführt werden soll? if (!string.IsNullOrWhiteSpace(user.AppUserId)) { //Logout-Aufforderung via SignalR await _appHubSender.LogoutAsync(user.AppUserId); //Logout-Aufforderung via Push-Notification await _pushNotificationService.SendLogoutAsync(user.AppUserId); } return View(); } } } } return View("DoDeleteAccountFailed"); } } }