Ejemplo n.º 1
0
 /// <summary>
 /// Initializes the commands and sets <see cref="CredentialTokens"/> to an empty collection.
 /// The ViewModel must be activated before use.
 /// </summary>
 /// <param name="accessList">A list used to look up candidates to get their underlying files.</param>
 /// <param name="exportService">Used to export stored files.</param>
 /// <param name="proxyProvider">Provider to use for accessing stored databases.</param>
 /// <param name="deletePrompter">Service to use for prompting user consent/understanding.</param>
 /// <param name="updatePrompter">Service to use for prompting user consent/understanding.</param>
 /// <param name="fileService">Service to use for accessing the filesystem.</param>
 public CachedFilesViewModel(
     IDatabaseAccessList accessList,
     IFileExportService exportService,
     IFileProxyProvider proxyProvider,
     IUserPromptingService deletePrompter,
     IUserPromptingService updatePrompter,
     IFileAccessService fileService
     ) : base(accessList, proxyProvider, exportService, deletePrompter, updatePrompter, fileService)
 {
     this.accessList       = accessList;
     this.proxyProvider    = proxyProvider;
     this.deleteAllCommand = new AsyncActionCommand(
         async() =>
     {
         if (await this.proxyProvider.TryDeleteAllProxiesAsync()
             .ConfigureAwait(false)
             )
         {
             ClearAllFiles();
         }
         else
         {
             // If clearing wasn't successful we might need to add back some
             // files.
             await ResyncFiles();
         }
     }
         );
 }
Ejemplo n.º 2
0
        /// <summary>
        /// Initializes the commands and sets <see cref="CredentialTokens"/> to an empty collection.
        /// The ViewModel must be activated before use.
        /// </summary>
        /// <param name="credentialProvider">Provider to use for accessing stored credentials.</param>
        public SavedCredentialsViewModel(
            ICredentialStorageProvider credentialProvider
            )
        {
            this.credentialProvider = credentialProvider ?? throw new ArgumentNullException(nameof(credentialProvider));

            this.deleteCredentialCommand = new AsyncTypedCommand <string>(
                (token) => token != null,
                async(token) =>
            {
                if (this.allCredentials.Contains(token))
                {
                    await this.credentialProvider.DeleteAsync(token);
                    this.allCredentials.Remove(token);
                }
            }
                );

            this.deleteAllCommand = new AsyncActionCommand(
                async() =>
            {
                await this.credentialProvider.ClearAsync();
                this.allCredentials.Clear();
            }
                );

            this.allCredentials = new ObservableCollection <string>();
        }
        /// <summary>
        /// Initializes the design data.
        /// </summary>
        public DesignDatabaseUnlockViewModel()
        {
            CandidateFile = new MockDatabaseCandidate
            {
                FileName     = "My Database.kdbx",
                LastModified = new DateTimeOffset(DateTime.UtcNow),
                Size         = 12345,
            };

            Password = "******";

            UnlockCommand = new AsyncActionCommand(
                () => HasGoodHeader,
                () => Task.CompletedTask
                );

            UseSavedCredentialsCommand = new AsyncActionCommand(
                () => true,
                () => Task.CompletedTask
                );

            HasGoodHeader    = true;
            ParseResult      = new ReaderResult(KdbxParserCode.Success);
            RememberDatabase = true;
        }
Ejemplo n.º 4
0
        /// <summary>
        /// Initializes the model from the provided struct.
        /// </summary>
        /// <param name="accessListEntry">The AccessListEntry to use as a reference.</param>
        public StoredFileDescriptor(AccessListEntry accessListEntry)
        {
            this.accessListEntry = accessListEntry;
            this.isAppOwned      = false;

            this.forgetCommand = new AsyncActionCommand(FireForgetRequested);
            this.exportCommand = new ActionCommand(FireExportRequested);
            this.updateCommand = new AsyncActionCommand(() => IsAppOwned, FireUpdateRequested);
            this.openCommand   = new ActionCommand(FireOpenRequested);
        }
Ejemplo n.º 5
0
        public async Task ShouldExecuteAsynchronous()
        {
            bool executeCalled = false;
            var  command       = new AsyncActionCommand <int>(o =>
            {
                executeCalled = true;
                return(Task.CompletedTask);
            });

            await command.ExecuteAsync();

            Assert.IsTrue(executeCalled);
        }
