1
0
mirror of https://github.com/bitwarden/mobile synced 2026-01-09 20:13:18 +00:00

Added account deletion feature on settings (#1621)

* Added account deletion feature on settings

* Disabled using Microsoft.AppCenter.Crashes for FDroid

* Moved drawable on Android.csproj to be with the others

Co-authored-by: Federico Maccaroni <fmaccaroni@bitwarden.com>
This commit is contained in:
Federico Maccaroni
2021-11-24 16:09:39 -03:00
committed by GitHub
parent 833103b2a0
commit 9fdf2ada6f
22 changed files with 884 additions and 20 deletions

View File

@@ -0,0 +1,56 @@
<?xml version="1.0" encoding="UTF-8" ?>
<pages:BaseContentPage
xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
x:Class="Bit.App.Pages.Accounts.DeleteAccountPage"
xmlns:pages="clr-namespace:Bit.App.Pages"
xmlns:u="clr-namespace:Bit.App.Utilities"
x:DataType="pages:DeleteAccountViewModel"
Title="{Binding PageTitle}">
<ContentPage.BindingContext>
<pages:DeleteAccountViewModel />
</ContentPage.BindingContext>
<ContentPage.ToolbarItems>
<ToolbarItem Text="{u:I18n Close}" Clicked="Close_Clicked" Order="Primary" Priority="-1" />
</ContentPage.ToolbarItems>
<ContentPage.Content>
<StackLayout Padding="20, 30" Spacing="0">
<Image
Source="ic_warning"
WidthRequest="28"
HeightRequest="25"
HorizontalOptions="Start" />
<Label
Text="{u:I18n DeletingYourAccountIsPermanent}"
HorizontalOptions="Start"
StyleClass="text-body"
Margin="0,15,0,0"/>
<Label
Text="{u:I18n DeleteAccountExplanation}"
HorizontalOptions="Start"
Margin="0,6,50,0"
Opacity="0.6" />
<Button
Text="{u:I18n Cancel}"
StyleClass="btn-primary"
HorizontalOptions="Start"
Margin="0,26,0,0"
Padding="16,6"
CornerRadius="2"
TextTransform="Uppercase"
Clicked="Close_Clicked" />
<Button
Text="{u:I18n DeleteAccount}"
StyleClass="btn-secondary"
TextColor="#99000000"
HorizontalOptions="Start"
Margin="0,12,0,0"
Padding="16,6"
CornerRadius="2"
TextTransform="Uppercase"
Clicked="DeleteAccount_Clicked"/>
</StackLayout>
</ContentPage.Content>
</pages:BaseContentPage>

View File

@@ -0,0 +1,33 @@
using System;
using Xamarin.Forms;
namespace Bit.App.Pages.Accounts
{
public partial class DeleteAccountPage : BaseContentPage
{
DeleteAccountViewModel _vm;
public DeleteAccountPage()
{
InitializeComponent();
_vm = BindingContext as DeleteAccountViewModel;
_vm.Page = this;
}
private async void Close_Clicked(object sender, EventArgs e)
{
if (DoOnce())
{
await Navigation.PopModalAsync();
}
}
private async void DeleteAccount_Clicked(object sender, EventArgs e)
{
if (DoOnce())
{
await _vm.DeleteAccountAsync();
}
}
}
}

View File

@@ -0,0 +1,84 @@
using System.Threading.Tasks;
using Bit.App.Abstractions;
using Bit.App.Resources;
using Bit.Core.Abstractions;
using Bit.Core.Exceptions;
using Bit.Core.Utilities;
#if !FDROID
using Microsoft.AppCenter.Crashes;
#endif
namespace Bit.App.Pages
{
public class DeleteAccountViewModel : BaseViewModel
{
readonly IApiService _apiService;
readonly IPasswordRepromptService _passwordRepromptService;
readonly IMessagingService _messagingService;
readonly ICryptoService _cryptoService;
readonly IPlatformUtilsService _platformUtilsService;
readonly IDeviceActionService _deviceActionService;
public DeleteAccountViewModel()
{
_apiService = ServiceContainer.Resolve<IApiService>("apiService");
_passwordRepromptService = ServiceContainer.Resolve<IPasswordRepromptService>("passwordRepromptService");
_messagingService = ServiceContainer.Resolve<IMessagingService>("messagingService");
_cryptoService = ServiceContainer.Resolve<ICryptoService>("cryptoService");
_platformUtilsService = ServiceContainer.Resolve<IPlatformUtilsService>("platformUtilsService");
_deviceActionService = ServiceContainer.Resolve<IDeviceActionService>("deviceActionService");
PageTitle = AppResources.DeleteAccount;
}
public async Task DeleteAccountAsync()
{
try
{
if (Xamarin.Essentials.Connectivity.NetworkAccess == Xamarin.Essentials.NetworkAccess.None)
{
await _platformUtilsService.ShowDialogAsync(AppResources.InternetConnectionRequiredMessage,
AppResources.InternetConnectionRequiredTitle, AppResources.Ok);
return;
}
var (password, valid) = await _passwordRepromptService.ShowPasswordPromptAndGetItAsync();
if (!valid)
{
return;
}
await _deviceActionService.ShowLoadingAsync(AppResources.DeletingYourAccount);
var masterPasswordHashKey = await _cryptoService.HashPasswordAsync(password, null);
await _apiService.DeleteAccountAsync(new Core.Models.Request.DeleteAccountRequest
{
MasterPasswordHash = masterPasswordHashKey
});
await _deviceActionService.HideLoadingAsync();
_messagingService.Send("logout");
await _platformUtilsService.ShowDialogAsync(AppResources.YourAccountHasBeenPermanentlyDeleted);
}
catch (ApiException apiEx)
{
await _deviceActionService.HideLoadingAsync();
if (apiEx?.Error != null)
{
await _platformUtilsService.ShowDialogAsync(apiEx.Error.GetSingleMessage(), AppResources.AnErrorHasOccurred);
}
}
catch (System.Exception ex)
{
await _deviceActionService.HideLoadingAsync();
#if !FDROID
Crashes.TrackError(ex);
#endif
await _platformUtilsService.ShowDialogAsync(AppResources.AnErrorHasOccurred);
}
}
}
}

View File

@@ -1,10 +1,11 @@
using System.ComponentModel;
using Bit.App.Abstractions;
using Bit.App.Resources;
using Bit.Core.Utilities;
using System.Linq;
using System.Threading.Tasks;
using Bit.App.Abstractions;
using Bit.App.Controls;
using Bit.App.Pages.Accounts;
using Bit.App.Resources;
using Bit.Core.Utilities;
using Xamarin.Forms;
namespace Bit.App.Pages
@@ -134,6 +135,10 @@ namespace Bit.App.Pages
{
await _vm.LogOutAsync();
}
else if (item.Name == AppResources.DeleteAccount)
{
await Navigation.PushModalAsync(new NavigationPage(new DeleteAccountPage()));
}
else if (item.Name == AppResources.LockNow)
{
await _vm.LockAsync();

View File

@@ -490,7 +490,8 @@ namespace Bit.App.Pages
new SettingsPageListItem { Name = AppResources.Options },
new SettingsPageListItem { Name = AppResources.About },
new SettingsPageListItem { Name = AppResources.HelpAndFeedback },
new SettingsPageListItem { Name = AppResources.RateTheApp }
new SettingsPageListItem { Name = AppResources.RateTheApp },
new SettingsPageListItem { Name = AppResources.DeleteAccount }
};
GroupedItems.ResetWithRange(new List<SettingsPageListGroup>
{