Ejemplo n.º 6
0
        public DiagnosticTraceButtonViewModel(IFolderPickerService folderPicker, IEventLogger logger, IEventTracer tracer, string startTraceLabel, string stopTraceLabel)
        {
            this.isBusy       = false;
            this.folderPicker = folderPicker ?? throw new ArgumentNullException(nameof(folderPicker));
            this.logger       = logger ?? throw new ArgumentNullException(nameof(logger));
            this.tracer       = tracer ?? throw new ArgumentNullException(nameof(tracer));
            this.traceCommand = new AsyncActionCommand(() => !this.isBusy, ToggleTrace);

            this.startTraceLabel = startTraceLabel;
            this.stopTraceLabel  = stopTraceLabel;

            IsTracing = false;
        }
Ejemplo n.º 7
0
        public async Task ShouldReceiveParameterAsynchronous()
        {
            int receivedParameter = 0;
            var command           = new AsyncActionCommand <int>(o =>
            {
                receivedParameter = o;
                return(Task.CompletedTask);
            });

            int parameterValue = 5;
            await command.ExecuteAsync(parameterValue);

            Assert.AreEqual(parameterValue, receivedParameter);
        }
Ejemplo n.º 8
0
        public async Task ShouldRaiseCanExecuteChangedAsynchronous()
        {
            bool canExecuteCalled = false;
            var  command          = new AsyncActionCommand(o => Task.FromResult((object)null),
                                                           o =>
            {
                canExecuteCalled = true;
                return(Task.FromResult(true));
            });

            await command.RefreshAsync();

            Assert.IsTrue(canExecuteCalled);
        }
Ejemplo n.º 9
0
        public CategoryPageViewModel(
            ILogger logger,
            IDataManager dataManager,
            IWindowManager windowManager,
            CommonViewModel commonViewModel)
        {
            _logger         = Arguments.NotNull(logger, nameof(logger));
            _dataManager    = Arguments.NotNull(dataManager, nameof(dataManager));
            CommonViewModel = Arguments.NotNull(commonViewModel, nameof(commonViewModel));
            WindowManager   = Arguments.NotNull(windowManager, nameof(windowManager));

            AddAccountCommand       = new AsyncActionCommand <object>(_logger, AddAccountEvent, ExecuteAddAccountCommandAsync);
            GeneratePasswordCommand = new AsyncActionCommand <object>(_logger, GeneratePasswordEvent, ExecuteGeneratePasswordCommandAsync);
            DeleteAccountCommand    = new AsyncActionCommand <Account>(_logger, DeleteAccountEvent, ExecuteDeleteAccountCommandAsync);
            PaneClosingCommand      = new ActionCommand <SplitViewPaneClosingEventArgs>(_logger, PaneClosingEvent, ExecutePaneClosingCommand);
        }
Ejemplo n.º 10
0
        /// <summary>
        /// Initializes the view model.
        /// </summary>
        public MasterKeyViewModel(IFileAccessService fileService)
        {
            this.fileService = fileService ?? throw new ArgumentNullException(nameof(fileService));

            this.keyfileCommand = new AsyncActionCommand(
                async() =>
            {
                KeyFile = await fileService.PickFileForOpenAsync();
            }
                );

            this.confirmCommand = new AsyncActionCommand(
                () => (!String.IsNullOrEmpty(this.password) || this.keyFile != null) && this.password == this.confirmedPassword,
                () => HandleCredentialsAsync(this.password, this.keyFile)
                );
        }
Ejemplo n.º 11
0
        public async Task ShouldSetEnabledToFalseAsynchronous()
        {
            bool[] canExecute = { true };
            var    command    = new AsyncActionCommand <int>(
                o => Task.CompletedTask,
                async o =>
            {
                await Task.Yield();
                return(canExecute[0]);
            });

            await command.RefreshAsync();

            Assert.IsTrue(command.Enabled);

            canExecute[0] = false;

            await command.RefreshAsync();

            Assert.IsFalse(command.Enabled);
        }
Ejemplo n.º 12
0
        /// <summary>
        /// Initializes a new instance of the class.
        /// </summary>
        /// <param name="syncContext">Synchronization context used for marshalling to the UI thread.</param>
        /// <param name="file">The candidate document file.</param>
        /// <param name="isSampleFile">Whether the file is a PassKeep sample.</param>
        /// <param name="futureAccessList">A database access list for persisting permission to the database.</param>
        /// <param name="reader">The IKdbxReader implementation used for parsing document files.</param>
        /// <param name="proxyProvider">Generates file proxies that the app controls.</param>
        /// <param name="candidateFactory">Factory used to generate new candidate files as needed.</param>
        /// <param name="keyChangeVmFactory">Factory used to generate the objects used to modify the master key of the database.</param>
        /// <param name="taskNotificationService">A service used to notify the UI of blocking operations.</param>
        /// <param name="identityService">The service used to verify the user's consent for saving credentials.</param>
        /// <param name="credentialProvider">The provider used to store/load saved credentials.</param>
        /// <param name="credentialViewModelFactory">A factory used to generate <see cref="ISavedCredentialsViewModel"/> instances.</param>
        public DatabaseUnlockViewModel(
            ISyncContext syncContext,
            IDatabaseCandidate file,
            bool isSampleFile,
            IDatabaseAccessList futureAccessList,
            IKdbxReader reader,
            IFileProxyProvider proxyProvider,
            IDatabaseCandidateFactory candidateFactory,
            IMasterKeyChangeViewModelFactory keyChangeVmFactory,
            ITaskNotificationService taskNotificationService,
            IIdentityVerificationService identityService,
            ICredentialStorageProvider credentialProvider,
            ISavedCredentialsViewModelFactory credentialViewModelFactory
            )
        {
            this.syncContext                = syncContext ?? throw new ArgumentNullException(nameof(syncContext));
            this.futureAccessList           = futureAccessList;
            this.kdbxReader                 = reader ?? throw new ArgumentNullException(nameof(reader));
            this.proxyProvider              = proxyProvider ?? throw new ArgumentNullException(nameof(proxyProvider));
            this.candidateFactory           = candidateFactory ?? throw new ArgumentNullException(nameof(candidateFactory));
            this.keyChangeVmFactory         = keyChangeVmFactory ?? throw new ArgumentNullException(nameof(keyChangeVmFactory));
            this.taskNotificationService    = taskNotificationService ?? throw new ArgumentNullException(nameof(taskNotificationService));
            this.identityService            = identityService ?? throw new ArgumentNullException(nameof(identityService));
            this.credentialProvider         = credentialProvider ?? throw new ArgumentNullException(nameof(credentialProvider));
            this.credentialViewModelFactory = credentialViewModelFactory ?? throw new ArgumentNullException(nameof(credentialViewModelFactory));

            SaveCredentials            = false;
            IdentityVerifiability      = UserConsentVerifierAvailability.Available;
            UnlockCommand              = new AsyncActionCommand(CanUnlock, DoUnlockAsync);
            UseSavedCredentialsCommand = new AsyncActionCommand(
                () => UnlockCommand.CanExecute(null) && HasSavedCredentials,
                DoUnlockWithSavedCredentials
                );
            IsSampleFile     = isSampleFile;
            RememberDatabase = true;

            this.initialConstruction = UpdateCandidateFileAsync(file);
        }
        public GameBoardTileViewModel(
            IGameplayService gameplayService,
            GameStateModel gameState)
        {
            _subscriptions = new CompositeDisposable();

            var cachedModel = Observable.CombineLatest(
                this.ObserveProperty(x => x.ColIndex),
                this.ObserveProperty(x => x.RowIndex),
                gameState.GameBoard,
                (colIndex, rowIndex, gameBoard) => gameBoard
                .Tiles
                .FirstOrDefault(x => (x.ColIndex == colIndex) && (x.RowIndex == rowIndex)))
                              .ToCached()
                              .DisposeWith(_subscriptions);

            var modelContent = cachedModel
                               .Select(x => x?.Content
                                       ?? Observable.Return <DominoModel>(null))
                               .SelectLatest();

            Observable.CombineLatest(
                modelContent
                .Select(x => x?.FirstSuit),
                modelContent
                .Select(x => x?.SecondSuit),
                cachedModel
                .Select(x => x?.IsRotated),
                (firstSuit, secondSuit, isRotated) => (firstSuit, secondSuit, isRotated))
            .Subscribe(x =>
            {
                if (!(x.isRotated is null))
                {
                    if (x.isRotated.Value)
                    {
                        FirstSuit  = x.secondSuit;
                        SecondSuit = x.firstSuit;
                    }
                    else
                    {
                        FirstSuit  = x.firstSuit;
                        SecondSuit = x.secondSuit;
                    }
                }
            })
            .DisposeWith(_subscriptions);

            modelContent
            .Select(x => x is null)
            .Subscribe(x => IsEmpty = x)
            .DisposeWith(_subscriptions);

            cachedModel
            .Select(x => x?.IsFaceUp?.Select(y => (bool?)y)
                    ?? Observable.Return <bool?>(null))
            .SelectLatest()
            .Subscribe(x => IsFaceUp = x)
            .DisposeWith(_subscriptions);

            FlipCommand = new AsyncActionCommand(
                cancellationToken => gameplayService.FlipTileAsync(cachedModel.Value, cancellationToken),
                gameplayService.ObserveCanFlipTile(cachedModel))
                          .DisposeWith(_subscriptions);
        }
Ejemplo n.º 14
0
        /// <summary>
        /// Passes provided parameters to the base constructor and initializes commands.
        /// </summary>
        /// <param name="resourceProvider">IResourceProvider for localizing strings.</param>
        /// <param name="navigationViewModel"></param>
        /// <param name="persistenceService"></param>
        /// <param name="clipboardService"></param>
        /// <param name="settingsService"></param>
        /// <param name="document"></param>
        /// <param name="entry"></param>
        /// <param name="isNew"></param>
        /// <param name="isReadOnly"></param>
        /// <param name="rng"></param>
        private EntryDetailsViewModel(
            IResourceProvider resourceProvider,
            IDatabaseNavigationViewModel navigationViewModel,
            IDatabasePersistenceService persistenceService,
            ISensitiveClipboardService clipboardService,
            IAppSettingsService settingsService,
            KdbxDocument document,
            IKeePassEntry entry,
            bool isNew,
            bool isReadOnly,
            IRandomNumberGenerator rng
            ) : base(navigationViewModel, persistenceService, document, entry, isNew, isReadOnly)
        {
            this.resourceProvider = resourceProvider;
            this.clipboardService = clipboardService;
            this.settingsService  = settingsService;
            this.rng = rng;

            this.copyFieldValueCommand = new TypedCommand <IProtectedString>(
                str =>
            {
                clipboardService.CopyCredential(str.ClearValue, ClipboardOperationType.Other);
            }
                );

            this.deleteFieldCommand = new TypedCommand <IProtectedString>(
                str => !IsReadOnly && PersistenceService.CanSave,
                str =>
            {
                DebugHelper.Assert(!IsReadOnly);
                WorkingCopy.Fields.Remove(str);
            }
                );

            this.editFieldCommand = new AsyncTypedCommand <IProtectedString>(
                str => PersistenceService.CanSave,
                async str =>
            {
                IsReadOnly = false;
                await UpdateFieldEditorViewModel(new FieldEditorViewModel(str, this.resourceProvider));
            }
                );

            this.newFieldCommand = new AsyncActionCommand(
                () => PersistenceService.CanSave,
                async() =>
            {
                IsReadOnly = false;
                await UpdateFieldEditorViewModel(new FieldEditorViewModel(this.rng, this.resourceProvider));
            }
                );

            this.commitFieldCommand = new AsyncActionCommand(
                () => FieldEditorViewModel?.CommitCommand.CanExecute(WorkingCopy) ?? false,
                async() =>
            {
                FieldEditorViewModel.CommitCommand.Execute(WorkingCopy);
                await UpdateFieldEditorViewModel(null);
            }
                );

            PropertyChanged += (s, e) =>
            {
                if (e.PropertyName == nameof(IsReadOnly))
                {
                    ((TypedCommand <IProtectedString>)DeleteFieldCommand).RaiseCanExecuteChanged();
                }
                else if (e.PropertyName == nameof(WorkingCopy))
                {
                    OnPropertyChanged(nameof(WorkingCopyViewModel));
                }
            };
        }